diff --git a/Software/VNA_embedded/.cproject b/Software/VNA_embedded/.cproject
index 486deae..ed61843 100644
--- a/Software/VNA_embedded/.cproject
+++ b/Software/VNA_embedded/.cproject
@@ -151,6 +151,8 @@
+
+
@@ -185,6 +187,8 @@
+
+
diff --git a/Software/VNA_embedded/Application/App.cpp b/Software/VNA_embedded/Application/App.cpp
index c8d9602..6e09120 100644
--- a/Software/VNA_embedded/Application/App.cpp
+++ b/Software/VNA_embedded/Application/App.cpp
@@ -5,12 +5,11 @@
#include "Communication.h"
#include "main.h"
#include "Exti.hpp"
-#include "FPGA.hpp"
+#include "FPGA/FPGA.hpp"
#include
#include
#include "USB/usb.h"
#include "Flash.hpp"
-#include "Firmware.hpp"
#include "FreeRTOS.h"
#include "task.h"
@@ -28,12 +27,17 @@ static Protocol::PacketInfo packet;
static TaskHandle_t handle;
// TODO set proper values
-#define HW_REVISION 'A'
+//#define HW_REVISION 'A'
#define FW_MAJOR 0
#define FW_MINOR 01
+#if HW_REVISION >= 'B'
+// has MCU controllable flash chip, firmware update supported
+#define HAS_FLASH
+#include "Firmware.hpp"
extern SPI_HandleTypeDef hspi1;
static Flash flash = Flash(&hspi1, FLASH_CS_GPIO_Port, FLASH_CS_Pin);
+#endif
#define FLAG_USB_PACKET 0x01
#define FLAG_DATAPOINT 0x02
@@ -67,6 +71,7 @@ void App_Start() {
Log_SetRedirect(usb_log);
LOG_INFO("Start");
Exti::Init();
+#ifdef HAS_FLASH
if(!flash.isPresent()) {
LOG_CRIT("Failed to detect onboard FLASH");
}
@@ -80,10 +85,19 @@ void App_Start() {
} else {
LOG_CRIT("Invalid bitstream/firmware, not configuring FPGA");
}
+#else
+ // The FPGA configures itself from the flash, allow time for this
+ vTaskDelay(2000);
+#endif
if (!VNA::Init()) {
LOG_CRIT("Initialization failed, unable to start");
}
+#if HW_REVISION == 'A'
+ // Allow USB enumeration
+ USB_EN_GPIO_Port->BSRR = USB_EN_Pin;
+#endif
+
uint32_t lastNewPoint = HAL_GetTick();
bool sweepActive = false;
@@ -180,25 +194,23 @@ void App_Start() {
manual = packet.manual;
VNA::ConfigureManual(manual, VNAStatusCallback);
break;
+#ifdef HAS_FLASH
case Protocol::PacketType::ClearFlash:
FPGA::AbortSweep();
sweepActive = false;
LOG_DEBUG("Erasing FLASH in preparation for firmware update...");
if(flash.eraseChip()) {
LOG_DEBUG("...FLASH erased")
- Protocol::PacketInfo p;
- p.type = Protocol::PacketType::Ack;
- Communication::Send(p);
+ Communication::SendWithoutPayload(Protocol::PacketType::Ack);
} else {
LOG_ERR("Failed to erase FLASH");
+ Communication::SendWithoutPayload(Protocol::PacketType::Nack);
}
break;
case Protocol::PacketType::FirmwarePacket:
LOG_INFO("Writing firmware packet at address %u", packet.firmware.address);
flash.write(packet.firmware.address, sizeof(packet.firmware.data), packet.firmware.data);
- Protocol::PacketInfo p;
- p.type = Protocol::PacketType::Ack;
- Communication::Send(p);
+ Communication::SendWithoutPayload(Protocol::PacketType::Ack);
break;
case Protocol::PacketType::PerformFirmwareUpdate: {
auto fw_info = Firmware::GetFlashContentInfo(&flash);
@@ -209,12 +221,15 @@ void App_Start() {
// Some delay to allow communication to finish
vTaskDelay(1000);
Firmware::PerformUpdate(&flash);
- // will never get here
+ // should never get here
+ Communication::SendWithoutPayload(Protocol::PacketType::Nack);
}
}
break;
+#endif
default:
- // ignore all other packets
+ // this packet type is not supported
+ Communication::SendWithoutPayload(Protocol::PacketType::Nack);
break;
}
}
diff --git a/Software/VNA_embedded/Application/Communication/Communication.cpp b/Software/VNA_embedded/Application/Communication/Communication.cpp
index 9b9b64e..0fb7122 100644
--- a/Software/VNA_embedded/Application/Communication/Communication.cpp
+++ b/Software/VNA_embedded/Application/Communication/Communication.cpp
@@ -63,3 +63,8 @@ void communication_usb_input(const uint8_t *buf, uint16_t len) {
Communication::Input(buf, len);
}
+bool Communication::SendWithoutPayload(Protocol::PacketType type) {
+ Protocol::PacketInfo p;
+ p.type = type;
+ return Send(p);
+}
diff --git a/Software/VNA_embedded/Application/Communication/Communication.h b/Software/VNA_embedded/Application/Communication/Communication.h
index d7fbd4d..1db380c 100644
--- a/Software/VNA_embedded/Application/Communication/Communication.h
+++ b/Software/VNA_embedded/Application/Communication/Communication.h
@@ -13,6 +13,7 @@ using Callback = void(*)(Protocol::PacketInfo);
void SetCallback(Callback cb);
void Input(const uint8_t *buf, uint16_t len);
bool Send(Protocol::PacketInfo packet);
+bool SendWithoutPayload(Protocol::PacketType type);
}
diff --git a/Software/VNA_embedded/Application/Communication/Protocol.hpp b/Software/VNA_embedded/Application/Communication/Protocol.hpp
index f30449b..6d62027 100644
--- a/Software/VNA_embedded/Application/Communication/Protocol.hpp
+++ b/Software/VNA_embedded/Application/Communication/Protocol.hpp
@@ -101,6 +101,7 @@ enum class PacketType : uint8_t {
Ack = 7,
ClearFlash = 8,
PerformFirmwareUpdate = 9,
+ Nack = 10,
};
using PacketInfo = struct _packetinfo {
diff --git a/Software/VNA_embedded/Application/Drivers/Exti.cpp b/Software/VNA_embedded/Application/Drivers/Exti.cpp
index 5f57e90..204713f 100644
--- a/Software/VNA_embedded/Application/Drivers/Exti.cpp
+++ b/Software/VNA_embedded/Application/Drivers/Exti.cpp
@@ -11,13 +11,13 @@ static constexpr uint8_t MaxEntries = 16;
static Entry entries[MaxEntries];
void Exti::Init() {
- HAL_NVIC_SetPriority(EXTI0_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI1_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI2_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI3_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI4_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI9_5_IRQn, 1, 0);
- HAL_NVIC_SetPriority(EXTI15_10_IRQn, 1, 0);
+ HAL_NVIC_SetPriority(EXTI0_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI1_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI2_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI3_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI4_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI9_5_IRQn, 5, 0);
+ HAL_NVIC_SetPriority(EXTI15_10_IRQn, 5, 0);
HAL_NVIC_EnableIRQ(EXTI0_IRQn);
HAL_NVIC_EnableIRQ(EXTI1_IRQn);
HAL_NVIC_EnableIRQ(EXTI2_IRQn);
diff --git a/Software/VNA_embedded/Application/Drivers/FPGA.cpp b/Software/VNA_embedded/Application/Drivers/FPGA/FPGA.cpp
similarity index 88%
rename from Software/VNA_embedded/Application/Drivers/FPGA.cpp
rename to Software/VNA_embedded/Application/Drivers/FPGA/FPGA.cpp
index 14d6179..4ee7ef8 100644
--- a/Software/VNA_embedded/Application/Drivers/FPGA.cpp
+++ b/Software/VNA_embedded/Application/Drivers/FPGA/FPGA.cpp
@@ -2,42 +2,18 @@
#include "delay.hpp"
#include "stm.hpp"
#include "main.h"
+#include "FPGA_HAL.hpp"
#define LOG_LEVEL LOG_LEVEL_DEBUG
#define LOG_MODULE "FPGA"
#include "Log.h"
-#define FPGA_SPI hspi1
-#define CONFIGURATION_SPI hspi2
-extern SPI_HandleTypeDef FPGA_SPI, CONFIGURATION_SPI;
-
-using GPIO = struct {
- GPIO_TypeDef *gpio;
- uint16_t pin;
-};
-static constexpr GPIO CS = {.gpio = FPGA_CS_GPIO_Port, .pin = FPGA_CS_Pin};
-static constexpr GPIO PROGRAM_B = {.gpio = FPGA_PROGRAM_B_GPIO_Port, .pin = FPGA_PROGRAM_B_Pin};
-static constexpr GPIO INIT_B = {.gpio = FPGA_INIT_B_GPIO_Port, .pin = FPGA_INIT_B_Pin};
-static constexpr GPIO DONE = {.gpio = FPGA_DONE_GPIO_Port, .pin = FPGA_DONE_Pin};
-static constexpr GPIO FPGA_RESET = {.gpio = FPGA_RESET_GPIO_Port, .pin = FPGA_RESET_Pin};
-static constexpr GPIO AUX1 = {.gpio = FPGA_AUX1_GPIO_Port, .pin = FPGA_AUX1_Pin};
-static constexpr GPIO AUX2 = {.gpio = FPGA_AUX2_GPIO_Port, .pin = FPGA_AUX2_Pin};
-static constexpr GPIO AUX3 = {.gpio = FPGA_AUX3_GPIO_Port, .pin = FPGA_AUX3_Pin};
-
-static inline void Low(GPIO g) {
- g.gpio->BSRR = g.pin << 16;
-}
-static inline void High(GPIO g) {
- g.gpio->BSRR = g.pin;
-}
-bool isHigh(GPIO g) {
- return g.gpio->IDR & g.pin;
-}
-
static FPGA::HaltedCallback halted_cb;
static uint16_t SysCtrlReg = 0x0000;
static uint16_t ISRMaskReg = 0x0000;
+using namespace FPGAHAL;
+
void WriteRegister(FPGA::Reg reg, uint16_t value) {
uint16_t cmd[2] = {(uint16_t) (0x8000 | (uint16_t) reg), value};
Low(CS);
@@ -46,6 +22,12 @@ void WriteRegister(FPGA::Reg reg, uint16_t value) {
}
bool FPGA::Configure(Flash *f, uint32_t start_address, uint32_t bitstream_size) {
+ if(!PROGRAM_B.gpio) {
+ LOG_WARN("PROGRAM_B not defined, assuming FPGA configures itself in master configuration");
+ // wait too allow enough time for FPGA configuration
+ HAL_Delay(2000);
+ return true;
+ }
LOG_INFO("Loading bitstream of size %lu...", bitstream_size);
Low(PROGRAM_B);
while(isHigh(INIT_B));
diff --git a/Software/VNA_embedded/Application/Drivers/FPGA.hpp b/Software/VNA_embedded/Application/Drivers/FPGA/FPGA.hpp
similarity index 100%
rename from Software/VNA_embedded/Application/Drivers/FPGA.hpp
rename to Software/VNA_embedded/Application/Drivers/FPGA/FPGA.hpp
diff --git a/Software/VNA_embedded/Application/Drivers/FPGA/FPGA_HAL.hpp b/Software/VNA_embedded/Application/Drivers/FPGA/FPGA_HAL.hpp
new file mode 100644
index 0000000..87196a1
--- /dev/null
+++ b/Software/VNA_embedded/Application/Drivers/FPGA/FPGA_HAL.hpp
@@ -0,0 +1,43 @@
+#pragma once
+
+#include "stm.hpp"
+#include "main.h"
+
+#define FPGA_SPI hspi1
+#define CONFIGURATION_SPI hspi2
+extern SPI_HandleTypeDef FPGA_SPI, CONFIGURATION_SPI;
+
+namespace FPGAHAL {
+
+using GPIO = struct {
+ GPIO_TypeDef *gpio;
+ uint16_t pin;
+};
+static constexpr GPIO CS = {.gpio = FPGA_CS_GPIO_Port, .pin = FPGA_CS_Pin};
+static constexpr GPIO PROGRAM_B = {.gpio = FPGA_PROGRAM_B_GPIO_Port, .pin = FPGA_PROGRAM_B_Pin};
+static constexpr GPIO INIT_B = {.gpio = FPGA_INIT_B_GPIO_Port, .pin = FPGA_INIT_B_Pin};
+static constexpr GPIO DONE = {.gpio = FPGA_DONE_GPIO_Port, .pin = FPGA_DONE_Pin};
+static constexpr GPIO FPGA_RESET = {.gpio = FPGA_RESET_GPIO_Port, .pin = FPGA_RESET_Pin};
+static constexpr GPIO AUX1 = {.gpio = FPGA_AUX1_GPIO_Port, .pin = FPGA_AUX1_Pin};
+static constexpr GPIO AUX2 = {.gpio = FPGA_AUX2_GPIO_Port, .pin = FPGA_AUX2_Pin};
+static constexpr GPIO AUX3 = {.gpio = FPGA_AUX3_GPIO_Port, .pin = FPGA_AUX3_Pin};
+
+static inline void Low(GPIO g) {
+ if(g.gpio) {
+ g.gpio->BSRR = g.pin << 16;
+ }
+}
+static inline void High(GPIO g) {
+ if(g.gpio) {
+ g.gpio->BSRR = g.pin;
+ }
+}
+bool isHigh(GPIO g) {
+ if(g.gpio) {
+ return g.gpio->IDR & g.pin;
+ } else {
+ return false;
+ }
+}
+
+}
diff --git a/Software/VNA_embedded/Application/VNA.cpp b/Software/VNA_embedded/Application/VNA.cpp
index 02edfee..2ebda5f 100644
--- a/Software/VNA_embedded/Application/VNA.cpp
+++ b/Software/VNA_embedded/Application/VNA.cpp
@@ -3,21 +3,15 @@
#include "max2871.hpp"
#include "main.h"
#include "delay.hpp"
-#include "FPGA.hpp"
+#include "FPGA/FPGA.hpp"
#include
#include "Exti.hpp"
+#include "VNA_HAL.hpp"
#define LOG_LEVEL LOG_LEVEL_INFO
#define LOG_MODULE "VNA"
#include "Log.h"
-extern I2C_HandleTypeDef hi2c2;
-extern SPI_HandleTypeDef hspi1;
-
-static Si5351C Si5351 = Si5351C(&hi2c2, 26000000);
-static MAX2871 Source = MAX2871(&hspi1, FPGA_CS_GPIO_Port, FPGA_CS_Pin, nullptr, 0, nullptr, 0, nullptr, 0, GPIOB, GPIO_PIN_4);
-static MAX2871 LO1 = MAX2871(&hspi1, FPGA_CS_GPIO_Port, FPGA_CS_Pin, nullptr, 0, nullptr, 0, nullptr, 0, GPIOB, GPIO_PIN_4);
-
static constexpr uint32_t IF1 = 60100000;
static constexpr uint32_t IF1_alternate = 57000000;
static constexpr uint32_t IF2 = 250000;
@@ -42,6 +36,8 @@ static uint16_t IFTableIndexCnt = 0;
static constexpr uint32_t BandSwitchFrequency = 25000000;
+using namespace VNAHAL;
+
static void HaltedCallback() {
LOG_DEBUG("Halted before point %d", pointCnt);
// Check if IF table has entry at this point
@@ -59,16 +55,16 @@ static void HaltedCallback() {
/ (settings.points - 1);
if (frequency < BandSwitchFrequency) {
// need the Si5351 as Source
- Si5351.SetCLK(0, frequency, Si5351C::PLL::B,
+ Si5351.SetCLK(SiChannel::LowbandSource, frequency, Si5351C::PLL::B,
Si5351C::DriveStrength::mA2);
if (pointCnt == 0) {
// First point in sweep, enable CLK
- Si5351.Enable(0);
+ Si5351.Enable(SiChannel::LowbandSource);
FPGA::Disable(FPGA::Periphery::SourceRF);
}
} else {
// first sweep point in highband is also halted, disable lowband source
- Si5351.Disable(0);
+ Si5351.Disable(SiChannel::LowbandSource);
FPGA::Enable(FPGA::Periphery::SourceRF);
}
@@ -122,8 +118,6 @@ static void FPGA_Interrupt(void*) {
bool VNA::Init() {
LOG_DEBUG("Initializing...");
- // Wait for FPGA to finish configuration
- Delay::ms(2000);
manualMode = false;
Si5351.Init();
@@ -136,24 +130,25 @@ bool VNA::Init() {
while(!Si5351.Locked(Si5351C::PLL::B));
// Both MAX2871 get a 100MHz reference
- Si5351.SetCLK(2, 100000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
- Si5351.Enable(2);
- Si5351.SetCLK(3, 100000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
- Si5351.Enable(3);
+ Si5351.SetCLK(SiChannel::Source, 100000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::Source);
+ Si5351.SetCLK(SiChannel::LO1, 100000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::LO1);
// 16MHz FPGA clock
- Si5351.SetCLK(7, 16000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
- Si5351.Enable(7);
- // 10 MHz external reference clock
- Si5351.SetCLK(6, 10000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA8);
- Si5351.Enable(6);
+ Si5351.SetCLK(SiChannel::FPGA, 16000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::FPGA);
+ // TODO reference settings controllable through USB
+// // 10 MHz external reference clock
+// Si5351.SetCLK(6, 10000000, Si5351C::PLL::A, Si5351C::DriveStrength::mA8);
+// Si5351.Enable(6);
// Generate second LO with Si5351
- Si5351.SetCLK(1, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(1);
- Si5351.SetCLK(4, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(4);
- Si5351.SetCLK(5, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(5);
+ Si5351.SetCLK(SiChannel::Port1LO2, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::Port1LO2);
+ Si5351.SetCLK(SiChannel::Port2LO2, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::Port2LO2);
+ Si5351.SetCLK(SiChannel::RefLO2, IF1 - IF2, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::RefLO2);
// PLL reset appears to realign phases of clock signals
Si5351.ResetPLL(Si5351C::PLL::B);
@@ -301,7 +296,7 @@ bool VNA::ConfigureSweep(Protocol::SweepSettings s, SweepCallback cb) {
IFTable[IFTableIndexCnt].IF1 = used_IF;
// Configure LO2 for the changed IF1. This is not necessary right now but it will generate
// the correct clock settings
- Si5351.SetCLK(1, used_IF + IF2, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
+ Si5351.SetCLK(SiChannel::RefLO2, used_IF + IF2, Si5351C::PLL::A, Si5351C::DriveStrength::mA2);
// store calculated clock configuration for later change
Si5351.ReadRawCLKConfig(1, IFTable[IFTableIndexCnt].clkconfig);
IFTableIndexCnt++;
@@ -349,11 +344,11 @@ bool VNA::ConfigureManual(Protocol::ManualControl m, StatusCallback cb) {
FPGA::AbortSweep();
// Configure lowband source
if (m.SourceLowEN) {
- Si5351.SetCLK(0, m.SourceLowFrequency, Si5351C::PLL::B,
+ Si5351.SetCLK(SiChannel::LowbandSource, m.SourceLowFrequency, Si5351C::PLL::B,
(Si5351C::DriveStrength) m.SourceLowPower);
- Si5351.Enable(0);
+ Si5351.Enable(SiChannel::LowbandSource);
} else {
- Si5351.Disable(0);
+ Si5351.Disable(SiChannel::LowbandSource);
}
// Configure highband source
Source.SetFrequency(m.SourceHighFrequency);
@@ -365,19 +360,19 @@ bool VNA::ConfigureManual(Protocol::ManualControl m, StatusCallback cb) {
// Configure LO2
if(m.LO2EN) {
// Generate second LO with Si5351
- Si5351.SetCLK(1, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(1);
- Si5351.SetCLK(4, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(4);
- Si5351.SetCLK(5, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
- Si5351.Enable(5);
+ Si5351.SetCLK(SiChannel::Port1LO2, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::Port1LO2);
+ Si5351.SetCLK(SiChannel::Port2LO2, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::Port2LO2);
+ Si5351.SetCLK(SiChannel::RefLO2, m.LO2Frequency, Si5351C::PLL::B, Si5351C::DriveStrength::mA2);
+ Si5351.Enable(SiChannel::RefLO2);
// PLL reset appears to realign phases of clock signals
Si5351.ResetPLL(Si5351C::PLL::B);
} else {
- Si5351.Disable(1);
- Si5351.Disable(4);
- Si5351.Disable(5);
+ Si5351.Disable(SiChannel::Port1LO2);
+ Si5351.Disable(SiChannel::Port2LO2);
+ Si5351.Disable(SiChannel::RefLO2);
}
FPGA::WriteMAX2871Default(Source.GetRegisters());
diff --git a/Software/VNA_embedded/Application/VNA.hpp b/Software/VNA_embedded/Application/VNA.hpp
index 6b65e95..74d379f 100644
--- a/Software/VNA_embedded/Application/VNA.hpp
+++ b/Software/VNA_embedded/Application/VNA.hpp
@@ -2,7 +2,7 @@
#include
#include "Protocol.hpp"
-#include "FPGA.hpp"
+#include "FPGA/FPGA.hpp"
namespace VNA {
diff --git a/Software/VNA_embedded/Application/VNA_HAL.hpp b/Software/VNA_embedded/Application/VNA_HAL.hpp
new file mode 100644
index 0000000..6e3d0fa
--- /dev/null
+++ b/Software/VNA_embedded/Application/VNA_HAL.hpp
@@ -0,0 +1,31 @@
+#pragma once
+
+#include "stm.hpp"
+#include "Si5351C.hpp"
+#include "max2871.hpp"
+#include "main.h"
+
+extern I2C_HandleTypeDef hi2c2;
+extern SPI_HandleTypeDef hspi1;
+
+namespace VNAHAL {
+
+static Si5351C Si5351 = Si5351C(&hi2c2, 26000000);
+static MAX2871 Source = MAX2871(&hspi1, FPGA_CS_GPIO_Port, FPGA_CS_Pin, nullptr, 0, nullptr, 0, nullptr, 0, GPIOB, GPIO_PIN_4);
+static MAX2871 LO1 = MAX2871(&hspi1, FPGA_CS_GPIO_Port, FPGA_CS_Pin, nullptr, 0, nullptr, 0, nullptr, 0, GPIOB, GPIO_PIN_4);
+
+// Mapping of the Si5351 channels to PLLs/Mixers
+namespace SiChannel {
+ enum {
+ Source = 3,
+ LO1 = 5,
+ Port2LO2 = 4,
+ RefLO2 = 1,
+ Port1LO2 = 2,
+ LowbandSource = 1,
+ ReferenceOut = 6,
+ FPGA = 7,
+ };
+}
+
+}