From b50c977dc96e73de18c6cfaeaab0f663771ee9c2 Mon Sep 17 00:00:00 2001 From: pascallanger Date: Tue, 3 Dec 2019 16:46:12 +0100 Subject: [PATCH] Add TXRSSI and TXLQI sensors to FrSky D8/D16/LBT when using MULTI (#7128) Add TXRSSI and TXLQI sensors to FrSky D8/D16/LBT when using MULTI --- radio/src/gui/gui_common.cpp | 6 +- radio/src/pulses/modules_constants.h | 5 +- radio/src/telemetry/flysky_ibus.cpp | 10 ++-- radio/src/telemetry/frsky.h | 7 +++ radio/src/telemetry/frsky_d.cpp | 84 +++++++++++++++++---------- radio/src/telemetry/frsky_sport.cpp | 10 ++++ radio/src/telemetry/hitec.cpp | 12 ++-- radio/src/telemetry/hott.cpp | 28 ++++----- radio/src/translations/untranslated.h | 2 +- 9 files changed, 105 insertions(+), 59 deletions(-) diff --git a/radio/src/gui/gui_common.cpp b/radio/src/gui/gui_common.cpp index 9af725566..d3b826b28 100644 --- a/radio/src/gui/gui_common.cpp +++ b/radio/src/gui/gui_common.cpp @@ -856,6 +856,8 @@ const char STR_SUBTYPE_REDPINE[] = "\004""Fast""Slow"; const char STR_SUBTYPE_POTENSIC[] = "\003""A20"; const char STR_SUBTYPE_ZSX[] = "\007""280JJRC"; const char STR_SUBTYPE_FLYZONE[] = "\005""FZ410"; +const char STR_SUBTYPE_FX816[] = "\003""P38"; +const char STR_SUBTYPE_ESKY150[] = "\003""4CH""7CH"; const char* mm_options_strings::options[] = { nullptr, @@ -902,7 +904,6 @@ const mm_protocol_definition multi_protocols[] = { {MODULE_SUBTYPE_MULTI_BUGS_MINI, 1, false, false, STR_SUBTYPE_BUGS_MINI, nullptr}, {MODULE_SUBTYPE_MULTI_TRAXXAS, 0, false, false, STR_SUBTYPE_TRAXXAS, nullptr}, {MODULE_SUBTYPE_MULTI_E01X, 2, false, false, STR_SUBTYPE_E01X, STR_MULTI_OPTION}, - {MODULE_SUBTYPE_MULTI_V911S, 0, false, false, NO_SUBTYPE, STR_MULTI_RFTUNE}, {MODULE_SUBTYPE_MULTI_GD00X, 1, false, false, STR_SUBTYPE_GD00X, STR_MULTI_RFTUNE}, {MODULE_SUBTYPE_MULTI_KF606, 0, false, false, NO_SUBTYPE, STR_MULTI_RFTUNE}, {MODULE_SUBTYPE_MULTI_REDPINE, 1, false, false, STR_SUBTYPE_REDPINE, STR_MULTI_RFTUNE}, @@ -912,6 +913,9 @@ const mm_protocol_definition multi_protocols[] = { {MODULE_SUBTYPE_MULTI_FRSKYX_RX, 0, false, false, NO_SUBTYPE, STR_MULTI_RFTUNE}, {MODULE_SUBTYPE_MULTI_ESky, 0, false, true, NO_SUBTYPE, nullptr}, {MODULE_SUBTYPE_MULTI_J6PRO, 0, false, true, NO_SUBTYPE, nullptr}, + {MODULE_SUBTYPE_MULTI_ESKY150, 1, false, false, STR_SUBTYPE_ESKY150, nullptr}, + {MODULE_SUBTYPE_MULTI_FX816, 0, false, false, STR_SUBTYPE_FX816, nullptr}, + {MODULE_SUBTYPE_MULTI_HOTT, 0, true, false, NO_SUBTYPE, STR_MULTI_RFTUNE}, {MM_RF_CUSTOM_SELECTED, 7, true, true, NO_SUBTYPE, STR_MULTI_OPTION}, // Sentinel and default for protocols not listed above (MM_RF_CUSTOM is 0xff) diff --git a/radio/src/pulses/modules_constants.h b/radio/src/pulses/modules_constants.h index 05331d34f..ec0f8f819 100644 --- a/radio/src/pulses/modules_constants.h +++ b/radio/src/pulses/modules_constants.h @@ -155,9 +155,10 @@ enum ModuleSubtypeMulti { MODULE_SUBTYPE_MULTI_SCANNER, MODULE_SUBTYPE_MULTI_FRSKYX_RX, MODULE_SUBTYPE_MULTI_AFHDS2A_RX, - MODULE_SUBTYPE_MULTI_LAST = MODULE_SUBTYPE_MULTI_AFHDS2A_RX + MODULE_SUBTYPE_MULTI_HOTT, + MODULE_SUBTYPE_MULTI_FX816, + MODULE_SUBTYPE_MULTI_LAST = MODULE_SUBTYPE_MULTI_FX816 }; -#define MODULE_SUBTYPE_MULTI_HOTT 57-3 #define MODULE_SUBTYPE_MULTI_XN297DP 63-3 enum MMDSM2Subtypes { diff --git a/radio/src/telemetry/flysky_ibus.cpp b/radio/src/telemetry/flysky_ibus.cpp index 9074daa21..0869fb0da 100644 --- a/radio/src/telemetry/flysky_ibus.cpp +++ b/radio/src/telemetry/flysky_ibus.cpp @@ -88,10 +88,10 @@ enum AFHDS2A_ID_END = 0xFF, // AC type telemetry with multiple values in one packet - AFHDS2A_ID_GPS_FULL = 0xFD, + AFHDS2A_ID_GPS_FULL = 0xFD, AFHDS2A_ID_VOLT_FULL = 0xF0, AFHDS2A_ID_ACC_FULL = 0xEF, - TX_RSSI_ID = 0x200, // Pseudo id outside 1 byte range of FlySky sensors + AFHDS2A_ID_TX_RSSI = 0x200, // Pseudo id outside 1 byte range of FlySky sensors }; const FlySkySensor flySkySensors[] = { @@ -133,7 +133,7 @@ const FlySkySensor flySkySensors[] = { {AFHDS2A_ID_RX_NOISE, ZSTR_RX_NOISE, UNIT_DB, 0}, // RX Noise {AFHDS2A_ID_RX_RSSI, ZSTR_RSSI, UNIT_DB, 0}, // RX RSSI (0xfc) {AFHDS2A_ID_RX_ERR_RATE, ZSTR_RX_QUALITY, UNIT_RAW, 0}, // RX error rate - {TX_RSSI_ID, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo sensor for TRSSI + {AFHDS2A_ID_TX_RSSI, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo sensor for TRSSI {0x00, NULL, UNIT_RAW, 0}, // sentinel }; @@ -227,7 +227,7 @@ static void processFlySkySensor(const uint8_t * packet, uint8_t type) void processFlySkyPacket(const uint8_t * packet) { // Set TX RSSI Value, reverse MULTIs scaling - setTelemetryValue(PROTOCOL_TELEMETRY_FLYSKY_IBUS, TX_RSSI_ID, 0, 0, packet[0], UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_FLYSKY_IBUS, AFHDS2A_ID_TX_RSSI, 0, 0, packet[0], UNIT_RAW, 0); const uint8_t * buffer = packet + 1; int sesnor = 0; @@ -241,7 +241,7 @@ void processFlySkyPacket(const uint8_t * packet) void processFlySkyPacketAC(const uint8_t * packet) { // Set TX RSSI Value, reverse MULTIs scaling - setTelemetryValue(PROTOCOL_TELEMETRY_FLYSKY_IBUS, TX_RSSI_ID, 0, 0, packet[0], UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_FLYSKY_IBUS, AFHDS2A_ID_TX_RSSI, 0, 0, packet[0], UNIT_RAW, 0); const uint8_t * buffer = packet + 1; while (buffer - packet < 26) //28 + 1(multi TX rssi) - 3(ac header) { diff --git a/radio/src/telemetry/frsky.h b/radio/src/telemetry/frsky.h index b2248ec28..d4a9ab87a 100644 --- a/radio/src/telemetry/frsky.h +++ b/radio/src/telemetry/frsky.h @@ -189,6 +189,13 @@ enum FrSkyDataState { #define FUEL_QTY_FIRST_ID 0x0A10 #define FUEL_QTY_LAST_ID 0x0A1F +#if defined(MULTIMODULE) +// Virtual IDs, value can be changed to anything only used for display +#define RX_LQI_ID 0xFFFC +#define TX_LQI_ID 0xFFFD +#define TX_RSSI_ID 0xFFFE +#endif + // Default sensor data IDs (Physical IDs + CRC) #define DATA_ID_VARIO 0x00 // 0 #define DATA_ID_FLVSS 0xA1 // 1 diff --git a/radio/src/telemetry/frsky_d.cpp b/radio/src/telemetry/frsky_d.cpp index b46b93e11..67445c193 100644 --- a/radio/src/telemetry/frsky_d.cpp +++ b/radio/src/telemetry/frsky_d.cpp @@ -71,6 +71,13 @@ void frskyDProcessPacket(const uint8_t *packet) setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, D_A1_ID, 0, 0, packet[1], UNIT_VOLTS, 0); setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, D_A2_ID, 0, 0, packet[2], UNIT_VOLTS, 0); setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, D_RSSI_ID, 0, 0, packet[3], UNIT_RAW, 0); +#if defined(MULTIMODULE) + if (telemetryProtocol == PROTOCOL_TELEMETRY_MULTIMODULE) { + setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, TX_RSSI_ID, 0, 0, packet[4]>>1, UNIT_DB, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, RX_LQI_ID, 0, 0, packet[5] , UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_FRSKY_D, TX_LQI_ID , 0, 0, packet[6] , UNIT_RAW, 0); + } +#endif telemetryData.rssi.set(packet[3]); telemetryStreaming = TELEMETRY_TIMEOUT10ms; // reset counter only if valid packets are being detected break; @@ -263,42 +270,59 @@ void processHubPacket(uint8_t id, int16_t value) void frskyDSetDefault(int index, uint16_t id) { - TelemetrySensor & telemetrySensor = g_model.telemetrySensors[index]; + TelemetrySensor &telemetrySensor = g_model.telemetrySensors[index]; telemetrySensor.id = id; telemetrySensor.instance = 0; - const FrSkyDSensor * sensor = getFrSkyDSensor(id); - if (sensor) { - TelemetryUnit unit = sensor->unit; - uint8_t prec = min(2, sensor->prec); - telemetrySensor.init(sensor->name, unit, prec); - if (id == D_RSSI_ID) { - telemetrySensor.filter = 1; - telemetrySensor.logs = true; - } - else if (id >= D_A1_ID && id <= D_A2_ID) { - telemetrySensor.custom.ratio = 132; - telemetrySensor.filter = 1; - } - else if (id == CURRENT_ID) { - telemetrySensor.onlyPositive = 1; - } - else if (id == BARO_ALT_AP_ID) { - telemetrySensor.autoOffset = 1; - } - if (unit == UNIT_RPMS) { - telemetrySensor.custom.ratio = 1; - telemetrySensor.custom.offset = 1; - } - else if (unit == UNIT_METERS) { - if (IS_IMPERIAL_ENABLE()) { - telemetrySensor.unit = UNIT_FEET; +#if defined(MULTIMODULE) + if (id == TX_RSSI_ID) { + telemetrySensor.init(ZSTR_TX_RSSI, UNIT_DB, 0); + telemetrySensor.filter = 1; + } + else if (id == TX_LQI_ID) { + telemetrySensor.init(ZSTR_TX_QUALITY, UNIT_RAW, 0); + telemetrySensor.filter = 1; + } + else if (id == RX_LQI_ID) { + telemetrySensor.init(ZSTR_RX_QUALITY, UNIT_RAW, 0); + telemetrySensor.filter = 1; + } + else +#endif + { + const FrSkyDSensor * sensor = getFrSkyDSensor(id); + if (sensor) { + TelemetryUnit unit = sensor->unit; + uint8_t prec = min(2, sensor->prec); + telemetrySensor.init(sensor->name, unit, prec); + if (id == D_RSSI_ID) { + telemetrySensor.filter = 1; + telemetrySensor.logs = true; + } + else if (id >= D_A1_ID && id <= D_A2_ID) { + telemetrySensor.custom.ratio = 132; + telemetrySensor.filter = 1; + } + else if (id == CURRENT_ID) { + telemetrySensor.onlyPositive = 1; + } + else if (id == BARO_ALT_AP_ID) { + telemetrySensor.autoOffset = 1; + } + if (unit == UNIT_RPMS) { + telemetrySensor.custom.ratio = 1; + telemetrySensor.custom.offset = 1; + } + else if (unit == UNIT_METERS) { + if (IS_IMPERIAL_ENABLE()) { + telemetrySensor.unit = UNIT_FEET; + } } } - } - else { - telemetrySensor.init(id); + else { + telemetrySensor.init(id); + } } storageDirty(EE_MODEL); diff --git a/radio/src/telemetry/frsky_sport.cpp b/radio/src/telemetry/frsky_sport.cpp index 73c3ec324..d67da2559 100644 --- a/radio/src/telemetry/frsky_sport.cpp +++ b/radio/src/telemetry/frsky_sport.cpp @@ -31,6 +31,10 @@ struct FrSkySportSensor { const FrSkySportSensor sportSensors[] = { { RSSI_ID, RSSI_ID, 0, ZSTR_RSSI, UNIT_DB, 0 }, +#if defined(MULTIMODULE) + { TX_RSSI_ID, TX_RSSI_ID, 0, ZSTR_TX_RSSI , UNIT_DB , 0 }, + { TX_LQI_ID , TX_LQI_ID, 0, ZSTR_TX_QUALITY, UNIT_RAW, 0 }, +#endif { ADC1_ID, ADC1_ID, 0, ZSTR_A1, UNIT_VOLTS, 1 }, { ADC2_ID, ADC2_ID, 0, ZSTR_A2, UNIT_VOLTS, 1 }, { A3_FIRST_ID, A3_LAST_ID, 0, ZSTR_A3, UNIT_VOLTS, 2 }, @@ -192,6 +196,12 @@ void sportProcessTelemetryPacketWithoutCrc(uint8_t origin, const uint8_t * packe else { telemetryData.rssi.set(data); } +#if defined(MULTIMODULE) + if (telemetryProtocol == PROTOCOL_TELEMETRY_MULTIMODULE) { + sportProcessTelemetryPacket(TX_RSSI_ID, 0, instance, packet[5] >> 1, UNIT_DB); + sportProcessTelemetryPacket(TX_LQI_ID, 0, instance, packet[7], UNIT_RAW); + } +#endif } else if (dataId == R9_PWR_ID) { uint32_t r9pwr[] = {100, 200, 500, 1000}; diff --git a/radio/src/telemetry/hitec.cpp b/radio/src/telemetry/hitec.cpp index 93a0f6a37..3d4770b81 100644 --- a/radio/src/telemetry/hitec.cpp +++ b/radio/src/telemetry/hitec.cpp @@ -150,8 +150,8 @@ enum HITEC_ID_AIR_SPEED = 0x1A02, // Air speed HITEC_ID_VARIO = 0x1B00, // Vario HITEC_ID_ALT = 0x1B02, // Vario - TX_RSSI_ID = 0xFF00, // Pseudo id outside 1 byte range of Hitec sensors - TX_LQI_ID = 0xFF01, // Pseudo id outside 1 byte range of Hitec sensors + HITEC_ID_TX_RSSI = 0xFF00, // Pseudo id outside 1 byte range of Hitec sensors + HITEC_ID_TX_LQI = 0xFF01, // Pseudo id outside 1 byte range of Hitec sensors }; const HitecSensor hitecSensors[] = { @@ -193,8 +193,8 @@ const HitecSensor hitecSensors[] = { {HITEC_ID_VARIO, ZSTR_VSPD, UNIT_METERS_PER_SECOND, 1}, // Vario {HITEC_ID_ALT, ZSTR_ALT, UNIT_METERS, 1}, // Altitude - {TX_RSSI_ID, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hitec sensors - {TX_LQI_ID, ZSTR_TX_QUALITY, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hitec sensors// Pseudo sensor for TLQI + {HITEC_ID_TX_RSSI, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hitec sensors + {HITEC_ID_TX_LQI, ZSTR_TX_QUALITY, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hitec sensors// Pseudo sensor for TLQI {0x00, NULL, UNIT_RAW, 0}, // sentinel }; @@ -212,12 +212,12 @@ void processHitecPacket(const uint8_t * packet) static uint16_t rssi = 0, lqi = 0; // Set TX RSSI Value, reverse MULTIs scaling rssi = ((packet[0] * 10) + (rssi * 90)) / 100; // quick filtering - setTelemetryValue(PROTOCOL_TELEMETRY_HITEC, TX_RSSI_ID, 0, 0, rssi >> 1, UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HITEC, HITEC_ID_TX_RSSI, 0, 0, rssi >> 1, UNIT_RAW, 0); telemetryData.rssi.set(rssi >> 1); if (packet[0] > 0) telemetryStreaming = TELEMETRY_TIMEOUT10ms; // Set TX LQI Value, reverse MULTIs scaling lqi = ((packet[1] * 10) + (lqi * 90)) / 100; // quick filtering - setTelemetryValue(PROTOCOL_TELEMETRY_HITEC, TX_LQI_ID, 0, 0, lqi, UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HITEC, HITEC_ID_TX_LQI, 0, 0, lqi, UNIT_RAW, 0); const HitecSensor * sensor; int32_t value, deg, min, sec, alt, amp; diff --git a/radio/src/telemetry/hott.cpp b/radio/src/telemetry/hott.cpp index fab1fb555..f36236add 100644 --- a/radio/src/telemetry/hott.cpp +++ b/radio/src/telemetry/hott.cpp @@ -63,12 +63,12 @@ enum // telemetry sensors ID enum { - HOTT_ID_RX_VOLTAGE = 0x0004,// RX_Batt Voltage - HOTT_ID_TEMP1 = 0x0005, // RX Temperature sensor - TX_RSSI_ID = 0xFF00, // Pseudo id outside 1 byte range of Hott sensors - TX_LQI_ID = 0xFF01, // Pseudo id outside 1 byte range of Hott sensors - RX_RSSI_ID = 0xFF02, // Pseudo id outside 1 byte range of Hott sensors - RX_LQI_ID = 0xFF03, // Pseudo id outside 1 byte range of Hott sensors + HOTT_ID_RX_VOLTAGE = 0x0004, // RX_Batt Voltage + HOTT_ID_TEMP1 = 0x0005, // RX Temperature sensor + HOTT_TX_RSSI_ID = 0xFF00, // Pseudo id outside 1 byte range of Hott sensors + HOTT_TX_LQI_ID = 0xFF01, // Pseudo id outside 1 byte range of Hott sensors + HOTT_RX_RSSI_ID = 0xFF02, // Pseudo id outside 1 byte range of Hott sensors + HOTT_RX_LQI_ID = 0xFF03, // Pseudo id outside 1 byte range of Hott sensors }; const HottSensor hottSensors[] = { @@ -79,10 +79,10 @@ const HottSensor hottSensors[] = { //frame 02 //frame 03 //frame 04 - {TX_RSSI_ID, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hott sensors - {TX_LQI_ID, ZSTR_TX_QUALITY, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hott sensors - {RX_RSSI_ID, ZSTR_RSSI, UNIT_DB, 0}, // RX RSSI - {RX_LQI_ID, ZSTR_RX_QUALITY, UNIT_RAW, 0}, // RX LQI + {HOTT_TX_RSSI_ID, ZSTR_TX_RSSI, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hott sensors + {HOTT_TX_LQI_ID, ZSTR_TX_QUALITY, UNIT_RAW, 0}, // Pseudo id outside 1 byte range of Hott sensors + {HOTT_RX_RSSI_ID, ZSTR_RSSI, UNIT_DB, 0}, // RX RSSI + {HOTT_RX_LQI_ID, ZSTR_RX_QUALITY, UNIT_RAW, 0}, // RX LQI {0x00, NULL, UNIT_RAW, 0}, // sentinel }; @@ -98,9 +98,9 @@ const HottSensor * getHottSensor(uint16_t id) void processHottPacket(const uint8_t * packet) { // Set TX RSSI Value - setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, TX_RSSI_ID, 0, 0, packet[0]>>1, UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, HOTT_TX_RSSI_ID, 0, 0, packet[0]>>1, UNIT_RAW, 0); // Set TX LQI Value - setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, TX_LQI_ID, 0, 0, packet[1], UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, HOTT_TX_LQI_ID, 0, 0, packet[1], UNIT_RAW, 0); #if defined(LUA) #define HOTT_MENU_NBR_PAGE 0x13 @@ -142,12 +142,12 @@ void processHottPacket(const uint8_t * packet) sensor = getHottSensor(HOTT_ID_TEMP1); setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, HOTT_ID_TEMP1, 0, 0, value, sensor->unit, sensor->precision); // RX_RSSI - setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, RX_RSSI_ID, 0, 0, packet[7], UNIT_DB, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, HOTT_RX_RSSI_ID, 0, 0, packet[7], UNIT_DB, 0); // RX_LQI telemetryData.rssi.set(packet[8]); if (packet[8] > 0) telemetryStreaming = TELEMETRY_TIMEOUT10ms; - setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, RX_LQI_ID, 0, 0, packet[8], UNIT_RAW, 0); + setTelemetryValue(PROTOCOL_TELEMETRY_HOTT, HOTT_RX_LQI_ID, 0, 0, packet[8], UNIT_RAW, 0); break; default: diff --git a/radio/src/translations/untranslated.h b/radio/src/translations/untranslated.h index 95fc0c716..e5abaedf5 100644 --- a/radio/src/translations/untranslated.h +++ b/radio/src/translations/untranslated.h @@ -123,4 +123,4 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\007" -#define TR_MULTI_PROTOCOLS "FlySky\0""Hubsan\0""FrSky\0 ""Hisky\0 ""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0 ""KN\0 ""SymaX\0 ""SLT\0 ""CX10\0 ""CG023\0 ""Bayang\0""ESky\0 ""MT99XX\0""MJXq\0 ""Shenqi\0""FY326\0 ""SFHSS\0 ""J6 Pro\0""FQ777\0 ""Assan\0 ""Hontai\0""OpenLrs""FSky 2A""Q2x2\0 ""Walkera""Q303\0 ""GW008\0 ""DM002\0 ""Cabell\0""Esky150""H8 3D\0 ""Corona\0""CFlie\0 ""Hitec\0 ""WFly\0 ""Bugs\0 ""BugMini""Traxxas""NCC1701""E01X\0 ""V911S\0 ""GD00X\0 ""V761\0 ""KF606\0 ""Redpine""Potensi""ZSX\0 ""FlyZone""Scanner""FrSkyRX""FS2A_RX" +#define TR_MULTI_PROTOCOLS "FlySky\0""Hubsan\0""FrSky\0 ""Hisky\0 ""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0 ""KN\0 ""SymaX\0 ""SLT\0 ""CX10\0 ""CG023\0 ""Bayang\0""ESky\0 ""MT99XX\0""MJXq\0 ""Shenqi\0""FY326\0 ""SFHSS\0 ""J6 Pro\0""FQ777\0 ""Assan\0 ""Hontai\0""OpenLrs""FSky 2A""Q2x2\0 ""Walkera""Q303\0 ""GW008\0 ""DM002\0 ""Cabell\0""Esky150""H8 3D\0 ""Corona\0""CFlie\0 ""Hitec\0 ""WFly\0 ""Bugs\0 ""BugMini""Traxxas""NCC1701""E01X\0 ""V911S\0 ""GD00X\0 ""V761\0 ""KF606\0 ""Redpine""Potensi""ZSX\0 ""FlyZone""Scanner""FrSkyRX""FS2A_RX""HoTT\0 ""FX816\0 "