Compare commits
12 Commits
34b8a3c214
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| 4f10ee8329 | |||
| 17a99ddd54 | |||
| eb827f5a60 | |||
| bc60028852 | |||
| 0ef379595f | |||
| 185d15cbaf | |||
| b728ca3c75 | |||
| c15afa9819 | |||
| 192a008150 | |||
| c827989f43 | |||
| 6115cd6b84 | |||
|
|
c84006da8a |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -16,3 +16,4 @@ Console/build
|
|||||||
build/*
|
build/*
|
||||||
.pio/*
|
.pio/*
|
||||||
.vscode/*
|
.vscode/*
|
||||||
|
Release/*.bin
|
||||||
|
|||||||
77
Boards.h
77
Boards.h
@@ -122,6 +122,8 @@
|
|||||||
#define MODEL_FE 0xFE // Homebrew board, max 17dBm output power
|
#define MODEL_FE 0xFE // Homebrew board, max 17dBm output power
|
||||||
#define MODEL_FF 0xFF // Homebrew board, max 14dBm output power
|
#define MODEL_FF 0xFF // Homebrew board, max 14dBm output power
|
||||||
|
|
||||||
|
#define BOARD_MESHADVENTURER_S3 0xF2
|
||||||
|
|
||||||
#if defined(__AVR_ATmega1284P__)
|
#if defined(__AVR_ATmega1284P__)
|
||||||
#define PLATFORM PLATFORM_AVR
|
#define PLATFORM PLATFORM_AVR
|
||||||
#define MCU_VARIANT MCU_1284P
|
#define MCU_VARIANT MCU_1284P
|
||||||
@@ -149,6 +151,10 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#define LORA_PA_UNKNOWN 0x00
|
||||||
|
#define LORA_PA_GC1109 0x01
|
||||||
|
#define LORA_PA_KCT8103L 0x02
|
||||||
|
|
||||||
#define HAS_DISPLAY false
|
#define HAS_DISPLAY false
|
||||||
#define HAS_BLUETOOTH false
|
#define HAS_BLUETOOTH false
|
||||||
#define HAS_BLE false
|
#define HAS_BLE false
|
||||||
@@ -361,7 +367,7 @@
|
|||||||
#define HAS_SLEEP true
|
#define HAS_SLEEP true
|
||||||
#define PIN_WAKEUP GPIO_NUM_0
|
#define PIN_WAKEUP GPIO_NUM_0
|
||||||
#define WAKEUP_LEVEL 0
|
#define WAKEUP_LEVEL 0
|
||||||
#define OCP_TUNED 0x18
|
#define OCP_TUNED 0x28
|
||||||
|
|
||||||
const int pin_btn_usr1 = 0;
|
const int pin_btn_usr1 = 0;
|
||||||
|
|
||||||
@@ -409,8 +415,9 @@
|
|||||||
#define HAS_LORA_LNA true
|
#define HAS_LORA_LNA true
|
||||||
#define PIN_WAKEUP GPIO_NUM_0
|
#define PIN_WAKEUP GPIO_NUM_0
|
||||||
#define WAKEUP_LEVEL 0
|
#define WAKEUP_LEVEL 0
|
||||||
#define OCP_TUNED 0x18
|
#define OCP_TUNED 0x28
|
||||||
#define Vext GPIO_NUM_36
|
#define Vext GPIO_NUM_36
|
||||||
|
#define LORA_PA_MODEL LORA_PA_UNKNOWN;
|
||||||
|
|
||||||
const int pin_btn_usr1 = 0;
|
const int pin_btn_usr1 = 0;
|
||||||
|
|
||||||
@@ -432,14 +439,17 @@
|
|||||||
|
|
||||||
#define LORA_LNA_GAIN 17
|
#define LORA_LNA_GAIN 17
|
||||||
#define LORA_LNA_GVT 12
|
#define LORA_LNA_GVT 12
|
||||||
#define LORA_PA_GC1109 true
|
|
||||||
#define LORA_PA_PWR_EN 7
|
#define LORA_PA_PWR_EN 7
|
||||||
#define LORA_PA_CSD 2
|
#define LORA_PA_CSD 2 // Same pin on GC1109
|
||||||
#define LORA_PA_CPS 46
|
#define LORA_PA_CPS 46 // Same pin on GC1109
|
||||||
|
#define LORA_PA_CTX 5 // Only used on KCT8103
|
||||||
|
|
||||||
#define PA_MAX_OUTPUT 28
|
#define PA_MAX_OUTPUT 28
|
||||||
#define PA_GAIN_POINTS 22
|
#define PA_GAIN_POINTS 22
|
||||||
#define PA_GAIN_VALUES 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 10, 10, 9, 9, 8, 7
|
|
||||||
|
#define LORA_LNA_KCT8103L_GAIN 21
|
||||||
|
const int PA_GC1109_VALUES[PA_GAIN_POINTS] = {11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 10, 10, 9, 9, 8, 7};
|
||||||
|
const int PA_KCT8103L_VALUES[PA_GAIN_POINTS] = {13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 12, 12, 11, 11, 10, 9, 8, 7};
|
||||||
|
|
||||||
const int pin_cs = 8;
|
const int pin_cs = 8;
|
||||||
const int pin_busy = 13;
|
const int pin_busy = 13;
|
||||||
@@ -449,6 +459,50 @@
|
|||||||
const int pin_miso = 11;
|
const int pin_miso = 11;
|
||||||
const int pin_sclk = 9;
|
const int pin_sclk = 9;
|
||||||
|
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
#define IS_ESP32S3 true
|
||||||
|
#define HAS_DISPLAY true
|
||||||
|
#define HAS_NP true
|
||||||
|
#define HAS_BLUETOOTH false
|
||||||
|
#define HAS_BLE true
|
||||||
|
#define HAS_WIFI true
|
||||||
|
#define HAS_CONSOLE true
|
||||||
|
#define HAS_EEPROM true
|
||||||
|
#define HAS_BUSY true
|
||||||
|
#define HAS_INPUT true
|
||||||
|
#define HAS_TCXO true
|
||||||
|
#define MODEM SX1262
|
||||||
|
#define DIO2_AS_RF_SWITCH false
|
||||||
|
#define HAS_RF_SWITCH_RX_TX true
|
||||||
|
#define HAS_LORA_LNA true
|
||||||
|
#define LORA_LNA_GAIN 30
|
||||||
|
#define LORA_LNA_GVT 14
|
||||||
|
#define PA_MAX_OUTPUT 22
|
||||||
|
|
||||||
|
const int pin_cs = 39;
|
||||||
|
const int pin_sclk = 38;
|
||||||
|
const int pin_miso = 40;
|
||||||
|
const int pin_mosi = 18;
|
||||||
|
const int pin_busy = 7;
|
||||||
|
const int pin_reset = 43;
|
||||||
|
const int pin_dio = 15;
|
||||||
|
const int pin_txen = 9;
|
||||||
|
const int pin_rxen = 8;
|
||||||
|
const int pin_tcxo_enable = -1;
|
||||||
|
|
||||||
|
const int pin_btn_usr1 = 4;
|
||||||
|
const int pin_np = 48;
|
||||||
|
|
||||||
|
#if HAS_NP == false
|
||||||
|
#if defined(EXTERNAL_LEDS)
|
||||||
|
const int pin_led_rx = 48;
|
||||||
|
const int pin_led_tx = 48;
|
||||||
|
#else
|
||||||
|
const int pin_led_rx = 48;
|
||||||
|
const int pin_led_tx = 48;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
#elif BOARD_MODEL == BOARD_RNODE_NG_20
|
#elif BOARD_MODEL == BOARD_RNODE_NG_20
|
||||||
#define HAS_DISPLAY true
|
#define HAS_DISPLAY true
|
||||||
#define HAS_BLUETOOTH true
|
#define HAS_BLUETOOTH true
|
||||||
@@ -483,13 +537,10 @@
|
|||||||
const int pin_np = 12;
|
const int pin_np = 12;
|
||||||
const int pin_dac = 25;
|
const int pin_dac = 25;
|
||||||
const int pin_adc = 34;
|
const int pin_adc = 34;
|
||||||
// CBA already defined by framework
|
const int SD_MISO = 2;
|
||||||
//const int SD_MISO = 2;
|
const int SD_MOSI = 15;
|
||||||
// CBA already defined by framework
|
|
||||||
//const int SD_MOSI = 15;
|
|
||||||
const int SD_CLK = 14;
|
const int SD_CLK = 14;
|
||||||
// CBA already defined by framework
|
const int SD_CS = 13;
|
||||||
//const int SD_CS = 13;
|
|
||||||
#if HAS_NP == false
|
#if HAS_NP == false
|
||||||
#if defined(EXTERNAL_LEDS)
|
#if defined(EXTERNAL_LEDS)
|
||||||
const int pin_led_rx = 12;
|
const int pin_led_rx = 12;
|
||||||
@@ -934,7 +985,7 @@
|
|||||||
// Default OCP value if not specified
|
// Default OCP value if not specified
|
||||||
// in board configuration
|
// in board configuration
|
||||||
#ifndef OCP_TUNED
|
#ifndef OCP_TUNED
|
||||||
#define OCP_TUNED 0x18
|
#define OCP_TUNED 0x28
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef PA_MAX_OUTPUT
|
#ifndef PA_MAX_OUTPUT
|
||||||
|
|||||||
@@ -105,10 +105,10 @@ static void config_send_html() {
|
|||||||
if (cur_txp == 0xFF) cur_txp = PA_MAX_OUTPUT; // Default to board max
|
if (cur_txp == 0xFF) cur_txp = PA_MAX_OUTPUT; // Default to board max
|
||||||
|
|
||||||
// Default frequency if not set
|
// Default frequency if not set
|
||||||
if (cur_freq == 0) cur_freq = 914875000; // 914.875 MHz default
|
if (cur_freq == 0) cur_freq = 868825000; // 914.875 MHz default
|
||||||
if (cur_bw == 0) cur_bw = 125000; // 125 kHz default
|
if (cur_bw == 0) cur_bw = 125000; // 125 kHz default
|
||||||
if (cur_sf == 0) cur_sf = 10; // SF10 default
|
if (cur_sf == 0) cur_sf = 10; // SF10 default
|
||||||
if (cur_cr < 5 || cur_cr > 8) cur_cr = 5; // CR 4/5 default
|
if (cur_cr < 5 || cur_cr > 8) cur_cr = 7; // CR 4/5 default
|
||||||
|
|
||||||
// Build the HTML page
|
// Build the HTML page
|
||||||
String html = F(
|
String html = F(
|
||||||
|
|||||||
9
Config.h
9
Config.h
@@ -20,7 +20,7 @@
|
|||||||
#define CONFIG_H
|
#define CONFIG_H
|
||||||
|
|
||||||
#define MAJ_VERS 0x01
|
#define MAJ_VERS 0x01
|
||||||
#define MIN_VERS 0x55
|
#define MIN_VERS 0x56
|
||||||
|
|
||||||
#define MODE_HOST 0x11
|
#define MODE_HOST 0x11
|
||||||
#define MODE_TNC 0x12
|
#define MODE_TNC 0x12
|
||||||
@@ -114,7 +114,14 @@
|
|||||||
#define CSMA_CW_PER_BAND_WINDOWS 15
|
#define CSMA_CW_PER_BAND_WINDOWS 15
|
||||||
#define CSMA_BAND_1_MAX_AIRTIME 7
|
#define CSMA_BAND_1_MAX_AIRTIME 7
|
||||||
#define CSMA_BAND_N_MIN_AIRTIME 85
|
#define CSMA_BAND_N_MIN_AIRTIME 85
|
||||||
|
|
||||||
|
// Increase threshold for specific boards
|
||||||
|
#if BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
#define CSMA_INFR_THRESHOLD_DB 14
|
||||||
|
#else
|
||||||
#define CSMA_INFR_THRESHOLD_DB 11
|
#define CSMA_INFR_THRESHOLD_DB 11
|
||||||
|
#endif
|
||||||
|
|
||||||
#define CSMA_RFENV_RECAL_MS 2500
|
#define CSMA_RFENV_RECAL_MS 2500
|
||||||
#define CSMA_RFENV_RECAL_LIMIT_DB -83
|
#define CSMA_RFENV_RECAL_LIMIT_DB -83
|
||||||
bool interference_detected = false;
|
bool interference_detected = false;
|
||||||
|
|||||||
10
Display.h
10
Display.h
@@ -97,6 +97,11 @@ extern BoundaryState boundary_state;
|
|||||||
#define DISP_ADDR 0x3C
|
#define DISP_ADDR 0x3C
|
||||||
#define SCL_OLED 18
|
#define SCL_OLED 18
|
||||||
#define SDA_OLED 17
|
#define SDA_OLED 17
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
#define DISP_RST -1
|
||||||
|
#define DISP_ADDR 0x3C
|
||||||
|
#define SCL_OLED 0
|
||||||
|
#define SDA_OLED 42
|
||||||
#elif BOARD_MODEL == BOARD_RAK4631
|
#elif BOARD_MODEL == BOARD_RAK4631
|
||||||
// RAK1921/SSD1306
|
// RAK1921/SSD1306
|
||||||
#define DISP_RST -1
|
#define DISP_RST -1
|
||||||
@@ -334,6 +339,8 @@ bool display_init() {
|
|||||||
digitalWrite(pin_display_en, HIGH);
|
digitalWrite(pin_display_en, HIGH);
|
||||||
delay(50);
|
delay(50);
|
||||||
Wire.begin(SDA_OLED, SCL_OLED);
|
Wire.begin(SDA_OLED, SCL_OLED);
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
Wire.begin(SDA_OLED, SCL_OLED);
|
||||||
#elif BOARD_MODEL == BOARD_LORA32_V1_0
|
#elif BOARD_MODEL == BOARD_LORA32_V1_0
|
||||||
int pin_display_en = 16;
|
int pin_display_en = 16;
|
||||||
digitalWrite(pin_display_en, LOW);
|
digitalWrite(pin_display_en, LOW);
|
||||||
@@ -455,6 +462,9 @@ bool display_init() {
|
|||||||
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
disp_mode = DISP_MODE_PORTRAIT;
|
disp_mode = DISP_MODE_PORTRAIT;
|
||||||
display.setRotation(1);
|
display.setRotation(1);
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
disp_mode = DISP_MODE_LANDSCAPE;
|
||||||
|
display.setRotation(0);
|
||||||
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
||||||
disp_mode = DISP_MODE_PORTRAIT;
|
disp_mode = DISP_MODE_PORTRAIT;
|
||||||
display.setRotation(1);
|
display.setRotation(1);
|
||||||
|
|||||||
17
Power.h
17
Power.h
@@ -147,6 +147,23 @@ float pmu_temperature = PMU_TEMP_MIN-1;
|
|||||||
bool bat_voltage_dropping = false;
|
bool bat_voltage_dropping = false;
|
||||||
float bat_delay_v = 0;
|
float bat_delay_v = 0;
|
||||||
float bat_state_change_v = 0;
|
float bat_state_change_v = 0;
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
#define BAT_V_MIN 3.05
|
||||||
|
#define BAT_V_MAX 4.0
|
||||||
|
#define BAT_V_CHG 4.48
|
||||||
|
#define BAT_V_FLOAT 4.33
|
||||||
|
#define BAT_SAMPLES 7
|
||||||
|
const uint8_t pin_vbat = 1;
|
||||||
|
const uint8_t pin_ctrl = 37;
|
||||||
|
float bat_p_samples[BAT_SAMPLES];
|
||||||
|
float bat_v_samples[BAT_SAMPLES];
|
||||||
|
uint8_t bat_samples_count = 0;
|
||||||
|
int bat_discharging_samples = 0;
|
||||||
|
int bat_charging_samples = 0;
|
||||||
|
int bat_charged_samples = 0;
|
||||||
|
bool bat_voltage_dropping = false;
|
||||||
|
float bat_delay_v = 0;
|
||||||
|
float bat_state_change_v = 0;
|
||||||
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
||||||
#define BAT_V_MIN 3.15
|
#define BAT_V_MIN 3.15
|
||||||
#define BAT_V_MAX 4.165
|
#define BAT_V_MAX 4.165
|
||||||
|
|||||||
@@ -363,7 +363,7 @@ void setup() {
|
|||||||
boot_seq();
|
boot_seq();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if BOARD_MODEL != BOARD_RAK4631 && BOARD_MODEL != BOARD_HELTEC_T114 && BOARD_MODEL != BOARD_TECHO && BOARD_MODEL != BOARD_T3S3 && BOARD_MODEL != BOARD_TBEAM_S_V1 && BOARD_MODEL != BOARD_HELTEC32_V4 && BOARD_MODEL != BOARD_HELTEC32_V3
|
#if BOARD_MODEL != BOARD_RAK4631 && BOARD_MODEL != BOARD_HELTEC_T114 && BOARD_MODEL != BOARD_TECHO && BOARD_MODEL != BOARD_T3S3 && BOARD_MODEL != BOARD_TBEAM_S_V1 && BOARD_MODEL != BOARD_HELTEC32_V4 && BOARD_MODEL != BOARD_HELTEC32_V3 && BOARD_MODEL != BOARD_MESHADVENTURER_S3
|
||||||
// Some boards need to wait until the hardware UART is set up before booting
|
// Some boards need to wait until the hardware UART is set up before booting
|
||||||
// the full firmware. In the case of the RAK4631, Heltec T114, and Heltec V3,
|
// the full firmware. In the case of the RAK4631, Heltec T114, and Heltec V3,
|
||||||
// the line below will wait until a serial connection is actually established
|
// the line below will wait until a serial connection is actually established
|
||||||
@@ -411,7 +411,7 @@ void setup() {
|
|||||||
#if MODEM == SX1276 || MODEM == SX1278
|
#if MODEM == SX1276 || MODEM == SX1278
|
||||||
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy);
|
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy);
|
||||||
#elif MODEM == SX1262
|
#elif MODEM == SX1262
|
||||||
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy, pin_rxen);
|
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy, pin_rxen, pin_txen);
|
||||||
#elif MODEM == SX1280
|
#elif MODEM == SX1280
|
||||||
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy, pin_rxen, pin_txen);
|
LoRa->setPins(pin_cs, pin_reset, pin_dio, pin_busy, pin_rxen, pin_txen);
|
||||||
#endif
|
#endif
|
||||||
@@ -1586,7 +1586,7 @@ void serial_callback(uint8_t sbyte) {
|
|||||||
if (txp > 13) txp = 13;
|
if (txp > 13) txp = 13;
|
||||||
#endif
|
#endif
|
||||||
#else
|
#else
|
||||||
if (txp > 17) txp = 17;
|
if (txp > 20) txp = 20;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
lora_txp = txp;
|
lora_txp = txp;
|
||||||
@@ -2648,7 +2648,13 @@ void sleep_now() {
|
|||||||
#if BOARD_MODEL == BOARD_HELTEC32_V4
|
#if BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
headless_led_off();
|
headless_led_off();
|
||||||
headless_led_detach_pwm();
|
headless_led_detach_pwm();
|
||||||
|
#if LORA_PA_AUTO_DETECT
|
||||||
|
if (sx126x_modem.isKCT8103L()) {
|
||||||
|
digitalWrite(LORA_PA_CTX, LOW);
|
||||||
|
} else {
|
||||||
digitalWrite(LORA_PA_CPS, LOW);
|
digitalWrite(LORA_PA_CPS, LOW);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
digitalWrite(LORA_PA_CSD, LOW);
|
digitalWrite(LORA_PA_CSD, LOW);
|
||||||
digitalWrite(LORA_PA_PWR_EN, LOW);
|
digitalWrite(LORA_PA_PWR_EN, LOW);
|
||||||
digitalWrite(Vext, HIGH);
|
digitalWrite(Vext, HIGH);
|
||||||
|
|||||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
33
Utilities.h
33
Utilities.h
@@ -324,6 +324,13 @@ extern RNS::Reticulum reticulum;
|
|||||||
void led_tx_off() { digitalWrite(pin_led_tx, LOW); }
|
void led_tx_off() { digitalWrite(pin_led_tx, LOW); }
|
||||||
void led_id_on() { }
|
void led_id_on() { }
|
||||||
void led_id_off() { }
|
void led_id_off() { }
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
void led_rx_on() { digitalWrite(pin_led_rx, HIGH); }
|
||||||
|
void led_rx_off() { digitalWrite(pin_led_rx, LOW); }
|
||||||
|
void led_tx_on() { digitalWrite(pin_led_tx, HIGH); }
|
||||||
|
void led_tx_off() { digitalWrite(pin_led_tx, LOW); }
|
||||||
|
void led_id_on() { }
|
||||||
|
void led_id_off() { }
|
||||||
#elif BOARD_MODEL == BOARD_LORA32_V2_1
|
#elif BOARD_MODEL == BOARD_LORA32_V2_1
|
||||||
void led_rx_on() { digitalWrite(pin_led_rx, HIGH); }
|
void led_rx_on() { digitalWrite(pin_led_rx, HIGH); }
|
||||||
void led_rx_off() { digitalWrite(pin_led_rx, LOW); }
|
void led_rx_off() { digitalWrite(pin_led_rx, LOW); }
|
||||||
@@ -388,7 +395,7 @@ extern RNS::Reticulum reticulum;
|
|||||||
|
|
||||||
// ── Headless LED indicators (for Heltec V4 without OLED) ─────────────────
|
// ── Headless LED indicators (for Heltec V4 without OLED) ─────────────────
|
||||||
// Uses LEDC PWM for smooth ramp effects on pin_led_tx (GPIO 35)
|
// Uses LEDC PWM for smooth ramp effects on pin_led_tx (GPIO 35)
|
||||||
#if BOARD_MODEL == BOARD_HELTEC32_V4 || BOARD_MODEL == BOARD_HELTEC32_V3
|
#if BOARD_MODEL == BOARD_HELTEC32_V4 || BOARD_MODEL == BOARD_HELTEC32_V3 || BOARD_MODEL == MESHADVENTURER_S3
|
||||||
#define HEADLESS_LED_CHANNEL 0
|
#define HEADLESS_LED_CHANNEL 0
|
||||||
bool headless_led_pwm_attached = false;
|
bool headless_led_pwm_attached = false;
|
||||||
|
|
||||||
@@ -1376,11 +1383,33 @@ int getTxPower() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#if HAS_LORA_PA
|
#if HAS_LORA_PA
|
||||||
|
#if BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
|
bool pa_values_determined = false;
|
||||||
|
int tx_gain[PA_GAIN_POINTS] = {100};
|
||||||
|
#else
|
||||||
|
bool pa_values_determined = true;
|
||||||
const int tx_gain[PA_GAIN_POINTS] = {PA_GAIN_VALUES};
|
const int tx_gain[PA_GAIN_POINTS] = {PA_GAIN_VALUES};
|
||||||
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
extern uint8_t lora_pa_model;
|
||||||
|
void determine_pa_values() {
|
||||||
|
#if BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
|
if (lora_pa_model == LORA_PA_GC1109) {
|
||||||
|
for (int i=0; i < PA_GAIN_POINTS; i++) { tx_gain[i] = PA_GC1109_VALUES[i]; }
|
||||||
|
pa_values_determined = true;
|
||||||
|
for (int i=0; i < PA_GAIN_POINTS; i++) { Serial.print(" "); Serial.printf("%d", tx_gain[i]); }
|
||||||
|
} else if (lora_pa_model == LORA_PA_KCT8103L) {
|
||||||
|
for (int i=0; i < PA_GAIN_POINTS; i++) { tx_gain[i] = PA_KCT8103L_VALUES[i]; }
|
||||||
|
pa_values_determined = true;
|
||||||
|
for (int i=0; i < PA_GAIN_POINTS; i++) { Serial.print(" "); Serial.printf("%d", tx_gain[i]); }
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
int map_target_power_to_modem_output(int target_tx_power) {
|
int map_target_power_to_modem_output(int target_tx_power) {
|
||||||
#if HAS_LORA_PA
|
#if HAS_LORA_PA
|
||||||
|
if (!pa_values_determined) { determine_pa_values(); }
|
||||||
int modem_output_dbm = -9;
|
int modem_output_dbm = -9;
|
||||||
for (int i = 0; i < PA_GAIN_POINTS; i++) {
|
for (int i = 0; i < PA_GAIN_POINTS; i++) {
|
||||||
int gain = tx_gain[i];
|
int gain = tx_gain[i];
|
||||||
@@ -1773,6 +1802,8 @@ bool eeprom_model_valid() {
|
|||||||
if (model == MODEL_C5 || model == MODEL_CA) {
|
if (model == MODEL_C5 || model == MODEL_CA) {
|
||||||
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
if (model == MODEL_C8) {
|
if (model == MODEL_C8) {
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
if (model == MODEL_C8) {
|
||||||
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
#elif BOARD_MODEL == BOARD_HELTEC_T114
|
||||||
if (model == MODEL_C6 || model == MODEL_C7) {
|
if (model == MODEL_C6 || model == MODEL_C7) {
|
||||||
#elif BOARD_MODEL == BOARD_RAK4631
|
#elif BOARD_MODEL == BOARD_RAK4631
|
||||||
|
|||||||
@@ -121,6 +121,8 @@ def device_provision(env):
|
|||||||
env.Execute("rnodeconf --product b1 --model b9 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
env.Execute("rnodeconf --product b1 --model b9 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
||||||
elif variant in ("heltec32v4", "heltec32v4_local", "heltec32v4_boundary", "heltec32v4_boundary_local"):
|
elif variant in ("heltec32v4", "heltec32v4_local", "heltec32v4_boundary", "heltec32v4_boundary_local"):
|
||||||
env.Execute("rnodeconf --product b1 --model b9 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
env.Execute("rnodeconf --product b1 --model b9 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
||||||
|
elif variant in ("meshadventurer_s3_boundary"):
|
||||||
|
env.Execute("rnodeconf --product f0 --model fe --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
||||||
elif variant in ("rak4631", "rak4631_local"):
|
elif variant in ("rak4631", "rak4631_local"):
|
||||||
env.Execute("rnodeconf --product 10 --model 12 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
env.Execute("rnodeconf --product 10 --model 12 --hwrev 1 --rom " + env.subst("$UPLOAD_PORT"))
|
||||||
elif variant in ("heltec_t114", "heltec_t114_local"):
|
elif variant in ("heltec_t114", "heltec_t114_local"):
|
||||||
|
|||||||
216
flash.py
216
flash.py
@@ -7,19 +7,12 @@ No PlatformIO required — just Python 3 and a USB cable.
|
|||||||
|
|
||||||
By default, downloads the latest firmware from GitHub Releases (if newer than
|
By default, downloads the latest firmware from GitHub Releases (if newer than
|
||||||
the local cache) and flashes the app partition only, preserving bootloader,
|
the local cache) and flashes the app partition only, preserving bootloader,
|
||||||
partition table, NVS, and EEPROM settings. For reproducible flashing, the
|
partition table, NVS, and EEPROM settings.
|
||||||
script prefers the bundled esptool in Release/ over any host-installed copy.
|
|
||||||
|
|
||||||
Usage:
|
Usage:
|
||||||
# Update firmware — V4 (default)
|
# Update firmware — V4 (default)
|
||||||
python flash.py
|
python flash.py
|
||||||
|
|
||||||
# Legacy alias for an app-only update flow
|
|
||||||
python flash.py --update
|
|
||||||
|
|
||||||
# Use a host-installed esptool instead of the bundled copy
|
|
||||||
python flash.py --use-system-esptool
|
|
||||||
|
|
||||||
# Update firmware — V3
|
# Update firmware — V3
|
||||||
python flash.py --board v3
|
python flash.py --board v3
|
||||||
|
|
||||||
@@ -62,7 +55,6 @@ GITHUB_REPO = "jrl290/RTNode-HeltecV4"
|
|||||||
|
|
||||||
# Runtime state (set automatically during main())
|
# Runtime state (set automatically during main())
|
||||||
_flash_mode_override = None # CLI --flash-mode sets this; otherwise board profile wins
|
_flash_mode_override = None # CLI --flash-mode sets this; otherwise board profile wins
|
||||||
_esptool_write_verify_support = {}
|
|
||||||
|
|
||||||
# Flash addresses for ESP32-S3 Arduino framework
|
# Flash addresses for ESP32-S3 Arduino framework
|
||||||
BOOTLOADER_ADDR = 0x0000
|
BOOTLOADER_ADDR = 0x0000
|
||||||
@@ -324,13 +316,25 @@ def detect_board(port, esptool_cmd):
|
|||||||
|
|
||||||
# ── Helpers ────────────────────────────────────────────────────────────────────
|
# ── Helpers ────────────────────────────────────────────────────────────────────
|
||||||
|
|
||||||
def find_esptool(prefer_system=False):
|
def find_esptool():
|
||||||
"""Find esptool, preferring repo-managed copies for reproducible flashing.
|
"""Find esptool — pip-installed, user-local, bundled, or PlatformIO's copy.
|
||||||
|
|
||||||
Default order is bundled Release/ copy, then PlatformIO's packaged copy,
|
Prefer pip/pipx-installed esptool first (handles its own deps and is
|
||||||
then any host-installed esptool. Pass ``prefer_system=True`` to invert that
|
usually the newest version), then fall back to the bundled script.
|
||||||
preference when a user explicitly wants their machine-wide installation.
|
|
||||||
"""
|
"""
|
||||||
|
# 1. pip-installed esptool on PATH
|
||||||
|
if shutil.which("esptool"):
|
||||||
|
return ["esptool"]
|
||||||
|
|
||||||
|
# 2. Common user-local install locations (pip install --user)
|
||||||
|
for candidate in [
|
||||||
|
os.path.expanduser("~/.local/bin/esptool"),
|
||||||
|
os.path.expanduser("~/.local/bin/esptool.py"),
|
||||||
|
]:
|
||||||
|
if os.path.isfile(candidate) and os.access(candidate, os.X_OK):
|
||||||
|
print(f" Found user-local esptool: {candidate}")
|
||||||
|
return [candidate]
|
||||||
|
|
||||||
# Check if pyserial is available before using script-based esptool
|
# Check if pyserial is available before using script-based esptool
|
||||||
try:
|
try:
|
||||||
import serial # noqa: F401
|
import serial # noqa: F401
|
||||||
@@ -338,36 +342,20 @@ def find_esptool(prefer_system=False):
|
|||||||
except ImportError:
|
except ImportError:
|
||||||
has_pyserial = False
|
has_pyserial = False
|
||||||
|
|
||||||
|
# 2. Bundled in Release/
|
||||||
bundled = os.path.join(os.path.dirname(__file__), "Release", "esptool", "esptool.py")
|
bundled = os.path.join(os.path.dirname(__file__), "Release", "esptool", "esptool.py")
|
||||||
|
if os.path.isfile(bundled) and has_pyserial:
|
||||||
|
return [sys.executable, bundled]
|
||||||
|
|
||||||
|
# 3. PlatformIO's esptool
|
||||||
pio_esptool = os.path.expanduser(
|
pio_esptool = os.path.expanduser(
|
||||||
"~/.platformio/packages/tool-esptoolpy/esptool.py"
|
"~/.platformio/packages/tool-esptoolpy/esptool.py"
|
||||||
)
|
)
|
||||||
|
if os.path.isfile(pio_esptool) and has_pyserial:
|
||||||
|
return [sys.executable, pio_esptool]
|
||||||
|
|
||||||
repo_candidates = []
|
# 4. Bundled exists but pyserial is missing — tell the user
|
||||||
if has_pyserial:
|
if os.path.isfile(bundled) and not has_pyserial:
|
||||||
if os.path.isfile(bundled):
|
|
||||||
repo_candidates.append(([sys.executable, bundled], f"bundled esptool: {bundled}"))
|
|
||||||
if os.path.isfile(pio_esptool):
|
|
||||||
repo_candidates.append(([sys.executable, pio_esptool], f"PlatformIO esptool: {pio_esptool}"))
|
|
||||||
|
|
||||||
system_candidates = []
|
|
||||||
if shutil.which("esptool.py"):
|
|
||||||
system_candidates.append((["esptool.py"], "system esptool.py from PATH"))
|
|
||||||
if shutil.which("esptool"):
|
|
||||||
system_candidates.append((["esptool"], "system esptool from PATH"))
|
|
||||||
for candidate in [
|
|
||||||
os.path.expanduser("~/.local/bin/esptool"),
|
|
||||||
os.path.expanduser("~/.local/bin/esptool.py"),
|
|
||||||
]:
|
|
||||||
if os.path.isfile(candidate) and os.access(candidate, os.X_OK):
|
|
||||||
system_candidates.append(([candidate], f"user-local esptool: {candidate}"))
|
|
||||||
|
|
||||||
search_order = system_candidates + repo_candidates if prefer_system else repo_candidates + system_candidates
|
|
||||||
for command, source in search_order:
|
|
||||||
print(f" Found {source}")
|
|
||||||
return command
|
|
||||||
|
|
||||||
if (os.path.isfile(bundled) or os.path.isfile(pio_esptool)) and not has_pyserial:
|
|
||||||
print("Found bundled esptool but pyserial is not installed.")
|
print("Found bundled esptool but pyserial is not installed.")
|
||||||
print("Install it with: pip install pyserial")
|
print("Install it with: pip install pyserial")
|
||||||
print("Or install the standalone esptool: pip install esptool")
|
print("Or install the standalone esptool: pip install esptool")
|
||||||
@@ -376,33 +364,6 @@ def find_esptool(prefer_system=False):
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
|
|
||||||
def esptool_supports_write_verify(esptool_cmd):
|
|
||||||
"""Return True if this esptool build accepts ``write_flash --verify``.
|
|
||||||
|
|
||||||
esptool v5 removed ``--verify`` from write-flash, while older releases
|
|
||||||
still accept it. Probe once and cache the result so flashing can choose
|
|
||||||
the compatible verification path.
|
|
||||||
"""
|
|
||||||
cache_key = tuple(esptool_cmd)
|
|
||||||
if cache_key in _esptool_write_verify_support:
|
|
||||||
return _esptool_write_verify_support[cache_key]
|
|
||||||
|
|
||||||
try:
|
|
||||||
result = subprocess.run(
|
|
||||||
esptool_cmd + ["write_flash", "-h"],
|
|
||||||
capture_output=True,
|
|
||||||
text=True,
|
|
||||||
timeout=10,
|
|
||||||
)
|
|
||||||
output = (result.stdout or "") + (result.stderr or "")
|
|
||||||
supported = "--verify" in output
|
|
||||||
except Exception:
|
|
||||||
supported = False
|
|
||||||
|
|
||||||
_esptool_write_verify_support[cache_key] = supported
|
|
||||||
return supported
|
|
||||||
|
|
||||||
|
|
||||||
def find_serial_port():
|
def find_serial_port():
|
||||||
"""List available serial ports and let the user choose."""
|
"""List available serial ports and let the user choose."""
|
||||||
system = platform.system()
|
system = platform.system()
|
||||||
@@ -750,7 +711,7 @@ def check_partition_table(port, esptool_cmd, baud=None):
|
|||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
True — partition table matches (or no expected table to compare against)
|
True — partition table matches (or no expected table to compare against)
|
||||||
False — partition table mismatch or unreadable state (device needs full flash)
|
False — partition table mismatch (device needs full flash)
|
||||||
"""
|
"""
|
||||||
expected_path = find_partitions()
|
expected_path = find_partitions()
|
||||||
if not expected_path:
|
if not expected_path:
|
||||||
@@ -764,7 +725,8 @@ def check_partition_table(port, esptool_cmd, baud=None):
|
|||||||
device_data = read_device_partitions(port, esptool_cmd, baud)
|
device_data = read_device_partitions(port, esptool_cmd, baud)
|
||||||
if device_data is None:
|
if device_data is None:
|
||||||
print(" Could not read partition table from device")
|
print(" Could not read partition table from device")
|
||||||
return False
|
# Can't verify — assume OK (user can always use --full)
|
||||||
|
return True
|
||||||
|
|
||||||
# Compare only the meaningful portion (both should be PARTITION_TABLE_SIZE)
|
# Compare only the meaningful portion (both should be PARTITION_TABLE_SIZE)
|
||||||
if device_data[:len(expected)] == expected:
|
if device_data[:len(expected)] == expected:
|
||||||
@@ -786,7 +748,7 @@ def check_app_on_device(port, esptool_cmd, baud=None):
|
|||||||
Reads a small chunk from APP_ADDR (0x10000). If the region is all 0xFF
|
Reads a small chunk from APP_ADDR (0x10000). If the region is all 0xFF
|
||||||
(erased flash), no app is present and the device needs a full flash.
|
(erased flash), no app is present and the device needs a full flash.
|
||||||
|
|
||||||
Returns True if app firmware is detected, False if blank/absent or unreadable.
|
Returns True if app firmware is detected, False if blank/absent.
|
||||||
"""
|
"""
|
||||||
import tempfile
|
import tempfile
|
||||||
if baud is None:
|
if baud is None:
|
||||||
@@ -808,7 +770,7 @@ def check_app_on_device(port, esptool_cmd, baud=None):
|
|||||||
result = subprocess.run(cmd, capture_output=True, text=True, timeout=30)
|
result = subprocess.run(cmd, capture_output=True, text=True, timeout=30)
|
||||||
if result.returncode != 0:
|
if result.returncode != 0:
|
||||||
print(" Warning: Could not read app region from device")
|
print(" Warning: Could not read app region from device")
|
||||||
return False
|
return True # assume app exists if we can't check
|
||||||
with open(tmp.name, "rb") as f:
|
with open(tmp.name, "rb") as f:
|
||||||
data = f.read()
|
data = f.read()
|
||||||
# All 0xFF means flash is blank — no app present
|
# All 0xFF means flash is blank — no app present
|
||||||
@@ -817,7 +779,7 @@ def check_app_on_device(port, esptool_cmd, baud=None):
|
|||||||
return True
|
return True
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f" Warning: App check failed: {e}")
|
print(f" Warning: App check failed: {e}")
|
||||||
return False
|
return True # assume app exists if we can't check
|
||||||
finally:
|
finally:
|
||||||
try:
|
try:
|
||||||
os.unlink(tmp.name)
|
os.unlink(tmp.name)
|
||||||
@@ -858,37 +820,6 @@ def reset_to_bootloader(port):
|
|||||||
return True
|
return True
|
||||||
|
|
||||||
|
|
||||||
def verify_firmware(firmware_path, port, esptool_cmd, baud=None,
|
|
||||||
flash_mode=None, no_hard_reset=False):
|
|
||||||
"""Verify flashed firmware using esptool's dedicated verify command."""
|
|
||||||
if baud is None:
|
|
||||||
baud = BAUD_RATE()
|
|
||||||
flash_size = FLASH_SIZE()
|
|
||||||
mode = flash_mode or BOARD_FLASH_MODE()
|
|
||||||
|
|
||||||
is_merged = is_merged_binary(firmware_path)
|
|
||||||
flash_addr = f"0x{BOOTLOADER_ADDR:x}" if is_merged else f"0x{APP_ADDR:x}"
|
|
||||||
after_arg = "no_reset" if no_hard_reset else "hard_reset"
|
|
||||||
|
|
||||||
print("\nVerifying flashed firmware...")
|
|
||||||
cmd = esptool_cmd + [
|
|
||||||
"--chip", CHIP,
|
|
||||||
"--port", port,
|
|
||||||
"--baud", baud,
|
|
||||||
"--before", "no_reset",
|
|
||||||
"--after", after_arg,
|
|
||||||
"verify_flash",
|
|
||||||
"--flash_mode", mode,
|
|
||||||
"--flash_freq", FLASH_FREQ,
|
|
||||||
"--flash_size", flash_size,
|
|
||||||
flash_addr, firmware_path,
|
|
||||||
]
|
|
||||||
|
|
||||||
print("Running: " + " ".join(cmd[-8:]))
|
|
||||||
result = subprocess.run(cmd)
|
|
||||||
return result.returncode == 0
|
|
||||||
|
|
||||||
|
|
||||||
def flash_firmware(firmware_path, port, esptool_cmd, baud=None,
|
def flash_firmware(firmware_path, port, esptool_cmd, baud=None,
|
||||||
no_reset_before=False, verify=False,
|
no_reset_before=False, verify=False,
|
||||||
flash_mode=None, no_hard_reset=False):
|
flash_mode=None, no_hard_reset=False):
|
||||||
@@ -918,10 +849,8 @@ def flash_firmware(firmware_path, port, esptool_cmd, baud=None,
|
|||||||
flash_addr = f"0x{APP_ADDR:x}"
|
flash_addr = f"0x{APP_ADDR:x}"
|
||||||
print(f" Detected: app-only binary -> flash at {flash_addr}")
|
print(f" Detected: app-only binary -> flash at {flash_addr}")
|
||||||
|
|
||||||
inline_verify = verify and esptool_supports_write_verify(esptool_cmd)
|
before_arg = "no_reset" if no_reset_before else "default-reset"
|
||||||
post_write_verify = verify and not inline_verify
|
after_arg = "no_reset" if no_hard_reset else "hard-reset"
|
||||||
before_arg = "no_reset" if no_reset_before else "default_reset"
|
|
||||||
after_arg = "no_reset" if (no_hard_reset or post_write_verify) else "hard_reset"
|
|
||||||
|
|
||||||
cmd = esptool_cmd + [
|
cmd = esptool_cmd + [
|
||||||
"--chip", CHIP,
|
"--chip", CHIP,
|
||||||
@@ -929,32 +858,19 @@ def flash_firmware(firmware_path, port, esptool_cmd, baud=None,
|
|||||||
"--baud", baud,
|
"--baud", baud,
|
||||||
"--before", before_arg,
|
"--before", before_arg,
|
||||||
"--after", after_arg,
|
"--after", after_arg,
|
||||||
"write_flash",
|
"write-flash",
|
||||||
"-z",
|
"-z",
|
||||||
"--flash_mode", mode,
|
"--flash-mode", mode,
|
||||||
"--flash_freq", FLASH_FREQ,
|
"--flash-freq", FLASH_FREQ,
|
||||||
"--flash_size", flash_size,
|
"--flash-size", flash_size,
|
||||||
]
|
]
|
||||||
if inline_verify:
|
if verify:
|
||||||
cmd.append("--verify")
|
cmd.append("--no-diff-verify")
|
||||||
cmd += [flash_addr, firmware_path]
|
cmd += [flash_addr, firmware_path]
|
||||||
|
|
||||||
print("Running: " + " ".join(cmd[-8:]))
|
print("Running: " + " ".join(cmd[-8:]))
|
||||||
result = subprocess.run(cmd)
|
result = subprocess.run(cmd)
|
||||||
if result.returncode != 0:
|
return result.returncode == 0
|
||||||
return False
|
|
||||||
|
|
||||||
if post_write_verify:
|
|
||||||
return verify_firmware(
|
|
||||||
firmware_path,
|
|
||||||
port,
|
|
||||||
esptool_cmd,
|
|
||||||
baud=baud,
|
|
||||||
flash_mode=mode,
|
|
||||||
no_hard_reset=no_hard_reset,
|
|
||||||
)
|
|
||||||
|
|
||||||
return True
|
|
||||||
|
|
||||||
|
|
||||||
def _monitor_boot(port, timeout=8):
|
def _monitor_boot(port, timeout=8):
|
||||||
@@ -1019,28 +935,15 @@ def main():
|
|||||||
formatter_class=argparse.RawDescriptionHelpFormatter,
|
formatter_class=argparse.RawDescriptionHelpFormatter,
|
||||||
epilog="""
|
epilog="""
|
||||||
Examples:
|
Examples:
|
||||||
python flash.py
|
python flash.py # Download latest & app-only update (V4)
|
||||||
Download latest firmware and flash default board.
|
python flash.py --board v3 # Download latest & app-only update (V3)
|
||||||
python flash.py --update
|
python flash.py --release v1.0.12 # Flash a specific release version
|
||||||
Legacy alias for an app-only update.
|
python flash.py --full # Full flash with merged binary
|
||||||
python flash.py --use-system-esptool
|
python flash.py --offline # Use cached/local firmware only
|
||||||
Prefer a host-installed esptool over the bundled Release copy.
|
python flash.py --file firmware.bin # Flash a specific file
|
||||||
python flash.py --board v3
|
python flash.py --merge-only # Build merged binary for release
|
||||||
Download latest firmware and flash a V3 board.
|
python flash.py --port /dev/ttyACM0 # Specify serial port
|
||||||
python flash.py --release v1.0.12
|
python flash.py --erase # Erase flash, then full flash (auto-verify)
|
||||||
Flash a specific release tag.
|
|
||||||
python flash.py --full
|
|
||||||
Do a full flash with the merged binary.
|
|
||||||
python flash.py --offline
|
|
||||||
Use only cached or local firmware.
|
|
||||||
python flash.py --file firmware.bin
|
|
||||||
Flash a specific local binary.
|
|
||||||
python flash.py --merge-only
|
|
||||||
Build the merged release binary without flashing.
|
|
||||||
python flash.py --port /dev/ttyACM0
|
|
||||||
Use a specific serial port.
|
|
||||||
python flash.py --erase
|
|
||||||
Erase flash first, then do a full flash.
|
|
||||||
""",
|
""",
|
||||||
)
|
)
|
||||||
parser.add_argument("--board", choices=["v3", "v4"], default=None,
|
parser.add_argument("--board", choices=["v3", "v4"], default=None,
|
||||||
@@ -1051,8 +954,6 @@ Examples:
|
|||||||
parser.add_argument("--baud", "-b", default=None, help="Baud rate (board-specific default)")
|
parser.add_argument("--baud", "-b", default=None, help="Baud rate (board-specific default)")
|
||||||
parser.add_argument("--release", "-r", default=None, metavar="TAG",
|
parser.add_argument("--release", "-r", default=None, metavar="TAG",
|
||||||
help="Flash a specific release version (e.g. v1.0.12)")
|
help="Flash a specific release version (e.g. v1.0.12)")
|
||||||
parser.add_argument("--update", action="store_true",
|
|
||||||
help="Legacy alias for an app-only firmware update")
|
|
||||||
parser.add_argument("--offline", action="store_true",
|
parser.add_argument("--offline", action="store_true",
|
||||||
help="Skip online check — use cached or local firmware only")
|
help="Skip online check — use cached or local firmware only")
|
||||||
parser.add_argument("--merge-only", action="store_true",
|
parser.add_argument("--merge-only", action="store_true",
|
||||||
@@ -1061,28 +962,17 @@ Examples:
|
|||||||
help="Flash merged binary (bootloader + partitions + app) — overwrites everything")
|
help="Flash merged binary (bootloader + partitions + app) — overwrites everything")
|
||||||
parser.add_argument("--erase", action="store_true",
|
parser.add_argument("--erase", action="store_true",
|
||||||
help="Erase entire flash before writing (implies --full)")
|
help="Erase entire flash before writing (implies --full)")
|
||||||
parser.add_argument("--use-system-esptool", action="store_true",
|
|
||||||
help="Use a host-installed esptool instead of the bundled Release copy")
|
|
||||||
# Power-user override (not shown in --help)
|
# Power-user override (not shown in --help)
|
||||||
parser.add_argument("--flash-mode", default=None,
|
parser.add_argument("--flash-mode", default=None,
|
||||||
help=argparse.SUPPRESS)
|
help=argparse.SUPPRESS)
|
||||||
|
|
||||||
args = parser.parse_args()
|
args = parser.parse_args()
|
||||||
|
|
||||||
if args.update and args.offline:
|
|
||||||
parser.error("--update cannot be combined with --offline")
|
|
||||||
|
|
||||||
if args.update:
|
|
||||||
print("Using legacy compatibility flag; default behavior already downloads and flashes the latest firmware unless --offline is set.")
|
|
||||||
|
|
||||||
# Find esptool early — needed for both auto-detect and flashing
|
# Find esptool early — needed for both auto-detect and flashing
|
||||||
esptool_cmd = find_esptool(prefer_system=args.use_system_esptool)
|
esptool_cmd = find_esptool()
|
||||||
if not esptool_cmd:
|
if not esptool_cmd:
|
||||||
print("Error: esptool not found!")
|
print("Error: esptool not found!")
|
||||||
print("Expected one of:")
|
print("Install it with: pip install esptool")
|
||||||
print(" 1. Bundled Release/esptool/esptool.py with pyserial available")
|
|
||||||
print(" 2. PlatformIO's packaged esptool")
|
|
||||||
print(" 3. A host-installed esptool (pip install esptool)")
|
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
# ── Board detection ─────────────────────────────────────────────────
|
# ── Board detection ─────────────────────────────────────────────────
|
||||||
|
|||||||
0
lib/microReticulum/library.properties
Normal file → Executable file
0
lib/microReticulum/library.properties
Normal file → Executable file
162
platformio.ini
162
platformio.ini
@@ -9,7 +9,6 @@
|
|||||||
; https://docs.platformio.org/page/projectconf.html
|
; https://docs.platformio.org/page/projectconf.html
|
||||||
|
|
||||||
[platformio]
|
[platformio]
|
||||||
; Change source and include directories to root of project since RNode places them here
|
|
||||||
include_dir = .
|
include_dir = .
|
||||||
src_dir = .
|
src_dir = .
|
||||||
|
|
||||||
@@ -19,37 +18,23 @@ monitor_speed = 115200
|
|||||||
upload_speed = 460800
|
upload_speed = 460800
|
||||||
build_flags =
|
build_flags =
|
||||||
-Wall
|
-Wall
|
||||||
;-Wextra
|
|
||||||
-Wno-missing-field-initializers
|
-Wno-missing-field-initializers
|
||||||
-Wno-format
|
-Wno-format
|
||||||
-I.
|
-I.
|
||||||
; CBA Define following to disable DEBUG build
|
|
||||||
;-DNDEBUG
|
|
||||||
; CBA Define following to include RNS stack
|
|
||||||
-DHAS_RNS
|
-DHAS_RNS
|
||||||
-DRNS_USE_FS
|
-DRNS_USE_FS
|
||||||
-DRNS_PERSIST_PATHS
|
-DRNS_PERSIST_PATHS
|
||||||
-DMSGPACK_USE_BOOST=OFF
|
-DMSGPACK_USE_BOOST=OFF
|
||||||
; CBA Define following to disable LFS asserts
|
|
||||||
;-DLFS_NO_ASSERT
|
|
||||||
; ???
|
|
||||||
;-DLFS_YES_TRACE
|
|
||||||
; ???
|
|
||||||
;-DCORE_DEBUG_LEVEL=5
|
|
||||||
; ??? NO
|
|
||||||
;-DLOG_LOCAL_LEVEL=5
|
|
||||||
;-DCONFIG_LOG_DEFAULT_LEVEL=5
|
|
||||||
lib_deps =
|
lib_deps =
|
||||||
ArduinoJson@^7.4.2
|
ArduinoJson@^7.4.2
|
||||||
MsgPack@^0.4.2
|
MsgPack@^0.4.2
|
||||||
adafruit/Adafruit SSD1306@^2.5.9
|
adafruit/Adafruit SSD1306@^2.5.9
|
||||||
https://github.com/attermann/Crypto.git
|
https://github.com/attermann/Crypto.git
|
||||||
; Exclude directories in root from sources
|
|
||||||
build_src_filter = +<*> -<variants/>
|
build_src_filter = +<*> -<variants/>
|
||||||
extra_scripts = pre:extra_script.py
|
extra_scripts = pre:extra_script.py
|
||||||
|
|
||||||
[env:rnode-ng-20]
|
[env:rnode-ng-20]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v2
|
board = ttgo-lora32-v2
|
||||||
custom_variant = ng20
|
custom_variant = ng20
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -60,10 +45,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
adafruit/Adafruit NeoPixel@^1.12.0
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:rnode-ng-21]
|
[env:rnode-ng-21]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v21
|
board = ttgo-lora32-v21
|
||||||
custom_variant = ng21
|
custom_variant = ng21
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -74,10 +59,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
adafruit/Adafruit NeoPixel@^1.12.0
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-t-beam]
|
[env:ttgo-t-beam]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-t-beam
|
board = ttgo-t-beam
|
||||||
custom_variant = tbeam
|
custom_variant = tbeam
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -88,9 +73,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-t-beam-sx1262]
|
[env:ttgo-t-beam-sx1262]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-t-beam
|
board = ttgo-t-beam
|
||||||
custom_variant = tbeam_sx1262
|
custom_variant = tbeam_sx1262
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -102,9 +88,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-t-beam-supreme]
|
[env:ttgo-t-beam-supreme]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-t-beam
|
board = ttgo-t-beam
|
||||||
custom_variant = tbeam_supreme
|
custom_variant = tbeam_supreme
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -118,9 +105,10 @@ lib_deps =
|
|||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
Adafruit_SH110X
|
Adafruit_SH110X
|
||||||
adafruit/Adafruit SH110X@^2.1.14
|
adafruit/Adafruit SH110X@^2.1.14
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:lilygo-t3-s3]
|
[env:lilygo-t3-s3]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = lilygo-t3-s3
|
board = lilygo-t3-s3
|
||||||
custom_variant = t3s3
|
custom_variant = t3s3
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -132,9 +120,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:lilygo-t3-s3-sx127x]
|
[env:lilygo-t3-s3-sx127x]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = lilygo-t3-s3
|
board = lilygo-t3-s3
|
||||||
custom_variant = t3s3_sx127x
|
custom_variant = t3s3_sx127x
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -146,9 +135,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:lilygo-t3-s3-sx1280-pa]
|
[env:lilygo-t3-s3-sx1280-pa]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = lilygo-t3-s3
|
board = lilygo-t3-s3
|
||||||
custom_variant = t3s3_sx1280_pa
|
custom_variant = t3s3_sx1280_pa
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -160,17 +150,16 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:lilygo-t-deck]
|
[env:lilygo-t-deck]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32-s3-devkitc-1
|
board = esp32-s3-devkitc-1
|
||||||
custom_variant = tdeck
|
custom_variant = tdeck
|
||||||
board_build.filesystem = littlefs
|
board_build.filesystem = littlefs
|
||||||
; Flash / memory layout
|
|
||||||
board_upload.flash_size = 16MB
|
board_upload.flash_size = 16MB
|
||||||
board_upload.maximum_size = 16777216
|
board_upload.maximum_size = 16777216
|
||||||
board_build.partitions = default_16MB.csv
|
board_build.partitions = default_16MB.csv
|
||||||
; Enable PSRAM + correct flash mode
|
|
||||||
board_build.flash_mode = qio
|
board_build.flash_mode = qio
|
||||||
board_build.psram_type = opi
|
board_build.psram_type = opi
|
||||||
board_build.arduino.memory_type = qio_opi
|
board_build.arduino.memory_type = qio_opi
|
||||||
@@ -180,16 +169,14 @@ build_flags =
|
|||||||
-DBOARD_HAS_PSRAM=1
|
-DBOARD_HAS_PSRAM=1
|
||||||
-DARDUINO_USB_MODE=1
|
-DARDUINO_USB_MODE=1
|
||||||
-DCORE_DEBUG_LEVEL=1
|
-DCORE_DEBUG_LEVEL=1
|
||||||
; Enable UARDUINO_ USB_ CDC_ ON_ BOOT will start printing and wait for terminal access during startup
|
|
||||||
-DARDUINO_USB_CDC_ON_BOOT=1
|
-DARDUINO_USB_CDC_ON_BOOT=1
|
||||||
; Enable UARDUINO_USB_CDC_ON_BOOT will turn off printing and will not block when using the battery
|
|
||||||
; -UARDUINO_USB_CDC_ON_BOOT
|
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v1]
|
[env:ttgo-lora32-v1]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v1
|
board = ttgo-lora32-v1
|
||||||
custom_variant = lora32v10
|
custom_variant = lora32v10
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -200,9 +187,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v2]
|
[env:ttgo-lora32-v2]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v2
|
board = ttgo-lora32-v2
|
||||||
custom_variant = lora32v20
|
custom_variant = lora32v20
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -213,9 +201,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v2-extled]
|
[env:ttgo-lora32-v2-extled]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v2
|
board = ttgo-lora32-v2
|
||||||
custom_variant = lora32v20_extled
|
custom_variant = lora32v20_extled
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -227,9 +216,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v21]
|
[env:ttgo-lora32-v21]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v21
|
board = ttgo-lora32-v21
|
||||||
custom_variant = lora32v21
|
custom_variant = lora32v21
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -240,9 +230,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v21-extled]
|
[env:ttgo-lora32-v21-extled]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v21
|
board = ttgo-lora32-v21
|
||||||
custom_variant = lora32v21_extled
|
custom_variant = lora32v21_extled
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -254,9 +245,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:ttgo-lora32-v21-tcxo]
|
[env:ttgo-lora32-v21-tcxo]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v21
|
board = ttgo-lora32-v21
|
||||||
custom_variant = lora32v21_extled
|
custom_variant = lora32v21_extled
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -268,9 +260,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:heltec_wifi_lora_32_V2]
|
[env:heltec_wifi_lora_32_V2]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = heltec_wifi_lora_32_V2
|
board = heltec_wifi_lora_32_V2
|
||||||
custom_variant = heltec32v2
|
custom_variant = heltec32v2
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -281,9 +274,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:heltec_wifi_lora_32_V2-extled]
|
[env:heltec_wifi_lora_32_V2-extled]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = heltec_wifi_lora_32_V2
|
board = heltec_wifi_lora_32_V2
|
||||||
custom_variant = heltec32v2_extled
|
custom_variant = heltec32v2_extled
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -295,9 +289,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:heltec_wifi_lora_32_V3]
|
[env:heltec_wifi_lora_32_V3]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = heltec_wifi_lora_32_V3
|
board = heltec_wifi_lora_32_V3
|
||||||
custom_variant = heltec32v3
|
custom_variant = heltec32v3
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -308,16 +303,13 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:heltec_V3_boundary]
|
[env:heltec_V3_boundary]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = heltec_wifi_lora_32_V3
|
board = heltec_wifi_lora_32_V3
|
||||||
custom_variant = heltec32v3
|
custom_variant = heltec32v3
|
||||||
board_build.filesystem = littlefs
|
board_build.filesystem = littlefs
|
||||||
; Flash / memory layout for 8MB flash
|
|
||||||
; PSRAM: V3 ESP32-S3FN8 has NO PSRAM — firmware detects this at runtime
|
|
||||||
; and falls back to internal SRAM for TLSF pool.
|
|
||||||
; BOARD_HAS_PSRAM tells Arduino to *attempt* psramInit(); harmless if absent.
|
|
||||||
board_upload.flash_size = 8MB
|
board_upload.flash_size = 8MB
|
||||||
board_upload.maximum_size = 8388608
|
board_upload.maximum_size = 8388608
|
||||||
board_build.partitions = default_8MB.csv
|
board_build.partitions = default_8MB.csv
|
||||||
@@ -330,21 +322,18 @@ build_flags =
|
|||||||
-DBOARD_MODEL=BOARD_HELTEC32_V3
|
-DBOARD_MODEL=BOARD_HELTEC32_V3
|
||||||
-DBOARD_HAS_PSRAM=1
|
-DBOARD_HAS_PSRAM=1
|
||||||
-DBOUNDARY_MODE
|
-DBOUNDARY_MODE
|
||||||
;-DNDEBUG
|
|
||||||
-DRNS_USE_TLSF=1
|
-DRNS_USE_TLSF=1
|
||||||
-DRNS_USE_ALLOCATOR=1
|
-DRNS_USE_ALLOCATOR=1
|
||||||
; --- Boundary mode defaults (override via EEPROM at runtime) ---
|
|
||||||
; TCP server mode (0=server, 1=client)
|
|
||||||
-DBOUNDARY_TCP_MODE=0
|
-DBOUNDARY_TCP_MODE=0
|
||||||
; TCP listen/connect port
|
|
||||||
-DBOUNDARY_TCP_PORT=4242
|
-DBOUNDARY_TCP_PORT=4242
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:heltec_wifi_lora_32_V4]
|
[env:heltec_wifi_lora_32_V4]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32-s3-devkitc-1
|
board = esp32-s3-devkitc-1
|
||||||
custom_variant = heltec32v4
|
custom_variant = heltec32v4
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -356,13 +345,41 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
|
[env:meshadventurer_S3_boundary]
|
||||||
|
platform = espressif32@6.12.0
|
||||||
|
board = esp32-s3-devkitc-1
|
||||||
|
custom_variant = meshadventurer_s3_boundary
|
||||||
|
board_build.filesystem = littlefs
|
||||||
|
board_upload.flash_size = 16MB
|
||||||
|
board_upload.maximum_size = 16777216
|
||||||
|
board_build.partitions = default_16MB.csv
|
||||||
|
board_build.flash_mode = qio
|
||||||
|
board_build.psram_type = qio
|
||||||
|
board_build.arduino.memory_type = qio_qspi
|
||||||
|
monitor_speed = 921600
|
||||||
|
build_flags =
|
||||||
|
${env.build_flags}
|
||||||
|
-DBOARD_MODEL=BOARD_MESHADVENTURER_S3
|
||||||
|
-DARDUINO_USB_CDC_ON_BOOT=1
|
||||||
|
-DBOARD_HAS_PSRAM=1
|
||||||
|
-DBOUNDARY_MODE
|
||||||
|
-DRNS_USE_TLSF=1
|
||||||
|
-DRNS_USE_ALLOCATOR=1
|
||||||
|
-DBOUNDARY_TCP_MODE=0
|
||||||
|
-DBOUNDARY_TCP_PORT=4242
|
||||||
|
lib_deps =
|
||||||
|
${env.lib_deps}
|
||||||
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:heltec_V4_boundary]
|
[env:heltec_V4_boundary]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32-s3-devkitc-1
|
board = esp32-s3-devkitc-1
|
||||||
custom_variant = heltec32v4_boundary
|
custom_variant = heltec32v4_boundary
|
||||||
board_build.filesystem = littlefs
|
board_build.filesystem = littlefs
|
||||||
; Flash / memory layout for 16MB flash + 2MB PSRAM
|
|
||||||
board_upload.flash_size = 16MB
|
board_upload.flash_size = 16MB
|
||||||
board_upload.maximum_size = 16777216
|
board_upload.maximum_size = 16777216
|
||||||
board_build.partitions = default_16MB.csv
|
board_build.partitions = default_16MB.csv
|
||||||
@@ -376,24 +393,18 @@ build_flags =
|
|||||||
-DARDUINO_USB_CDC_ON_BOOT=1
|
-DARDUINO_USB_CDC_ON_BOOT=1
|
||||||
-DBOARD_HAS_PSRAM=1
|
-DBOARD_HAS_PSRAM=1
|
||||||
-DBOUNDARY_MODE
|
-DBOUNDARY_MODE
|
||||||
;-DNDEBUG
|
|
||||||
-DRNS_USE_TLSF=1
|
-DRNS_USE_TLSF=1
|
||||||
-DRNS_USE_ALLOCATOR=1
|
-DRNS_USE_ALLOCATOR=1
|
||||||
; --- Boundary mode defaults (override via EEPROM at runtime) ---
|
|
||||||
; TCP server mode (0=server, 1=client)
|
|
||||||
-DBOUNDARY_TCP_MODE=0
|
-DBOUNDARY_TCP_MODE=0
|
||||||
; TCP listen/connect port
|
|
||||||
-DBOUNDARY_TCP_PORT=4242
|
-DBOUNDARY_TCP_PORT=4242
|
||||||
; Backbone host for client mode (empty = server mode)
|
|
||||||
; -DBOUNDARY_BACKBONE_HOST=\"192.168.1.100\"
|
|
||||||
; -DBOUNDARY_BACKBONE_PORT=4242
|
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:heltec_V4_boundary-local]
|
[env:heltec_V4_boundary-local]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32-s3-devkitc-1
|
board = esp32-s3-devkitc-1
|
||||||
custom_variant = heltec32v4_boundary_local
|
custom_variant = heltec32v4_boundary_local
|
||||||
board_build.filesystem = littlefs
|
board_build.filesystem = littlefs
|
||||||
@@ -414,10 +425,11 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:featheresp32]
|
[env:featheresp32]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = featheresp32
|
board = featheresp32
|
||||||
custom_variant = featheresp32
|
custom_variant = featheresp32
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -428,9 +440,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:seeed_xiao_esp32s3]
|
[env:seeed_xiao_esp32s3]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = seeed_xiao_esp32s3
|
board = seeed_xiao_esp32s3
|
||||||
custom_variant = xiao_esp32s3
|
custom_variant = xiao_esp32s3
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -441,9 +454,10 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:generic-esp32]
|
[env:generic-esp32]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32dev
|
board = esp32dev
|
||||||
custom_variant = esp32_generic
|
custom_variant = esp32_generic
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -454,6 +468,7 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:wiscore_rak4631]
|
[env:wiscore_rak4631]
|
||||||
platform = nordicnrf52
|
platform = nordicnrf52
|
||||||
@@ -471,11 +486,10 @@ build_flags =
|
|||||||
-DRNS_USE_ALLOCATOR=1
|
-DRNS_USE_ALLOCATOR=1
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
|
|
||||||
[env:ttgo-t-beam-local]
|
[env:ttgo-t-beam-local]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-t-beam
|
board = ttgo-t-beam
|
||||||
upload_speed = 460800
|
upload_speed = 460800
|
||||||
custom_variant = tbeam_local
|
custom_variant = tbeam_local
|
||||||
@@ -485,16 +499,15 @@ build_flags =
|
|||||||
${env.build_flags}
|
${env.build_flags}
|
||||||
-fexceptions
|
-fexceptions
|
||||||
-DBOARD_MODEL=BOARD_TBEAM
|
-DBOARD_MODEL=BOARD_TBEAM
|
||||||
; CBA TEST
|
|
||||||
;-DUSE_FLASHFS=1
|
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
Adafruit_SPIFlash=symlink://../Adafruit_SPIFlash
|
Adafruit_SPIFlash=symlink://../Adafruit_SPIFlash
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:ttgo-lora32-v21-local]
|
[env:ttgo-lora32-v21-local]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = ttgo-lora32-v21
|
board = ttgo-lora32-v21
|
||||||
upload_speed = 460800
|
upload_speed = 460800
|
||||||
custom_variant = lora32v21_local
|
custom_variant = lora32v21_local
|
||||||
@@ -506,10 +519,11 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:heltec_wifi_lora_32_V4-local]
|
[env:heltec_wifi_lora_32_V4-local]
|
||||||
platform = espressif32
|
platform = espressif32@6.12.0
|
||||||
board = esp32-s3-devkitc-1
|
board = esp32-s3-devkitc-1
|
||||||
custom_variant = heltec32v4_local
|
custom_variant = heltec32v4_local
|
||||||
board_build.partitions = no_ota.csv
|
board_build.partitions = no_ota.csv
|
||||||
@@ -521,6 +535,7 @@ build_flags =
|
|||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
XPowersLib@^0.2.1
|
XPowersLib@^0.2.1
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
monitor_filters = esp32_exception_decoder
|
monitor_filters = esp32_exception_decoder
|
||||||
|
|
||||||
[env:wiscore_rak4631-local]
|
[env:wiscore_rak4631-local]
|
||||||
@@ -535,17 +550,15 @@ build_flags =
|
|||||||
-I variants/rak4630
|
-I variants/rak4630
|
||||||
-fexceptions
|
-fexceptions
|
||||||
-DBOARD_MODEL=BOARD_RAK4631
|
-DBOARD_MODEL=BOARD_RAK4631
|
||||||
; CBA TEST
|
|
||||||
-DRNS_USE_TLSF=1
|
-DRNS_USE_TLSF=1
|
||||||
-DRNS_USE_ALLOCATOR=1
|
-DRNS_USE_ALLOCATOR=1
|
||||||
;-DUSE_FLASHFS=1
|
|
||||||
build_unflags = -fno-exceptions
|
build_unflags = -fno-exceptions
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
Adafruit_SPIFlash=symlink://../Adafruit_SPIFlash
|
Adafruit_SPIFlash=symlink://../Adafruit_SPIFlash
|
||||||
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|
||||||
[env:heltec_t114_local]
|
[env:heltec_t114_local]
|
||||||
;upload_port = /dev/cu.usbmodem1101
|
|
||||||
platform = nordicnrf52
|
platform = nordicnrf52
|
||||||
board = nrf52840_dk_adafruit
|
board = nrf52840_dk_adafruit
|
||||||
custom_variant = heltec_t114_local
|
custom_variant = heltec_t114_local
|
||||||
@@ -555,11 +568,10 @@ build_flags =
|
|||||||
${env.build_flags}
|
${env.build_flags}
|
||||||
-fexceptions
|
-fexceptions
|
||||||
-DBOARD_MODEL=BOARD_HELTEC_T114
|
-DBOARD_MODEL=BOARD_HELTEC_T114
|
||||||
; CBA TEST
|
|
||||||
-DRNS_USE_TLSF=1
|
-DRNS_USE_TLSF=1
|
||||||
-DRNS_USE_ALLOCATOR=1
|
-DRNS_USE_ALLOCATOR=1
|
||||||
build_unflags = -fno-exceptions
|
build_unflags = -fno-exceptions
|
||||||
lib_deps =
|
lib_deps =
|
||||||
${env.lib_deps}
|
${env.lib_deps}
|
||||||
https://github.com/liamcottle/esp8266-oled-ssd1306#e16cee124fe26490cb14880c679321ad8ac89c95
|
https://github.com/liamcottle/esp8266-oled-ssd1306#e16cee124fe26490cb14880c679321ad8ac89c95
|
||||||
adafruit/Adafruit NeoPixel@^1.12.0
|
adafruit/Adafruit NeoPixel@^1.15.4
|
||||||
|
|||||||
2841
rnodethv3.log
2841
rnodethv3.log
File diff suppressed because it is too large
Load Diff
123
sx126x.cpp
123
sx126x.cpp
@@ -96,13 +96,21 @@
|
|||||||
#define SPI spiModem
|
#define SPI spiModem
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if HAS_LORA_PA
|
||||||
|
uint8_t lora_pa_model = LORA_PA_MODEL;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if HAS_LORA_LNA
|
||||||
|
int lora_lna_gain = LORA_LNA_GAIN;
|
||||||
|
#endif
|
||||||
|
|
||||||
extern SPIClass SPI;
|
extern SPIClass SPI;
|
||||||
|
|
||||||
#define MAX_PKT_LENGTH 255
|
#define MAX_PKT_LENGTH 255
|
||||||
|
|
||||||
sx126x::sx126x() :
|
sx126x::sx126x() :
|
||||||
_spiSettings(16E6, MSBFIRST, SPI_MODE0),
|
_spiSettings(16E6, MSBFIRST, SPI_MODE0),
|
||||||
_ss(LORA_DEFAULT_SS_PIN), _reset(LORA_DEFAULT_RESET_PIN), _dio0(LORA_DEFAULT_DIO0_PIN), _busy(LORA_DEFAULT_BUSY_PIN), _rxen(LORA_DEFAULT_RXEN_PIN),
|
_ss(LORA_DEFAULT_SS_PIN), _reset(LORA_DEFAULT_RESET_PIN), _dio0(LORA_DEFAULT_DIO0_PIN), _busy(LORA_DEFAULT_BUSY_PIN), _rxen(LORA_DEFAULT_RXEN_PIN), _txen(LORA_DEFAULT_TXEN_PIN),
|
||||||
_frequency(0),
|
_frequency(0),
|
||||||
_txp(0),
|
_txp(0),
|
||||||
_sf(0x07),
|
_sf(0x07),
|
||||||
@@ -126,7 +134,7 @@ bool sx126x::preInit() {
|
|||||||
pinMode(_ss, OUTPUT);
|
pinMode(_ss, OUTPUT);
|
||||||
digitalWrite(_ss, HIGH);
|
digitalWrite(_ss, HIGH);
|
||||||
|
|
||||||
#if BOARD_MODEL == BOARD_T3S3 || BOARD_MODEL == BOARD_HELTEC32_V3 || BOARD_MODEL == BOARD_HELTEC32_V4 || BOARD_MODEL == BOARD_TDECK || BOARD_MODEL == BOARD_XIAO_S3
|
#if BOARD_MODEL == BOARD_T3S3 || BOARD_MODEL == BOARD_HELTEC32_V3 || BOARD_MODEL == BOARD_HELTEC32_V4 || BOARD_MODEL == BOARD_TDECK || BOARD_MODEL == BOARD_XIAO_S3 || BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
SPI.begin(pin_sclk, pin_miso, pin_mosi, pin_cs);
|
SPI.begin(pin_sclk, pin_miso, pin_mosi, pin_cs);
|
||||||
#elif BOARD_MODEL == BOARD_TECHO
|
#elif BOARD_MODEL == BOARD_TECHO
|
||||||
SPI.setPins(pin_miso, pin_sclk, pin_mosi);
|
SPI.setPins(pin_miso, pin_sclk, pin_mosi);
|
||||||
@@ -184,6 +192,7 @@ uint8_t ISR_VECT sx126x::singleTransfer(uint8_t opcode, uint16_t address, uint8_
|
|||||||
|
|
||||||
void sx126x::rxAntEnable() {
|
void sx126x::rxAntEnable() {
|
||||||
if (_rxen != -1) { digitalWrite(_rxen, HIGH); }
|
if (_rxen != -1) { digitalWrite(_rxen, HIGH); }
|
||||||
|
if (_txen != -1) { digitalWrite(_txen, LOW); }
|
||||||
}
|
}
|
||||||
|
|
||||||
void sx126x::loraMode() {
|
void sx126x::loraMode() {
|
||||||
@@ -274,6 +283,21 @@ void sx126x::setPacketParams(long preamble_symbols, uint8_t headermode, uint8_t
|
|||||||
buf[7] = 0x00;
|
buf[7] = 0x00;
|
||||||
buf[8] = 0x00;
|
buf[8] = 0x00;
|
||||||
executeOpcode(OP_PACKET_PARAMS_6X, buf, 9);
|
executeOpcode(OP_PACKET_PARAMS_6X, buf, 9);
|
||||||
|
|
||||||
|
// SX1262 errata section 15.4: IQ polarity is inverted compared to
|
||||||
|
// SX1276. The SetPacketParams command resets register 0x0736 to an
|
||||||
|
// incorrect default. For standard IQ (no inversion), bit 2 must be
|
||||||
|
// SET after every SetPacketParams call. For inverted IQ, bit 2 must
|
||||||
|
// be CLEARED. Without this fix, LoRa RX demodulation fails silently
|
||||||
|
// while TX continues to work.
|
||||||
|
uint8_t iqreg = readRegister(0x0736);
|
||||||
|
if (buf[5] == 0x00) {
|
||||||
|
// Standard IQ: set bit 2
|
||||||
|
writeRegister(0x0736, iqreg | 0x04);
|
||||||
|
} else {
|
||||||
|
// Inverted IQ: clear bit 2
|
||||||
|
writeRegister(0x0736, iqreg & ~0x04);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void sx126x::reset(void) {
|
void sx126x::reset(void) {
|
||||||
@@ -286,6 +310,22 @@ void sx126x::reset(void) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void sx126x::setDCDCRegulator(void) {
|
||||||
|
// Documentation
|
||||||
|
// 5. Power Distribution -> 5.1 Selecting DC-DC Converter or LDO Regulation
|
||||||
|
// 13.1.11 SetRegulatorMode
|
||||||
|
|
||||||
|
uint8_t mode_byte = MODE_STDBY_RC_6X;
|
||||||
|
executeOpcode(OP_STANDBY_6X, &mode_byte, 1);
|
||||||
|
|
||||||
|
// Enable DC-DC regulator for high power operation
|
||||||
|
uint8_t reg_mode = 0x01; // 0x00 = LDO, 0x01 = DC-DC
|
||||||
|
executeOpcode(OP_REGULATOR_MODE_6X, ®_mode, 1);
|
||||||
|
|
||||||
|
delay(5);
|
||||||
|
waitOnBusy();
|
||||||
|
}
|
||||||
|
|
||||||
void sx126x::calibrate(void) {
|
void sx126x::calibrate(void) {
|
||||||
// Put in STDBY_RC mode before calibration
|
// Put in STDBY_RC mode before calibration
|
||||||
uint8_t mode_byte = MODE_STDBY_RC_6X;
|
uint8_t mode_byte = MODE_STDBY_RC_6X;
|
||||||
@@ -316,10 +356,21 @@ int sx126x::begin(long frequency) {
|
|||||||
if (_busy != -1) { pinMode(_busy, INPUT); }
|
if (_busy != -1) { pinMode(_busy, INPUT); }
|
||||||
if (!_preinit_done) { if (!preInit()) { return false; } }
|
if (!_preinit_done) { if (!preInit()) { return false; } }
|
||||||
if (_rxen != -1) { pinMode(_rxen, OUTPUT); }
|
if (_rxen != -1) { pinMode(_rxen, OUTPUT); }
|
||||||
|
if (_txen != -1) { pinMode(_txen, OUTPUT); }
|
||||||
|
|
||||||
|
//TODO: if it works, make it optional
|
||||||
|
//#ifdef SX1262_USE_DCDC_REGULATOR
|
||||||
|
setDCDCRegulator();
|
||||||
|
//#endif
|
||||||
|
|
||||||
calibrate();
|
calibrate();
|
||||||
calibrate_image(frequency);
|
calibrate_image(frequency);
|
||||||
|
#if HAS_TCXO
|
||||||
enableTCXO();
|
enableTCXO();
|
||||||
|
//13.1.15 SetRxTxFallbackMode to STDBY_XOSC
|
||||||
|
uint8_t fallback_mode = 0x30; // STDBY_XOSC after TX/RX
|
||||||
|
executeOpcode(OP_RX_TX_FALLBACK_MODE_6X, &fallback_mode, 1);
|
||||||
|
#endif
|
||||||
loraMode();
|
loraMode();
|
||||||
standby();
|
standby();
|
||||||
|
|
||||||
@@ -336,7 +387,9 @@ int sx126x::begin(long frequency) {
|
|||||||
setFrequency(frequency);
|
setFrequency(frequency);
|
||||||
setTxPower(2);
|
setTxPower(2);
|
||||||
enableCrc();
|
enableCrc();
|
||||||
writeRegister(REG_LNA_6X, 0x96); // Set LNA boost
|
writeRegister(REG_LNA_6X, 0x96); // Set LNA boosted gain mode
|
||||||
|
// Undocumented SX1262 register patch recommended by Heltec/Semtech for improved RX sensitivity.
|
||||||
|
writeRegister(0x08B5, readRegister(0x08B5) | 0x01);
|
||||||
uint8_t basebuf[2] = {0}; // Set base addresses
|
uint8_t basebuf[2] = {0}; // Set base addresses
|
||||||
executeOpcode(OP_BUFFER_BASE_ADDR_6X, basebuf, 2);
|
executeOpcode(OP_BUFFER_BASE_ADDR_6X, basebuf, 2);
|
||||||
|
|
||||||
@@ -344,7 +397,22 @@ int sx126x::begin(long frequency) {
|
|||||||
setPacketParams(_preambleLength, _implicitHeaderMode, _payloadLength, _crcMode);
|
setPacketParams(_preambleLength, _implicitHeaderMode, _payloadLength, _crcMode);
|
||||||
|
|
||||||
#if HAS_LORA_PA
|
#if HAS_LORA_PA
|
||||||
#if LORA_PA_GC1109
|
if (lora_pa_model == LORA_PA_UNKNOWN) {
|
||||||
|
#if BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
|
|
||||||
|
pinMode(LORA_PA_PWR_EN, OUTPUT);
|
||||||
|
pinMode(LORA_PA_CSD, INPUT);
|
||||||
|
digitalWrite(LORA_PA_PWR_EN, HIGH); delay(5);
|
||||||
|
if (digitalRead(LORA_PA_CSD) == HIGH) {
|
||||||
|
lora_pa_model = LORA_PA_KCT8103L;
|
||||||
|
lora_lna_gain = LORA_LNA_KCT8103L_GAIN;
|
||||||
|
} else {
|
||||||
|
lora_pa_model = LORA_PA_GC1109;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lora_pa_model == LORA_PA_GC1109) {
|
||||||
// Enable Vfem_ctl for supply to
|
// Enable Vfem_ctl for supply to
|
||||||
// PA power net.
|
// PA power net.
|
||||||
pinMode(LORA_PA_PWR_EN, OUTPUT);
|
pinMode(LORA_PA_PWR_EN, OUTPUT);
|
||||||
@@ -369,7 +437,26 @@ int sx126x::begin(long frequency) {
|
|||||||
// is driven by the SX1262 DIO2
|
// is driven by the SX1262 DIO2
|
||||||
// pin directly, so we do not
|
// pin directly, so we do not
|
||||||
// need to manually raise this.
|
// need to manually raise this.
|
||||||
#endif
|
|
||||||
|
} else if (lora_pa_model == LORA_PA_KCT8103L) {
|
||||||
|
// Enable Vfem_ctl for supply to
|
||||||
|
// PA power net.
|
||||||
|
pinMode(LORA_PA_PWR_EN, OUTPUT);
|
||||||
|
digitalWrite(LORA_PA_PWR_EN, HIGH);
|
||||||
|
|
||||||
|
// Enable KCT8103L chip
|
||||||
|
pinMode(LORA_PA_CSD, OUTPUT);
|
||||||
|
digitalWrite(LORA_PA_CSD, HIGH);
|
||||||
|
|
||||||
|
// Enable receive LNA
|
||||||
|
pinMode(LORA_PA_CTX, OUTPUT);
|
||||||
|
digitalWrite(LORA_PA_CTX, LOW);
|
||||||
|
|
||||||
|
// On Heltec V4.3, the PA CPS pin
|
||||||
|
// is driven by the SX1262 DIO2
|
||||||
|
// pin directly, so we do not
|
||||||
|
// need to manually raise this.
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
@@ -379,14 +466,18 @@ void sx126x::end() { sleep(); SPI.end(); _preinit_done = false; }
|
|||||||
|
|
||||||
int sx126x::beginPacket(int implicitHeader) {
|
int sx126x::beginPacket(int implicitHeader) {
|
||||||
#if HAS_LORA_PA
|
#if HAS_LORA_PA
|
||||||
#if LORA_PA_GC1109
|
if (lora_pa_model == LORA_PA_GC1109) {
|
||||||
// Enable PA CPS for transmit
|
// Enable PA CPS for transmit
|
||||||
// digitalWrite(LORA_PA_CPS, HIGH);
|
// digitalWrite(LORA_PA_CPS, HIGH);
|
||||||
// Disabled since we're keeping it
|
// Disabled since we're keeping it
|
||||||
// on permanently as long as the
|
// on permanently as long as the
|
||||||
// radio is powered up.
|
// radio is powered up.
|
||||||
|
} else if (lora_pa_model == LORA_PA_KCT8103L) {
|
||||||
|
digitalWrite(LORA_PA_CTX, HIGH);
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
#endif
|
|
||||||
|
if (_txen != -1) { digitalWrite(_txen, HIGH); } //Set TXen high when transmitting
|
||||||
|
|
||||||
standby();
|
standby();
|
||||||
if (implicitHeader) { implicitHeaderMode(); }
|
if (implicitHeader) { implicitHeaderMode(); }
|
||||||
@@ -401,6 +492,9 @@ int sx126x::beginPacket(int implicitHeader) {
|
|||||||
|
|
||||||
int sx126x::endPacket() {
|
int sx126x::endPacket() {
|
||||||
setPacketParams(_preambleLength, _implicitHeaderMode, _payloadLength, _crcMode);
|
setPacketParams(_preambleLength, _implicitHeaderMode, _payloadLength, _crcMode);
|
||||||
|
|
||||||
|
if (_rxen != -1) { digitalWrite(_rxen, LOW); } //Set RXen low when transmitting
|
||||||
|
|
||||||
uint8_t timeout[3] = {0}; // Put in single TX mode
|
uint8_t timeout[3] = {0}; // Put in single TX mode
|
||||||
executeOpcode(OP_TX_6X, timeout, 3);
|
executeOpcode(OP_TX_6X, timeout, 3);
|
||||||
|
|
||||||
@@ -473,7 +567,7 @@ int ISR_VECT sx126x::currentRssi() {
|
|||||||
executeOpcodeRead(OP_CURRENT_RSSI_6X, &byte, 1);
|
executeOpcodeRead(OP_CURRENT_RSSI_6X, &byte, 1);
|
||||||
int rssi = -(int(byte)) / 2;
|
int rssi = -(int(byte)) / 2;
|
||||||
#if HAS_LORA_LNA
|
#if HAS_LORA_LNA
|
||||||
rssi -= LORA_LNA_GAIN;
|
rssi -= lora_lna_gain;
|
||||||
#endif
|
#endif
|
||||||
return rssi;
|
return rssi;
|
||||||
}
|
}
|
||||||
@@ -489,7 +583,7 @@ int ISR_VECT sx126x::packetRssi() {
|
|||||||
executeOpcodeRead(OP_PACKET_STATUS_6X, buf, 3);
|
executeOpcodeRead(OP_PACKET_STATUS_6X, buf, 3);
|
||||||
int pkt_rssi = -buf[0] / 2;
|
int pkt_rssi = -buf[0] / 2;
|
||||||
#if HAS_LORA_LNA
|
#if HAS_LORA_LNA
|
||||||
pkt_rssi -= LORA_LNA_GAIN;
|
pkt_rssi -= lora_lna_gain;
|
||||||
#endif
|
#endif
|
||||||
return pkt_rssi;
|
return pkt_rssi;
|
||||||
}
|
}
|
||||||
@@ -596,7 +690,7 @@ void sx126x::onReceive(void(*callback)(int)){
|
|||||||
|
|
||||||
void sx126x::receive(int size) {
|
void sx126x::receive(int size) {
|
||||||
#if HAS_LORA_PA
|
#if HAS_LORA_PA
|
||||||
#if LORA_PA_GC1109
|
if (lora_pa_model == LORA_PA_GC1109) {
|
||||||
// Disable PA CPS for receive
|
// Disable PA CPS for receive
|
||||||
// digitalWrite(LORA_PA_CPS, LOW);
|
// digitalWrite(LORA_PA_CPS, LOW);
|
||||||
// That turned out to be a bad idea.
|
// That turned out to be a bad idea.
|
||||||
@@ -604,7 +698,9 @@ void sx126x::receive(int size) {
|
|||||||
// on and off too quickly. We'll keep
|
// on and off too quickly. We'll keep
|
||||||
// it on permanently, as long as the
|
// it on permanently, as long as the
|
||||||
// radio is powered up.
|
// radio is powered up.
|
||||||
#endif
|
} else if (lora_pa_model == LORA_PA_KCT8103L) {
|
||||||
|
digitalWrite(LORA_PA_CTX, LOW);
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (size > 0) {
|
if (size > 0) {
|
||||||
@@ -643,6 +739,8 @@ void sx126x::enableTCXO() {
|
|||||||
uint8_t buf[4] = {MODE_TCXO_1_8V_6X, 0x00, 0x00, 0xFF};
|
uint8_t buf[4] = {MODE_TCXO_1_8V_6X, 0x00, 0x00, 0xFF};
|
||||||
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
#elif BOARD_MODEL == BOARD_HELTEC32_V4
|
||||||
uint8_t buf[4] = {MODE_TCXO_1_8V_6X, 0x00, 0x00, 0xFF};
|
uint8_t buf[4] = {MODE_TCXO_1_8V_6X, 0x00, 0x00, 0xFF};
|
||||||
|
#elif BOARD_MODEL == BOARD_MESHADVENTURER_S3
|
||||||
|
uint8_t buf[4] = {MODE_TCXO_1_8V_6X, 0x00, 0x00, 0xFF};
|
||||||
#endif
|
#endif
|
||||||
executeOpcode(OP_DIO3_TCXO_CTRL_6X, buf, 4);
|
executeOpcode(OP_DIO3_TCXO_CTRL_6X, buf, 4);
|
||||||
#endif
|
#endif
|
||||||
@@ -770,12 +868,13 @@ void sx126x::setSyncWord(uint16_t sw) {
|
|||||||
writeRegister(REG_SYNC_WORD_LSB_6X, 0x24);
|
writeRegister(REG_SYNC_WORD_LSB_6X, 0x24);
|
||||||
}
|
}
|
||||||
|
|
||||||
void sx126x::setPins(int ss, int reset, int dio0, int busy, int rxen) {
|
void sx126x::setPins(int ss, int reset, int dio0, int busy, int rxen, int txen) {
|
||||||
_ss = ss;
|
_ss = ss;
|
||||||
_reset = reset;
|
_reset = reset;
|
||||||
_dio0 = dio0;
|
_dio0 = dio0;
|
||||||
_busy = busy;
|
_busy = busy;
|
||||||
_rxen = rxen;
|
_rxen = rxen;
|
||||||
|
_txen = txen;
|
||||||
}
|
}
|
||||||
|
|
||||||
void sx126x::dumpRegisters(Stream& out) {
|
void sx126x::dumpRegisters(Stream& out) {
|
||||||
|
|||||||
10
sx126x.h
10
sx126x.h
@@ -74,6 +74,7 @@ public:
|
|||||||
void disableCrc();
|
void disableCrc();
|
||||||
void enableTCXO();
|
void enableTCXO();
|
||||||
void disableTCXO();
|
void disableTCXO();
|
||||||
|
void setDCDCRegulator();
|
||||||
|
|
||||||
void rxAntEnable();
|
void rxAntEnable();
|
||||||
void loraMode();
|
void loraMode();
|
||||||
@@ -92,11 +93,13 @@ public:
|
|||||||
|
|
||||||
byte random();
|
byte random();
|
||||||
|
|
||||||
void setPins(int ss = LORA_DEFAULT_SS_PIN, int reset = LORA_DEFAULT_RESET_PIN, int dio0 = LORA_DEFAULT_DIO0_PIN, int busy = LORA_DEFAULT_BUSY_PIN, int rxen = LORA_DEFAULT_RXEN_PIN);
|
void setPins(int ss = LORA_DEFAULT_SS_PIN, int reset = LORA_DEFAULT_RESET_PIN, int dio0 = LORA_DEFAULT_DIO0_PIN, int busy = LORA_DEFAULT_BUSY_PIN, int rxen = LORA_DEFAULT_RXEN_PIN, int txen = LORA_DEFAULT_TXEN_PIN);
|
||||||
void setSPIFrequency(uint32_t frequency);
|
void setSPIFrequency(uint32_t frequency);
|
||||||
|
|
||||||
void dumpRegisters(Stream& out);
|
void dumpRegisters(Stream& out);
|
||||||
|
|
||||||
|
bool isKCT8103L() { return _kct8103l; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void explicitHeaderMode();
|
void explicitHeaderMode();
|
||||||
void implicitHeaderMode();
|
void implicitHeaderMode();
|
||||||
@@ -107,7 +110,8 @@ public:
|
|||||||
// Poll for deferred DIO0 interrupt (call from main loop)
|
// Poll for deferred DIO0 interrupt (call from main loop)
|
||||||
void pollDio0();
|
void pollDio0();
|
||||||
|
|
||||||
private: uint8_t readRegister(uint16_t address);
|
private:
|
||||||
|
uint8_t readRegister(uint16_t address);
|
||||||
void writeRegister(uint16_t address, uint8_t value);
|
void writeRegister(uint16_t address, uint8_t value);
|
||||||
uint8_t singleTransfer(uint8_t opcode, uint16_t address, uint8_t value);
|
uint8_t singleTransfer(uint8_t opcode, uint16_t address, uint8_t value);
|
||||||
|
|
||||||
@@ -125,6 +129,7 @@ private:
|
|||||||
int _reset;
|
int _reset;
|
||||||
int _dio0;
|
int _dio0;
|
||||||
int _rxen;
|
int _rxen;
|
||||||
|
int _txen;
|
||||||
int _busy;
|
int _busy;
|
||||||
long _frequency;
|
long _frequency;
|
||||||
int _txp;
|
int _txp;
|
||||||
@@ -141,6 +146,7 @@ private:
|
|||||||
int _fifo_rx_addr_ptr;
|
int _fifo_rx_addr_ptr;
|
||||||
uint8_t _packet[255];
|
uint8_t _packet[255];
|
||||||
bool _preinit_done;
|
bool _preinit_done;
|
||||||
|
bool _kct8103l;
|
||||||
volatile bool _dio0_risen;
|
volatile bool _dio0_risen;
|
||||||
void (*_onReceive)(int);
|
void (*_onReceive)(int);
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user