mirror of
https://github.com/meshtastic/firmware.git
synced 2025-08-03 12:20:43 +00:00
Multi gpiochip support for native environment (#5743)
* For each GPIO PIN, allow to specify gpiochip and line * Added support for LLCC68 in native env. * Removed one if by employing && * Fix for log, as std::string and not const char* * Remove CH341 flag, enabling it for all LoRa chips * Provide a default example --------- Co-authored-by: Ben Meadors <benmmeadors@gmail.com> Co-authored-by: Jonathan Bennett <jbennett@incomsystems.biz>
This commit is contained in:
parent
0cf4a2951a
commit
70296b47bc
@ -23,6 +23,47 @@ Lora:
|
|||||||
# Busy: 20
|
# Busy: 20
|
||||||
# Reset: 18
|
# Reset: 18
|
||||||
|
|
||||||
|
### The Radxa Zero 3E/W employs multiple gpio chips.
|
||||||
|
### Each gpio pin must be unique, but can be assigned to a specific gpio chip and line.
|
||||||
|
### In case solely a no. is given, the default gpio chip and pin == line will be employed.
|
||||||
|
###
|
||||||
|
# Module: sx1262 # Radxa Zero 3E/W + Ebyte E22-900M30S
|
||||||
|
# DIO2_AS_RF_SWITCH: true
|
||||||
|
# DIO3_TCXO_VOLTAGE: 1.8
|
||||||
|
# CS: # NSS PIN_24 -> chip 4, line 22
|
||||||
|
# pin: 24
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 22
|
||||||
|
# SCK: # SCK PIN_23 -> chip 4, line 18
|
||||||
|
# pin: 23
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 18
|
||||||
|
# Busy: # BUSY PIN_29 -> chip 3!, line 11
|
||||||
|
# pin: 29
|
||||||
|
# gpiochip: 3
|
||||||
|
# line: 11
|
||||||
|
# MOSI: # MOSI PIN_19 -> chip 4, line 19
|
||||||
|
# pin: 19
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 19
|
||||||
|
# MISO: # MISO PIN_21 -> chip 4, line 21
|
||||||
|
# pin: 21
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 21
|
||||||
|
# Reset: # NRST PIN_27 -> chip 4, line 10
|
||||||
|
# pin: 27
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 10
|
||||||
|
# IRQ: # DIO1 PIN_28 -> chip 4, line 11
|
||||||
|
# pin: 28
|
||||||
|
# gpiochip: 4
|
||||||
|
# line: 11
|
||||||
|
# RXen: # RXEN PIN_22 -> chip 3!, line 17
|
||||||
|
# pin: 22
|
||||||
|
# gpiochip: 3
|
||||||
|
# line: 17
|
||||||
|
# TXen: RADIOLIB_NC # TXEN no PIN, no line, fallback to default gpio chip
|
||||||
|
|
||||||
# Module: sx1268 # SX1268-based modules, tested with Ebyte E22 400M33S
|
# Module: sx1268 # SX1268-based modules, tested with Ebyte E22 400M33S
|
||||||
# CS: 21
|
# CS: 21
|
||||||
# IRQ: 16
|
# IRQ: 16
|
||||||
@ -39,7 +80,7 @@ Lora:
|
|||||||
|
|
||||||
# spiSpeed: 2000000
|
# spiSpeed: 2000000
|
||||||
|
|
||||||
### Set gpio chip to use in /dev/. Defaults to 0.
|
### Set default/fallback gpio chip to use in /dev/. Defaults to 0.
|
||||||
### Notably the Raspberry Pi 5 puts the GPIO header on gpiochip4
|
### Notably the Raspberry Pi 5 puts the GPIO header on gpiochip4
|
||||||
# gpiochip: 4
|
# gpiochip: 4
|
||||||
|
|
||||||
|
139
src/main.cpp
139
src/main.cpp
@ -826,116 +826,61 @@ void setup()
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef ARCH_PORTDUINO
|
#ifdef ARCH_PORTDUINO
|
||||||
if (settingsMap[use_sx1262]) {
|
const struct { configNames cfgName;
|
||||||
if (!rIf) {
|
std::string strName;
|
||||||
LOG_DEBUG("Activate sx1262 radio on SPI port %s", settingsStrings[spidev].c_str());
|
} loraModules[] = {
|
||||||
|
{ use_rf95, "RF95" },
|
||||||
|
{ use_sx1262, "sx1262" },
|
||||||
|
{ use_sx1268, "sx1268" },
|
||||||
|
{ use_sx1280, "sx1280" },
|
||||||
|
{ use_lr1110, "lr1110" },
|
||||||
|
{ use_lr1120, "lr1120" },
|
||||||
|
{ use_lr1121, "lr1121" },
|
||||||
|
{ use_llcc68, "LLCC68" }
|
||||||
|
};
|
||||||
|
// as one can't use a function pointer to the class constructor:
|
||||||
|
auto loraModuleInterface = [](configNames cfgName, LockingArduinoHal *hal, RADIOLIB_PIN_TYPE cs, RADIOLIB_PIN_TYPE irq, RADIOLIB_PIN_TYPE rst, RADIOLIB_PIN_TYPE busy) {
|
||||||
|
switch (cfgName) {
|
||||||
|
case use_rf95:
|
||||||
|
return (RadioInterface*)new RF95Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_sx1262:
|
||||||
|
return (RadioInterface*)new SX1262Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_sx1268:
|
||||||
|
return (RadioInterface*)new SX1268Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_sx1280:
|
||||||
|
return (RadioInterface*)new SX1280Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_lr1110:
|
||||||
|
return (RadioInterface*)new LR1110Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_lr1120:
|
||||||
|
return (RadioInterface*)new LR1120Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_lr1121:
|
||||||
|
return (RadioInterface*)new LR1121Interface(hal, cs, irq, rst, busy);
|
||||||
|
case use_llcc68:
|
||||||
|
return (RadioInterface*)new LLCC68Interface(hal, cs, irq, rst, busy);
|
||||||
|
default:
|
||||||
|
assert(0); // shouldn't happen
|
||||||
|
return (RadioInterface*)nullptr;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
for (auto& loraModule : loraModules) {
|
||||||
|
if (settingsMap[loraModule.cfgName] && !rIf) {
|
||||||
|
LOG_DEBUG("Activate %s radio on SPI port %s", loraModule.strName.c_str(), settingsStrings[spidev].c_str());
|
||||||
if (settingsStrings[spidev] == "ch341") {
|
if (settingsStrings[spidev] == "ch341") {
|
||||||
RadioLibHAL = ch341Hal;
|
RadioLibHAL = ch341Hal;
|
||||||
} else {
|
} else {
|
||||||
RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
||||||
}
|
}
|
||||||
rIf = new SX1262Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
rIf = loraModuleInterface(loraModule.cfgName, (LockingArduinoHal *)RadioLibHAL, settingsMap[cs_pin], settingsMap[irq_pin], settingsMap[reset_pin], settingsMap[busy_pin]);
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
if (!rIf->init()) {
|
||||||
LOG_WARN("No SX1262 radio");
|
LOG_WARN("No %s radio", loraModule.strName.c_str());
|
||||||
delete rIf;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("SX1262 init success");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_rf95]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate rf95 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new RF95Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No RF95 radio");
|
|
||||||
delete rIf;
|
delete rIf;
|
||||||
rIf = NULL;
|
rIf = NULL;
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
} else {
|
} else {
|
||||||
LOG_INFO("RF95 init success");
|
LOG_INFO("%s init success", loraModule.strName.c_str());
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_sx1280]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate sx1280 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new SX1280Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No SX1280 radio");
|
|
||||||
delete rIf;
|
|
||||||
rIf = NULL;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("SX1280 init success");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_lr1110]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate lr1110 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
LockingArduinoHal *RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new LR1110Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No LR1110 radio");
|
|
||||||
delete rIf;
|
|
||||||
rIf = NULL;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("LR1110 init success");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_lr1120]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate lr1120 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
LockingArduinoHal *RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new LR1120Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No LR1120 radio");
|
|
||||||
delete rIf;
|
|
||||||
rIf = NULL;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("LR1120 init success");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_lr1121]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate lr1121 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
LockingArduinoHal *RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new LR1121Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No LR1121 radio");
|
|
||||||
delete rIf;
|
|
||||||
rIf = NULL;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("LR1121 init success");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (settingsMap[use_sx1268]) {
|
|
||||||
if (!rIf) {
|
|
||||||
LOG_DEBUG("Activate sx1268 radio on SPI port %s", settingsStrings[spidev].c_str());
|
|
||||||
RadioLibHAL = new LockingArduinoHal(SPI, spiSettings);
|
|
||||||
rIf = new SX1268Interface((LockingArduinoHal *)RadioLibHAL, settingsMap[cs], settingsMap[irq], settingsMap[reset],
|
|
||||||
settingsMap[busy]);
|
|
||||||
if (!rIf->init()) {
|
|
||||||
LOG_WARN("No SX1268 radio");
|
|
||||||
delete rIf;
|
|
||||||
rIf = NULL;
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
} else {
|
|
||||||
LOG_INFO("SX1268 init success");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#elif defined(HW_SPI1_DEVICE)
|
#elif defined(HW_SPI1_DEVICE)
|
||||||
LockingArduinoHal *RadioLibHAL = new LockingArduinoHal(SPI1, spiSettings);
|
LockingArduinoHal *RadioLibHAL = new LockingArduinoHal(SPI1, spiSettings);
|
||||||
#else // HW_SPI1_DEVICE
|
#else // HW_SPI1_DEVICE
|
||||||
|
@ -91,16 +91,16 @@ void RF95Interface::setTransmitEnable(bool txon)
|
|||||||
#ifdef RF95_TXEN
|
#ifdef RF95_TXEN
|
||||||
digitalWrite(RF95_TXEN, txon ? 1 : 0);
|
digitalWrite(RF95_TXEN, txon ? 1 : 0);
|
||||||
#elif ARCH_PORTDUINO
|
#elif ARCH_PORTDUINO
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[txen], txon ? 1 : 0);
|
digitalWrite(settingsMap[txen_pin], txon ? 1 : 0);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef RF95_RXEN
|
#ifdef RF95_RXEN
|
||||||
digitalWrite(RF95_RXEN, txon ? 0 : 1);
|
digitalWrite(RF95_RXEN, txon ? 0 : 1);
|
||||||
#elif ARCH_PORTDUINO
|
#elif ARCH_PORTDUINO
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[rxen], txon ? 0 : 1);
|
digitalWrite(settingsMap[rxen_pin], txon ? 0 : 1);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@ -164,13 +164,13 @@ bool RF95Interface::init()
|
|||||||
digitalWrite(RF95_RXEN, 1);
|
digitalWrite(RF95_RXEN, 1);
|
||||||
#endif
|
#endif
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
pinMode(settingsMap[txen], OUTPUT);
|
pinMode(settingsMap[txen_pin], OUTPUT);
|
||||||
digitalWrite(settingsMap[txen], 0);
|
digitalWrite(settingsMap[txen_pin], 0);
|
||||||
}
|
}
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
pinMode(settingsMap[rxen], OUTPUT);
|
pinMode(settingsMap[rxen_pin], OUTPUT);
|
||||||
digitalWrite(settingsMap[rxen], 0);
|
digitalWrite(settingsMap[rxen_pin], 0);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
setTransmitEnable(false);
|
setTransmitEnable(false);
|
||||||
|
@ -51,9 +51,9 @@ template <typename T> bool SX126xInterface<T>::init()
|
|||||||
|
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
float tcxoVoltage = (float)settingsMap[dio3_tcxo_voltage] / 1000;
|
float tcxoVoltage = (float)settingsMap[dio3_tcxo_voltage] / 1000;
|
||||||
if (settingsMap[sx126x_ant_sw] != RADIOLIB_NC) {
|
if (settingsMap[sx126x_ant_sw_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[sx126x_ant_sw], HIGH);
|
digitalWrite(settingsMap[sx126x_ant_sw_pin], HIGH);
|
||||||
pinMode(settingsMap[sx126x_ant_sw], OUTPUT);
|
pinMode(settingsMap[sx126x_ant_sw_pin], OUTPUT);
|
||||||
}
|
}
|
||||||
// FIXME: correct logic to default to not using TCXO if no voltage is specified for SX126X_DIO3_TCXO_VOLTAGE
|
// FIXME: correct logic to default to not using TCXO if no voltage is specified for SX126X_DIO3_TCXO_VOLTAGE
|
||||||
#elif !defined(SX126X_DIO3_TCXO_VOLTAGE)
|
#elif !defined(SX126X_DIO3_TCXO_VOLTAGE)
|
||||||
@ -121,8 +121,8 @@ template <typename T> bool SX126xInterface<T>::init()
|
|||||||
// no effect
|
// no effect
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (res == RADIOLIB_ERR_NONE) {
|
if (res == RADIOLIB_ERR_NONE) {
|
||||||
LOG_DEBUG("Use MCU pin %i as RXEN and pin %i as TXEN to control RF switching", settingsMap[rxen], settingsMap[txen]);
|
LOG_DEBUG("Use MCU pin %i as RXEN and pin %i as TXEN to control RF switching", settingsMap[rxen_pin], settingsMap[txen_pin]);
|
||||||
lora.setRfSwitchPins(settingsMap[rxen], settingsMap[txen]);
|
lora.setRfSwitchPins(settingsMap[rxen_pin], settingsMap[txen_pin]);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
#ifndef SX126X_RXEN
|
#ifndef SX126X_RXEN
|
||||||
|
@ -38,13 +38,13 @@ template <typename T> bool SX128xInterface<T>::init()
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
pinMode(settingsMap[rxen], OUTPUT);
|
pinMode(settingsMap[rxen_pin], OUTPUT);
|
||||||
digitalWrite(settingsMap[rxen], LOW); // Set low before becoming an output
|
digitalWrite(settingsMap[rxen_pin], LOW); // Set low before becoming an output
|
||||||
}
|
}
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
pinMode(settingsMap[txen], OUTPUT);
|
pinMode(settingsMap[txen_pin], OUTPUT);
|
||||||
digitalWrite(settingsMap[txen], LOW); // Set low before becoming an output
|
digitalWrite(settingsMap[txen_pin], LOW); // Set low before becoming an output
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
#if defined(SX128X_RXEN) && (SX128X_RXEN != RADIOLIB_NC) // set not rx or tx mode
|
#if defined(SX128X_RXEN) && (SX128X_RXEN != RADIOLIB_NC) // set not rx or tx mode
|
||||||
@ -93,8 +93,8 @@ template <typename T> bool SX128xInterface<T>::init()
|
|||||||
lora.setRfSwitchPins(SX128X_RXEN, SX128X_TXEN);
|
lora.setRfSwitchPins(SX128X_RXEN, SX128X_TXEN);
|
||||||
}
|
}
|
||||||
#elif ARCH_PORTDUINO
|
#elif ARCH_PORTDUINO
|
||||||
if (res == RADIOLIB_ERR_NONE && settingsMap[rxen] != RADIOLIB_NC && settingsMap[txen] != RADIOLIB_NC) {
|
if (res == RADIOLIB_ERR_NONE && settingsMap[rxen_pin] != RADIOLIB_NC && settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
lora.setRfSwitchPins(settingsMap[rxen], settingsMap[txen]);
|
lora.setRfSwitchPins(settingsMap[rxen_pin], settingsMap[txen_pin]);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -174,11 +174,11 @@ template <typename T> void SX128xInterface<T>::setStandby()
|
|||||||
LOG_ERROR("SX128x standby %s%d", radioLibErr, err);
|
LOG_ERROR("SX128x standby %s%d", radioLibErr, err);
|
||||||
assert(err == RADIOLIB_ERR_NONE);
|
assert(err == RADIOLIB_ERR_NONE);
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[rxen], LOW);
|
digitalWrite(settingsMap[rxen_pin], LOW);
|
||||||
}
|
}
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[txen], LOW);
|
digitalWrite(settingsMap[txen_pin], LOW);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
#if defined(SX128X_RXEN) && (SX128X_RXEN != RADIOLIB_NC) // we have RXEN/TXEN control - turn off RX and TX power
|
#if defined(SX128X_RXEN) && (SX128X_RXEN != RADIOLIB_NC) // we have RXEN/TXEN control - turn off RX and TX power
|
||||||
@ -210,11 +210,11 @@ template <typename T> void SX128xInterface<T>::addReceiveMetadata(meshtastic_Mes
|
|||||||
template <typename T> void SX128xInterface<T>::configHardwareForSend()
|
template <typename T> void SX128xInterface<T>::configHardwareForSend()
|
||||||
{
|
{
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[txen], HIGH);
|
digitalWrite(settingsMap[txen_pin], HIGH);
|
||||||
}
|
}
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[rxen], LOW);
|
digitalWrite(settingsMap[rxen_pin], LOW);
|
||||||
}
|
}
|
||||||
|
|
||||||
#else
|
#else
|
||||||
@ -241,11 +241,11 @@ template <typename T> void SX128xInterface<T>::startReceive()
|
|||||||
setStandby();
|
setStandby();
|
||||||
|
|
||||||
#if ARCH_PORTDUINO
|
#if ARCH_PORTDUINO
|
||||||
if (settingsMap[rxen] != RADIOLIB_NC) {
|
if (settingsMap[rxen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[rxen], HIGH);
|
digitalWrite(settingsMap[rxen_pin], HIGH);
|
||||||
}
|
}
|
||||||
if (settingsMap[txen] != RADIOLIB_NC) {
|
if (settingsMap[txen_pin] != RADIOLIB_NC) {
|
||||||
digitalWrite(settingsMap[txen], LOW);
|
digitalWrite(settingsMap[txen_pin], LOW);
|
||||||
}
|
}
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
@ -134,13 +134,13 @@ void portduinoSetup()
|
|||||||
{
|
{
|
||||||
printf("Set up Meshtastic on Portduino...\n");
|
printf("Set up Meshtastic on Portduino...\n");
|
||||||
int max_GPIO = 0;
|
int max_GPIO = 0;
|
||||||
const configNames GPIO_lines[] = {cs,
|
const configNames GPIO_lines[] = {cs_pin,
|
||||||
irq,
|
irq_pin,
|
||||||
busy,
|
busy_pin,
|
||||||
reset,
|
reset_pin,
|
||||||
sx126x_ant_sw,
|
sx126x_ant_sw_pin,
|
||||||
txen,
|
txen_pin,
|
||||||
rxen,
|
rxen_pin,
|
||||||
displayDC,
|
displayDC,
|
||||||
displayCS,
|
displayCS,
|
||||||
displayBacklight,
|
displayBacklight,
|
||||||
@ -247,7 +247,7 @@ void portduinoSetup()
|
|||||||
// Rather important to set this, if not running simulated.
|
// Rather important to set this, if not running simulated.
|
||||||
randomSeed(time(NULL));
|
randomSeed(time(NULL));
|
||||||
|
|
||||||
gpioChipName += std::to_string(settingsMap[gpiochip]);
|
std::string defaultGpioChipName = gpioChipName + std::to_string(settingsMap[default_gpiochip]);
|
||||||
|
|
||||||
for (configNames i : GPIO_lines) {
|
for (configNames i : GPIO_lines) {
|
||||||
if (settingsMap.count(i) && settingsMap[i] > max_GPIO)
|
if (settingsMap.count(i) && settingsMap[i] > max_GPIO)
|
||||||
@ -260,62 +260,46 @@ void portduinoSetup()
|
|||||||
// TODO: Can we do this in the for loop above?
|
// TODO: Can we do this in the for loop above?
|
||||||
// TODO: If one of these fails, we should log and terminate
|
// TODO: If one of these fails, we should log and terminate
|
||||||
if (settingsMap.count(user) > 0 && settingsMap[user] != RADIOLIB_NC) {
|
if (settingsMap.count(user) > 0 && settingsMap[user] != RADIOLIB_NC) {
|
||||||
if (initGPIOPin(settingsMap[user], gpioChipName) != ERRNO_OK) {
|
if (initGPIOPin(settingsMap[user], defaultGpioChipName, settingsMap[user]) != ERRNO_OK) {
|
||||||
settingsMap[user] = RADIOLIB_NC;
|
settingsMap[user] = RADIOLIB_NC;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (settingsMap[displayPanel] != no_screen) {
|
if (settingsMap[displayPanel] != no_screen) {
|
||||||
if (settingsMap[displayCS] > 0)
|
if (settingsMap[displayCS] > 0)
|
||||||
initGPIOPin(settingsMap[displayCS], gpioChipName);
|
initGPIOPin(settingsMap[displayCS], defaultGpioChipName, settingsMap[displayCS]);
|
||||||
if (settingsMap[displayDC] > 0)
|
if (settingsMap[displayDC] > 0)
|
||||||
initGPIOPin(settingsMap[displayDC], gpioChipName);
|
initGPIOPin(settingsMap[displayDC], defaultGpioChipName, settingsMap[displayDC]);
|
||||||
if (settingsMap[displayBacklight] > 0)
|
if (settingsMap[displayBacklight] > 0)
|
||||||
initGPIOPin(settingsMap[displayBacklight], gpioChipName);
|
initGPIOPin(settingsMap[displayBacklight], defaultGpioChipName, settingsMap[displayBacklight]);
|
||||||
if (settingsMap[displayReset] > 0)
|
if (settingsMap[displayReset] > 0)
|
||||||
initGPIOPin(settingsMap[displayReset], gpioChipName);
|
initGPIOPin(settingsMap[displayReset], defaultGpioChipName, settingsMap[displayReset]);
|
||||||
}
|
}
|
||||||
if (settingsMap[touchscreenModule] != no_touchscreen) {
|
if (settingsMap[touchscreenModule] != no_touchscreen) {
|
||||||
if (settingsMap[touchscreenCS] > 0)
|
if (settingsMap[touchscreenCS] > 0)
|
||||||
initGPIOPin(settingsMap[touchscreenCS], gpioChipName);
|
initGPIOPin(settingsMap[touchscreenCS], defaultGpioChipName, settingsMap[touchscreenCS]);
|
||||||
if (settingsMap[touchscreenIRQ] > 0)
|
if (settingsMap[touchscreenIRQ] > 0)
|
||||||
initGPIOPin(settingsMap[touchscreenIRQ], gpioChipName);
|
initGPIOPin(settingsMap[touchscreenIRQ], defaultGpioChipName, settingsMap[touchscreenIRQ]);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Only initialize the radio pins when dealing with real, kernel controlled SPI hardware
|
// Only initialize the radio pins when dealing with real, kernel controlled SPI hardware
|
||||||
if (settingsStrings[spidev] != "" && settingsStrings[spidev] != "ch341") {
|
if (settingsStrings[spidev] != "" && settingsStrings[spidev] != "ch341") {
|
||||||
if (settingsMap.count(cs) > 0 && settingsMap[cs] != RADIOLIB_NC) {
|
const struct { configNames pin; configNames gpiochip; configNames line; } pinMappings[] = {
|
||||||
if (initGPIOPin(settingsMap[cs], gpioChipName) != ERRNO_OK) {
|
{ cs_pin, cs_gpiochip, cs_line },
|
||||||
settingsMap[cs] = RADIOLIB_NC;
|
{ irq_pin, irq_gpiochip, irq_line },
|
||||||
}
|
{ busy_pin, busy_gpiochip, busy_line },
|
||||||
}
|
{ reset_pin, reset_gpiochip, reset_line },
|
||||||
if (settingsMap.count(irq) > 0 && settingsMap[irq] != RADIOLIB_NC) {
|
{ rxen_pin, rxen_gpiochip, rxen_line },
|
||||||
if (initGPIOPin(settingsMap[irq], gpioChipName) != ERRNO_OK) {
|
{ txen_pin, txen_gpiochip, txen_line },
|
||||||
settingsMap[irq] = RADIOLIB_NC;
|
{ sx126x_ant_sw_pin, sx126x_ant_sw_gpiochip, sx126x_ant_sw_line }
|
||||||
}
|
};
|
||||||
}
|
for (auto& pinMap : pinMappings) {
|
||||||
if (settingsMap.count(busy) > 0 && settingsMap[busy] != RADIOLIB_NC) {
|
auto setMapIter = settingsMap.find(pinMap.pin);
|
||||||
if (initGPIOPin(settingsMap[busy], gpioChipName) != ERRNO_OK) {
|
if (setMapIter != settingsMap.end() && setMapIter->second != RADIOLIB_NC) {
|
||||||
settingsMap[busy] = RADIOLIB_NC;
|
if (initGPIOPin(setMapIter->second, gpioChipName + std::to_string(settingsMap[pinMap.gpiochip]), settingsMap[pinMap.line] ) != ERRNO_OK) {
|
||||||
}
|
settingsMap[pinMap.pin] = RADIOLIB_NC;
|
||||||
}
|
settingsMap[pinMap.gpiochip] = RADIOLIB_NC;
|
||||||
if (settingsMap.count(reset) > 0 && settingsMap[reset] != RADIOLIB_NC) {
|
settingsMap[pinMap.line] = RADIOLIB_NC;
|
||||||
if (initGPIOPin(settingsMap[reset], gpioChipName) != ERRNO_OK) {
|
}
|
||||||
settingsMap[reset] = RADIOLIB_NC;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (settingsMap.count(sx126x_ant_sw) > 0 && settingsMap[sx126x_ant_sw] != RADIOLIB_NC) {
|
|
||||||
if (initGPIOPin(settingsMap[sx126x_ant_sw], gpioChipName) != ERRNO_OK) {
|
|
||||||
settingsMap[sx126x_ant_sw] = RADIOLIB_NC;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (settingsMap.count(rxen) > 0 && settingsMap[rxen] != RADIOLIB_NC) {
|
|
||||||
if (initGPIOPin(settingsMap[rxen], gpioChipName) != ERRNO_OK) {
|
|
||||||
settingsMap[rxen] = RADIOLIB_NC;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (settingsMap.count(txen) > 0 && settingsMap[txen] != RADIOLIB_NC) {
|
|
||||||
if (initGPIOPin(settingsMap[txen], gpioChipName) != ERRNO_OK) {
|
|
||||||
settingsMap[txen] = RADIOLIB_NC;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
SPI.begin(settingsStrings[spidev].c_str());
|
SPI.begin(settingsStrings[spidev].c_str());
|
||||||
@ -332,13 +316,13 @@ void portduinoSetup()
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int initGPIOPin(int pinNum, const std::string gpioChipName)
|
int initGPIOPin(int pinNum, const std::string gpioChipName, int line)
|
||||||
{
|
{
|
||||||
#ifdef PORTDUINO_LINUX_HARDWARE
|
#ifdef PORTDUINO_LINUX_HARDWARE
|
||||||
std::string gpio_name = "GPIO" + std::to_string(pinNum);
|
std::string gpio_name = "GPIO" + std::to_string(pinNum);
|
||||||
try {
|
try {
|
||||||
GPIOPin *csPin;
|
GPIOPin *csPin;
|
||||||
csPin = new LinuxGPIOPin(pinNum, gpioChipName.c_str(), pinNum, gpio_name.c_str());
|
csPin = new LinuxGPIOPin(pinNum, gpioChipName.c_str(), line, gpio_name.c_str());
|
||||||
csPin->setSilent();
|
csPin->setSilent();
|
||||||
gpioBind(csPin);
|
gpioBind(csPin);
|
||||||
return ERRNO_OK;
|
return ERRNO_OK;
|
||||||
@ -376,42 +360,65 @@ bool loadConfig(const char *configPath)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (yamlConfig["Lora"]) {
|
if (yamlConfig["Lora"]) {
|
||||||
settingsMap[use_sx1262] = false;
|
const struct { configNames cfgName; std::string strName; } loraModules[] = {
|
||||||
settingsMap[use_rf95] = false;
|
{ use_rf95, "RF95" },
|
||||||
settingsMap[use_sx1280] = false;
|
{ use_sx1262, "sx1262" },
|
||||||
settingsMap[use_lr1110] = false;
|
{ use_sx1268, "sx1268" },
|
||||||
settingsMap[use_lr1120] = false;
|
{ use_sx1280, "sx1280" },
|
||||||
settingsMap[use_lr1121] = false;
|
{ use_lr1110, "lr1110" },
|
||||||
settingsMap[use_sx1268] = false;
|
{ use_lr1120, "lr1120" },
|
||||||
|
{ use_lr1121, "lr1121" },
|
||||||
if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "sx1262") {
|
{ use_llcc68, "LLCC68" }
|
||||||
settingsMap[use_sx1262] = true;
|
};
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "RF95") {
|
for (auto& loraModule : loraModules) {
|
||||||
settingsMap[use_rf95] = true;
|
settingsMap[loraModule.cfgName] = false;
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "sx1280") {
|
|
||||||
settingsMap[use_sx1280] = true;
|
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "lr1110") {
|
|
||||||
settingsMap[use_lr1110] = true;
|
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "lr1120") {
|
|
||||||
settingsMap[use_lr1120] = true;
|
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "lr1121") {
|
|
||||||
settingsMap[use_lr1121] = true;
|
|
||||||
} else if (yamlConfig["Lora"]["Module"] && yamlConfig["Lora"]["Module"].as<std::string>("") == "sx1268") {
|
|
||||||
settingsMap[use_sx1268] = true;
|
|
||||||
}
|
}
|
||||||
|
if (yamlConfig["Lora"]["Module"]) {
|
||||||
|
for (auto& loraModule : loraModules) {
|
||||||
|
if (yamlConfig["Lora"]["Module"].as<std::string>("") == loraModule.strName) {
|
||||||
|
settingsMap[loraModule.cfgName] = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
settingsMap[dio2_as_rf_switch] = yamlConfig["Lora"]["DIO2_AS_RF_SWITCH"].as<bool>(false);
|
settingsMap[dio2_as_rf_switch] = yamlConfig["Lora"]["DIO2_AS_RF_SWITCH"].as<bool>(false);
|
||||||
settingsMap[dio3_tcxo_voltage] = yamlConfig["Lora"]["DIO3_TCXO_VOLTAGE"].as<float>(0) * 1000;
|
settingsMap[dio3_tcxo_voltage] = yamlConfig["Lora"]["DIO3_TCXO_VOLTAGE"].as<float>(0) * 1000;
|
||||||
if (settingsMap[dio3_tcxo_voltage] == 0 && yamlConfig["Lora"]["DIO3_TCXO_VOLTAGE"].as<bool>(false)) {
|
if (settingsMap[dio3_tcxo_voltage] == 0 && yamlConfig["Lora"]["DIO3_TCXO_VOLTAGE"].as<bool>(false)) {
|
||||||
settingsMap[dio3_tcxo_voltage] = 1800; // default millivolts for "true"
|
settingsMap[dio3_tcxo_voltage] = 1800; // default millivolts for "true"
|
||||||
}
|
}
|
||||||
settingsMap[cs] = yamlConfig["Lora"]["CS"].as<int>(RADIOLIB_NC);
|
|
||||||
settingsMap[irq] = yamlConfig["Lora"]["IRQ"].as<int>(RADIOLIB_NC);
|
// backwards API compatibility and to globally set gpiochip once
|
||||||
settingsMap[busy] = yamlConfig["Lora"]["Busy"].as<int>(RADIOLIB_NC);
|
int defaultGpioChip = settingsMap[default_gpiochip] = yamlConfig["Lora"]["gpiochip"].as<int>(0);
|
||||||
settingsMap[reset] = yamlConfig["Lora"]["Reset"].as<int>(RADIOLIB_NC);
|
|
||||||
settingsMap[txen] = yamlConfig["Lora"]["TXen"].as<int>(RADIOLIB_NC);
|
const struct { configNames pin;
|
||||||
settingsMap[rxen] = yamlConfig["Lora"]["RXen"].as<int>(RADIOLIB_NC);
|
configNames gpiochip;
|
||||||
settingsMap[sx126x_ant_sw] = yamlConfig["Lora"]["SX126X_ANT_SW"].as<int>(RADIOLIB_NC);
|
configNames line;
|
||||||
settingsMap[gpiochip] = yamlConfig["Lora"]["gpiochip"].as<int>(0);
|
std::string strName; } pinMappings[] = {
|
||||||
|
{ cs_pin, cs_gpiochip, cs_line, "CS" },
|
||||||
|
{ irq_pin, irq_gpiochip, irq_line, "IRQ" },
|
||||||
|
{ busy_pin, busy_gpiochip, busy_line, "Busy" },
|
||||||
|
{ reset_pin, reset_gpiochip, reset_line, "Reset" },
|
||||||
|
{ txen_pin, txen_gpiochip, txen_line, "TXen" },
|
||||||
|
{ rxen_pin, rxen_gpiochip, rxen_line, "RXen" },
|
||||||
|
{ sx126x_ant_sw_pin, sx126x_ant_sw_gpiochip, sx126x_ant_sw_line, "SX126X_ANT_SW" },
|
||||||
|
};
|
||||||
|
for (auto& pinMap : pinMappings) {
|
||||||
|
if (yamlConfig["Lora"][pinMap.strName].IsMap()
|
||||||
|
&& (yamlConfig["Lora"][pinMap.strName]["pin"]
|
||||||
|
|| yamlConfig["Lora"][pinMap.strName]["line"]
|
||||||
|
|| yamlConfig["Lora"][pinMap.strName]["gpiochip"])) {
|
||||||
|
settingsMap[pinMap.pin] = yamlConfig["Lora"][pinMap.strName]["pin"].as<int>(RADIOLIB_NC);
|
||||||
|
settingsMap[pinMap.line] = yamlConfig["Lora"][pinMap.strName]["line"].as<int>(settingsMap[pinMap.pin]);
|
||||||
|
settingsMap[pinMap.gpiochip] = yamlConfig["Lora"][pinMap.strName]["gpiochip"].as<int>(defaultGpioChip);
|
||||||
|
}
|
||||||
|
else { // backwards API compatibility
|
||||||
|
settingsMap[pinMap.pin] = yamlConfig["Lora"][pinMap.strName].as<int>(RADIOLIB_NC);
|
||||||
|
settingsMap[pinMap.line] = settingsMap[pinMap.pin];
|
||||||
|
settingsMap[pinMap.gpiochip] = defaultGpioChip;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
settingsMap[spiSpeed] = yamlConfig["Lora"]["spiSpeed"].as<int>(2000000);
|
settingsMap[spiSpeed] = yamlConfig["Lora"]["spiSpeed"].as<int>(2000000);
|
||||||
settingsStrings[lora_usb_serial_num] = yamlConfig["Lora"]["USB_Serialnum"].as<std::string>("");
|
settingsStrings[lora_usb_serial_num] = yamlConfig["Lora"]["USB_Serialnum"].as<std::string>("");
|
||||||
settingsMap[lora_usb_pid] = yamlConfig["Lora"]["USB_PID"].as<int>(0x5512);
|
settingsMap[lora_usb_pid] = yamlConfig["Lora"]["USB_PID"].as<int>(0x5512);
|
||||||
|
@ -5,27 +5,42 @@
|
|||||||
#include "platform/portduino/USBHal.h"
|
#include "platform/portduino/USBHal.h"
|
||||||
|
|
||||||
enum configNames {
|
enum configNames {
|
||||||
use_sx1262,
|
default_gpiochip,
|
||||||
cs,
|
cs_pin,
|
||||||
irq,
|
cs_line,
|
||||||
busy,
|
cs_gpiochip,
|
||||||
reset,
|
irq_pin,
|
||||||
sx126x_ant_sw,
|
irq_line,
|
||||||
txen,
|
irq_gpiochip,
|
||||||
rxen,
|
busy_pin,
|
||||||
|
busy_line,
|
||||||
|
busy_gpiochip,
|
||||||
|
reset_pin,
|
||||||
|
reset_line,
|
||||||
|
reset_gpiochip,
|
||||||
|
txen_pin,
|
||||||
|
txen_line,
|
||||||
|
txen_gpiochip,
|
||||||
|
rxen_pin,
|
||||||
|
rxen_line,
|
||||||
|
rxen_gpiochip,
|
||||||
|
sx126x_ant_sw_pin,
|
||||||
|
sx126x_ant_sw_line,
|
||||||
|
sx126x_ant_sw_gpiochip,
|
||||||
dio2_as_rf_switch,
|
dio2_as_rf_switch,
|
||||||
dio3_tcxo_voltage,
|
dio3_tcxo_voltage,
|
||||||
use_rf95,
|
use_rf95,
|
||||||
|
use_sx1262,
|
||||||
|
use_sx1268,
|
||||||
use_sx1280,
|
use_sx1280,
|
||||||
use_lr1110,
|
use_lr1110,
|
||||||
use_lr1120,
|
use_lr1120,
|
||||||
use_lr1121,
|
use_lr1121,
|
||||||
use_sx1268,
|
use_llcc68,
|
||||||
lora_usb_serial_num,
|
lora_usb_serial_num,
|
||||||
lora_usb_pid,
|
lora_usb_pid,
|
||||||
lora_usb_vid,
|
lora_usb_vid,
|
||||||
user,
|
user,
|
||||||
gpiochip,
|
|
||||||
spidev,
|
spidev,
|
||||||
spiSpeed,
|
spiSpeed,
|
||||||
i2cdev,
|
i2cdev,
|
||||||
@ -75,7 +90,7 @@ extern std::map<configNames, int> settingsMap;
|
|||||||
extern std::map<configNames, std::string> settingsStrings;
|
extern std::map<configNames, std::string> settingsStrings;
|
||||||
extern std::ofstream traceFile;
|
extern std::ofstream traceFile;
|
||||||
extern Ch341Hal *ch341Hal;
|
extern Ch341Hal *ch341Hal;
|
||||||
int initGPIOPin(int pinNum, std::string gpioChipname);
|
int initGPIOPin(int pinNum, std::string gpioChipname, int line);
|
||||||
bool loadConfig(const char *configPath);
|
bool loadConfig(const char *configPath);
|
||||||
static bool ends_with(std::string_view str, std::string_view suffix);
|
static bool ends_with(std::string_view str, std::string_view suffix);
|
||||||
void getMacAddr(uint8_t *dmac);
|
void getMacAddr(uint8_t *dmac);
|
||||||
|
Loading…
Reference in New Issue
Block a user