diff --git a/companion/src/firmwares/edgetx/yaml_moduledata.cpp b/companion/src/firmwares/edgetx/yaml_moduledata.cpp index 8739843c0..588562bdf 100644 --- a/companion/src/firmwares/edgetx/yaml_moduledata.cpp +++ b/companion/src/firmwares/edgetx/yaml_moduledata.cpp @@ -48,6 +48,20 @@ // ghost: // raw12bits: 0 +// FRM303 (as of PR3501) +// type: TYPE_FLYSKY +// subType: AFHDS3 +// channelsStart: 0 +// channelsCount: 18 +// failsafeMode: NOT_SET +// mod: +// afhds3: +// emi: 2 +// telemetry: 1 +// phyMode: 2 +// reserved: 0 +// rfPower: 1 + static const YamlLookupTable protocolLut = { { PULSES_OFF, "TYPE_NONE" }, { PULSES_PPM, "TYPE_PPM" }, @@ -97,6 +111,11 @@ static const YamlLookupTable dsmLut = { { 2, "DSMX" }, }; +static const YamlLookupTable afhdsLut = { + { 0, "AFHDS3" }, + { 1, "AFHDS2A" } // could be complete nonsense, CHECK IT! +}; + static const YamlLookupTable failsafeLut = { { FAILSAFE_NOT_SET, "NOT_SET" }, { FAILSAFE_HOLD, "HOLD" }, @@ -156,6 +175,10 @@ Node convert::encode(const ModuleData& rhs) st_str += std::to_string(subType); node["subType"] = st_str; } break; + case PULSES_AFHDS3: { + node["subType"] = LookupValue(afhdsLut, subtype); + break; + } } node["channelsStart"] = rhs.channelsStart; @@ -223,7 +246,17 @@ Node convert::encode(const ModuleData& rhs) dsmp["flags"] = rhs.dsmp.flags; mod["dsmp"] = dsmp; } break; - // TODO: afhds3, flysky + // TODO: flysky + // TODO: afhds3 + case PULSES_AFHDS3: { + Node afhds3; + afhds3["emi"] = rhs.afhds3.emi; + afhds3["telemetry"] = rhs.afhds3.telemetry; + afhds3["phyMode"] = rhs.afhds3.phyMode; + afhds3["reserved"] = rhs.afhds3.reserved; + afhds3["rfPower"] = rhs.afhds3.rfPower; + mod["afhds3"] = afhds3; + } break; default: { Node ppm; ppm["delay"] = exportPpmDelay(rhs.ppm.delay); @@ -348,9 +381,15 @@ bool convert::decode(const Node& node, ModuleData& rhs) Node dsmp = mod["dsmp"]; dsmp["flags"] >> rhs.dsmp.flags; } else if (mod["flysky"]) { - //TODO + // TODO: flysky } else if (mod["afhds3"]) { - //TODO + // TODO: afhds3 + Node afhds3 = mod["afhds3"]; + afhds3["emi"] >> rhs.afhds3.emi; + afhds3["telemetry"] >> rhs.afhds3.telemetry; + afhds3["phyMode"] >> rhs.afhds3.phyMode; + afhds3["reserved"] >> rhs.afhds3.reserved; + afhds3["rfPower"] >> rhs.afhds3.rfPower; } } diff --git a/companion/src/firmwares/moduledata.h b/companion/src/firmwares/moduledata.h index a47ab2bb9..712221bd1 100644 --- a/companion/src/firmwares/moduledata.h +++ b/companion/src/firmwares/moduledata.h @@ -140,6 +140,10 @@ class ModuleData { struct Afhds3 { unsigned int rxFreq; unsigned int rfPower; + unsigned int emi; + unsigned int telemetry; + unsigned int phyMode; + unsigned int reserved; } afhds3; struct PXX { diff --git a/radio/src/datastructs_private.h b/radio/src/datastructs_private.h index 555fdc8d4..688aba4be 100644 --- a/radio/src/datastructs_private.h +++ b/radio/src/datastructs_private.h @@ -514,6 +514,7 @@ PACK(struct ModuleData { uint8_t telemetry:1; uint8_t phyMode:3; uint8_t reserved:2; + uint8_t rfPower; } afhds3); NOBACKUP(struct { uint8_t raw12bits:1; diff --git a/radio/src/gui/colorlcd/afhds3_options.cpp b/radio/src/gui/colorlcd/afhds3_options.cpp index 9598a310b..0376d79b4 100644 --- a/radio/src/gui/colorlcd/afhds3_options.cpp +++ b/radio/src/gui/colorlcd/afhds3_options.cpp @@ -80,7 +80,8 @@ PWMfrequencyChoice::PWMfrequencyChoice(Window* parent, uint8_t moduleIdx, uint8_ setFlexLayout(LV_FLEX_FLOW_ROW); lv_obj_set_width(lvobj, LV_SIZE_CONTENT); uint16_t &pwmvalue_type = _v1_pwmvalue_type[moduleIdx][channelIdx]; - auto vCfg = &afhds3::getConfig(moduleIdx)->v1; + auto cfg = afhds3::getConfig(moduleIdx); + auto vCfg = &cfg->v1; if( 0xff ==pwmvalue_type ) { if ( 50 == vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx] ) pwmvalue_type = 0; @@ -96,12 +97,14 @@ PWMfrequencyChoice::PWMfrequencyChoice(Window* parent, uint8_t moduleIdx, uint8_ [=,&pwmvalue_type](int32_t newValue) { pwmvalue_type=newValue; vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx] = _v1_index2pwmvalue[newValue]; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_FREQUENCY_V1); }); - auto num_edit = new NumberEdit(this, rect_t{}, 50, 400, - [=,&pwmvalue_type] { return (pwmvalue_type==4?vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx]:50); }, - [=](int16_t newVal) { - vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx] = newVal; - }); + auto num_edit = new NumberEdit(this, rect_t{}, 50, 400, + [=,&pwmvalue_type] { return (pwmvalue_type==4?vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx]:50); }, + [=](int16_t newVal) { + vCfg->PWMFrequenciesV1.PWMFrequencies[channelIdx] = newVal; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_FREQUENCY_V1); + }); c_obj = choice->getLvObj(); auto btn_obj = num_edit->getLvObj(); lv_obj_add_event_cb(c_obj, pwmfreq_changed, LV_EVENT_VALUE_CHANGED, btn_obj); @@ -114,7 +117,8 @@ PWMfrequencyChoice::PWMfrequencyChoice(Window* parent, uint8_t moduleIdx ) : setFlexLayout(LV_FLEX_FLOW_ROW); lv_obj_set_width(lvobj, LV_SIZE_CONTENT); uint16_t &pwmvalue_type = _v1_pwmvalue_type[moduleIdx][0]; - auto vCfg = &afhds3::getConfig(moduleIdx)->v0; + auto cfg = afhds3::getConfig(moduleIdx); + auto vCfg = &cfg->v0; if( 0xff ==pwmvalue_type ) { if ( 50 == (vCfg->PWMFrequency.Frequency&0x7fff) ) pwmvalue_type = 0; @@ -124,16 +128,18 @@ PWMfrequencyChoice::PWMfrequencyChoice(Window* parent, uint8_t moduleIdx ) : auto choice = new Choice(this, rect_t{}, _v0_pwmfreq_types, 0, 2, [=,&pwmvalue_type]{ return pwmvalue_type; - }, + }, [=,&pwmvalue_type](int32_t newValue) { pwmvalue_type=newValue; vCfg->PWMFrequency.Frequency = _v0_index2pwmvalue[newValue]; - }); - auto num_edit = new NumberEdit(this, rect_t{}, 50, 400, - [=,&pwmvalue_type] { return (pwmvalue_type==2?vCfg->PWMFrequency.Frequency&0x7fff:50); }, - [=](int16_t newVal) { - vCfg->PWMFrequency.Frequency = newVal; - }); + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_FREQUENCY_V0); + }); + auto num_edit = new NumberEdit(this, rect_t{}, 50, 400, + [=,&pwmvalue_type] { return (pwmvalue_type==2?vCfg->PWMFrequency.Frequency&0x7fff:50); }, + [=](int16_t newVal) { + vCfg->PWMFrequency.Frequency = newVal; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_FREQUENCY_V0); + }); c_obj = choice->getLvObj(); auto btn_obj = num_edit->getLvObj(); lv_obj_add_event_cb(c_obj, pwmfreq_changedV0, LV_EVENT_VALUE_CHANGED, btn_obj); @@ -145,8 +151,6 @@ void PWMfrequencyChoice::update() const lv_event_send(c_obj, LV_EVENT_VALUE_CHANGED, nullptr); } - - AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) { cfg = afhds3::getConfig(moduleIdx); @@ -179,7 +183,8 @@ AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) temp_str += " "; temp_str += STR_SYNC; new StaticText(line, rect_t{}, temp_str); - new CheckBox(line, rect_t{}, GET_SET_DEFAULT(vCfg->PWMFrequency.Synchronized)); + new CheckBox(line, rect_t{}, GET_SET_AND_SYNC(cfg, vCfg->PWMFrequency.Synchronized, + afhds3::DirtyConfig::DC_RX_CMD_FREQUENCY_V0)); line = form->newLine(&grid); temp_str = STR_CH; @@ -187,12 +192,12 @@ AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) new StaticText(line, rect_t{}, temp_str ); new Choice(line, rect_t{}, _analog_outputs, afhds3::SES_ANALOG_OUTPUT_PWM, afhds3::SES_ANALOG_OUTPUT_PPM, - GET_SET_DEFAULT(vCfg->AnalogOutput)); + GET_SET_AND_SYNC(cfg, vCfg->AnalogOutput, afhds3::DirtyConfig::DC_RX_CMD_OUT_PWM_PPM_MODE)); line = form->newLine(&grid); new StaticText(line, rect_t{}, STR_SERIAL_BUS); new Choice(line, rect_t{}, _bus_types, 0, 2, - GET_SET_DEFAULT(cfg->BusType.ExternalBusType)); + GET_SET_AND_SYNC(cfg, cfg->others.ExternalBusType, afhds3::DirtyConfig::DC_RX_CMD_BUS_TYPE_V0)); } else { auto vCfg = &cfg->v1; for (uint8_t i = 0; i < channel_num[vCfg->PhyMode]; i++) { @@ -212,6 +217,7 @@ AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) [=](uint8_t newVal) { vCfg->PWMFrequenciesV1.Synchronized &= ~(1<PWMFrequenciesV1.Synchronized |= (newVal?1:0)<NewPortTypes[i]), [=](int32_t newValue) { if(!newValue) + { vCfg->NewPortTypes[i] = newValue; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_PORT_TYPE_V1); + } else { uint8_t j = 0; for ( j = 0; j < SES_NPT_NB_MAX_PORTS; j++) { @@ -233,7 +242,11 @@ AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) break; } //The RX does not support two or more ports to output IBUS (the same is true for PPM and SBUS). - if(j==SES_NPT_NB_MAX_PORTS ) vCfg->NewPortTypes[i] = newValue; + if(j==SES_NPT_NB_MAX_PORTS ) + { + vCfg->NewPortTypes[i] = newValue; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_PORT_TYPE_V1); + } } }); } @@ -250,5 +263,8 @@ AFHDS3_Options::AFHDS3_Options(uint8_t moduleIdx) : Page(ICON_MODEL_SETUP) new Choice(line, rect_t{}, signed_strength_ch, 0, channel_num[cfg->v1.PhyMode], [=] { return cfg->v1.SignalStrengthRCChannelNb==0xff?0:cfg->v1.SignalStrengthRCChannelNb+1; }, - [=](int32_t newValue) { newValue?cfg->v1.SignalStrengthRCChannelNb = newValue-1:cfg->v1.SignalStrengthRCChannelNb=0xff;}); + [=](int32_t newValue) { + newValue?cfg->v1.SignalStrengthRCChannelNb = newValue-1:cfg->v1.SignalStrengthRCChannelNb=0xff; + DIRTY_CMD(cfg, afhds3::DirtyConfig::DC_RX_CMD_RSSI_CHANNEL_SETUP); + }); } diff --git a/radio/src/gui/colorlcd/flysky_settings.cpp b/radio/src/gui/colorlcd/flysky_settings.cpp index 923db157c..07025ba4d 100644 --- a/radio/src/gui/colorlcd/flysky_settings.cpp +++ b/radio/src/gui/colorlcd/flysky_settings.cpp @@ -28,6 +28,7 @@ #include "pulses/flysky.h" #include "pulses/afhds3.h" +#include "pulses/afhds3_config.h" #define SET_DIRTY() storageDirty(EE_MODEL) @@ -88,71 +89,170 @@ FlySkySettings::FlySkySettings(Window* parent, const FlexGridLayout& g, grid(g) { setFlexLayout(); + + FormGroup::Line* line; + +#if defined(AFHDS2) + // RX options: + line = newLine(&grid); + afhds2OptionsLabel = new StaticText(line, rect_t{}, STR_OPTIONS, 0, COLOR_THEME_PRIMARY1); + + afhds2ProtoOpts = new FSProtoOpts( + line, [=]() { return md->flysky.mode; }, + [=](uint8_t v) { md->flysky.mode = v; }); + +#if defined(PCBNV14) + if (getNV14RfFwVersion() >= 0x1000E) { + line = newLine(&grid); + static const char* _rf_power[] = {"Default", "High"}; + afhds2RFPowerText = new StaticText(line, rect_t{}, STR_MULTI_RFPOWER); + afhds2RFPowerChoice = new Choice(line, rect_t{}, _rf_power, 0, 1, + GET_DEFAULT(md->flysky.rfPower), + [=](int32_t newValue) -> void { + md->flysky.rfPower = newValue; + resetPulsesAFHDS2(); + }); +#endif + } + + hideAFHDS2Options(); +#endif + +#if defined(AFHDS3) + // Status + line = newLine(&grid); + afhds3StatusLabel = new StaticText(line, rect_t{}, STR_MODULE_STATUS, 0, COLOR_THEME_PRIMARY1); + afhds3StatusText = new DynamicText(line, rect_t{}, [=] { + char msg[64] = ""; + getModuleStatusString(moduleIdx, msg); + return std::string(msg); + }); + + // TYPE + line = newLine(&grid); + afhds3TypeLabel = new StaticText(line, rect_t{}, STR_TYPE, 0, COLOR_THEME_PRIMARY1); + + afhds3TypeForm = new FormGroup(line, rect_t{}); + afhds3TypeForm->setFlexLayout(LV_FLEX_FLOW_ROW_WRAP); + lv_obj_set_style_grid_cell_x_align(afhds3TypeForm->getLvObj(), LV_GRID_ALIGN_STRETCH, 0); + + afhds3PhyMode = new Choice(afhds3TypeForm, rect_t{}, _afhds3_phy_mode, 0, afhds3::PHYMODE_MAX, + GET_SET_DEFAULT(md->afhds3.phyMode)); + lv_obj_set_style_bg_color(afhds3PhyMode->getLvObj(), makeLvColor(COLOR_THEME_DISABLED), LV_PART_MAIN | LV_STATE_DISABLED); + + afhds3Emi = new Choice(afhds3TypeForm, rect_t{}, _afhds3_region, + afhds3::LNK_ES_CE, afhds3::LNK_ES_FCC, + GET_SET_DEFAULT(md->afhds3.emi)); + lv_obj_set_style_bg_color(afhds3Emi->getLvObj(), makeLvColor(COLOR_THEME_DISABLED), LV_PART_MAIN | LV_STATE_DISABLED); + + new TextButton(afhds3TypeForm, rect_t{}, STR_MODULE_OPTIONS, + [=]() { + afhds3::applyModelConfig(moduleIdx); + new AFHDS3_Options(moduleIdx); + return 0; + }); + + if (moduleIdx == EXTERNAL_MODULE) { + line = newLine(&grid); + auto cfg = afhds3::getConfig(moduleIdx); + new StaticText(line, rect_t{}, STR_MULTI_RFPOWER); + afhds3RfPower = new Choice(line, rect_t{}, STR_AFHDS3_POWERS, 0, AFHDS3_FRM303_POWER_MAX, + GET_DEFAULT(md->afhds3.rfPower), + [=](int32_t newValue) { md->afhds3.rfPower = newValue; + cfg->others.dirtyFlag |= (uint32_t) 1 << afhds3::DirtyConfig::DC_RX_CMD_TX_PWR; + SET_DIRTY();}); + } + + hideAFHDS3Options(); +#endif +} + +#if defined(AFHDS2) +void FlySkySettings::hideAFHDS2Options() +{ + lv_obj_add_flag(afhds2OptionsLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_add_flag(afhds2ProtoOpts->getLvObj(), LV_OBJ_FLAG_HIDDEN); +#if defined(PCBNV14) + if (afhds2RFPowerText != nullptr) + lv_obj_add_flag(afhds2RFPowerText->getLvObj(), LV_OBJ_FLAG_HIDDEN); + if (afhds2RFPowerChoice != nullptr) + lv_obj_add_flag(afhds2RFPowerChoice->getLvObj(), LV_OBJ_FLAG_HIDDEN); +#endif +} + +void FlySkySettings::showAFHDS2Options() +{ + lv_obj_clear_flag(afhds2OptionsLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_clear_flag(afhds2ProtoOpts->getLvObj(), LV_OBJ_FLAG_HIDDEN); +#if defined(PCBNV14) + if (afhds2RFPowerText != nullptr) + lv_obj_clear_flag(afhds2RFPowerText->getLvObj(), LV_OBJ_FLAG_HIDDEN); + if (afhds2RFPowerChoice != nullptr) + { + lv_obj_clear_flag(afhds2RFPowerChoice->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_event_send(afhds2RFPowerChoice->getLvObj(), LV_EVENT_VALUE_CHANGED, nullptr); + } +#endif +} +#endif + +#if defined(AFHDS3) +void FlySkySettings::hideAFHDS3Options() +{ + lv_obj_add_flag(afhds3StatusLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_add_flag(afhds3StatusText->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_add_flag(afhds3TypeLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_add_flag(afhds3TypeForm->getLvObj(), LV_OBJ_FLAG_HIDDEN); +} + +void FlySkySettings::showAFHDS3Options() +{ + lv_obj_clear_flag(afhds3StatusLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_clear_flag(afhds3StatusText->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_clear_flag(afhds3TypeLabel->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_obj_clear_flag(afhds3TypeForm->getLvObj(), LV_OBJ_FLAG_HIDDEN); + lv_event_send(afhds3StatusText->getLvObj(), LV_EVENT_VALUE_CHANGED, nullptr); + lv_event_send(afhds3PhyMode->getLvObj(), LV_EVENT_VALUE_CHANGED, nullptr); + lv_event_send(afhds3Emi->getLvObj(), LV_EVENT_VALUE_CHANGED, nullptr); + if (moduleIdx == EXTERNAL_MODULE) { + lv_event_send(afhds3RfPower->getLvObj(), LV_EVENT_VALUE_CHANGED, nullptr); + } + if (afhds3::getConfig(moduleIdx)->others.isConnected) + { + lv_obj_add_state(afhds3PhyMode->getLvObj(), LV_STATE_DISABLED); + lv_obj_add_state(afhds3Emi->getLvObj(), LV_STATE_DISABLED); + } + else + { + lv_obj_clear_state(afhds3PhyMode->getLvObj(), LV_STATE_DISABLED); + lv_obj_clear_state(afhds3Emi->getLvObj(), LV_STATE_DISABLED); + } +} +#endif + +void FlySkySettings::checkEvents() { + if (afhds3::getConfig(moduleIdx)->others.lastUpdated > lastRefresh) { + update(); + } + FormGroup::checkEvents(); } void FlySkySettings::update() { - clear(); - + lastRefresh = get_tmr10ms(); #if defined(AFHDS2) if (isModuleAFHDS2A(moduleIdx)) { - // RX options: - auto line = newLine(&grid); - new StaticText(line, rect_t{}, STR_OPTIONS, 0, COLOR_THEME_PRIMARY1); - - new FSProtoOpts( - line, [=]() { return md->flysky.mode; }, - [=](uint8_t v) { md->flysky.mode = v; }); - -#if defined(AFHDS2) && defined(PCBNV14) - if (getNV14RfFwVersion() >= 0x1000E) { - line = newLine(&grid); - static const char* _rf_power[] = {"Default", "High"}; - new StaticText(line, rect_t{}, STR_MULTI_RFPOWER); - new Choice(line, rect_t{}, _rf_power, 0, 1, - GET_DEFAULT(md->flysky.rfPower), - [=](int32_t newValue) -> void { - md->flysky.rfPower = newValue; - resetPulsesAFHDS2(); - }); - } -#endif + showAFHDS2Options(); + } else { + hideAFHDS2Options(); } #endif + #if defined(AFHDS3) if (isModuleAFHDS3(moduleIdx)) { - - // Status - auto line = newLine(&grid); - new StaticText(line, rect_t{}, STR_MODULE_STATUS, 0, COLOR_THEME_PRIMARY1); - new DynamicText(line, rect_t{}, [=] { - char msg[64] = ""; - getModuleStatusString(moduleIdx, msg); - return std::string(msg); - }); - - // TYPE - line = newLine(&grid); - new StaticText(line, rect_t{}, STR_TYPE, 0, COLOR_THEME_PRIMARY1); - - auto box = new FormGroup(line, rect_t{}); - box->setFlexLayout(LV_FLEX_FLOW_ROW_WRAP); - lv_obj_set_style_grid_cell_x_align(box->getLvObj(), LV_GRID_ALIGN_STRETCH, 0); - - new Choice(box, rect_t{}, _afhds3_phy_mode, 0, afhds3::PHYMODE_MAX, - GET_SET_DEFAULT(md->afhds3.phyMode)); - - new Choice(box, rect_t{}, _afhds3_region, - afhds3::LNK_ES_CE, afhds3::LNK_ES_FCC, - GET_SET_DEFAULT(md->afhds3.emi)); - - uint8_t module = moduleIdx; - new TextButton(box, rect_t{}, STR_MODULE_OPTIONS, - [=]() { - afhds3::applyModelConfig(module); - new AFHDS3_Options(module); - return 0; - }); + showAFHDS3Options(); + } else { + hideAFHDS3Options(); } #endif } diff --git a/radio/src/gui/colorlcd/flysky_settings.h b/radio/src/gui/colorlcd/flysky_settings.h index d4e346d7e..0b035a97e 100644 --- a/radio/src/gui/colorlcd/flysky_settings.h +++ b/radio/src/gui/colorlcd/flysky_settings.h @@ -22,6 +22,7 @@ #pragma once #include "form.h" +#include "choice.h" #include "module_setup.h" struct ModuleData; @@ -31,7 +32,32 @@ class FlySkySettings : public FormGroup, public ModuleOptions uint8_t moduleIdx; ModuleData* md; FlexGridLayout grid; + tmr10ms_t lastRefresh = 0; +#if defined(AFHDS2) + Window* afhds2OptionsLabel = nullptr; + Window* afhds2ProtoOpts = nullptr; +#if defined(PCBNV14) + Window* afhds2RFPowerText = nullptr; + Window* afhds2RFPowerChoice = nullptr; +#endif + void hideAFHDS2Options(); + void showAFHDS2Options(); +#endif + +#if defined(AFHDS3) + Window* afhds3StatusLabel = nullptr; + Window* afhds3StatusText = nullptr; + Window* afhds3TypeLabel = nullptr; + FormGroup* afhds3TypeForm = nullptr; + Choice *afhds3PhyMode = nullptr; + Choice *afhds3Emi = nullptr; + Choice *afhds3RfPower = nullptr; + void hideAFHDS3Options(); + void showAFHDS3Options(); +#endif + + void checkEvents() override; void update() override; public: diff --git a/radio/src/hal/module_port.h b/radio/src/hal/module_port.h index 80597179b..677852f70 100644 --- a/radio/src/hal/module_port.h +++ b/radio/src/hal/module_port.h @@ -145,10 +145,12 @@ inline uint8_t modulePortGetType(const etx_module_driver_t& d) { } inline const etx_serial_driver_t* modulePortGetSerialDrv(const etx_module_driver_t& d) { + if (d.port == nullptr) return nullptr; return d.port->drv.serial; } inline const etx_timer_driver_t* modulePortGetTimerDrv(const etx_module_driver_t& d) { + if (d.port == nullptr) return nullptr; return d.port->drv.timer; } diff --git a/radio/src/pulses/afhds3.cpp b/radio/src/pulses/afhds3.cpp index dee612f47..8c52328a0 100644 --- a/radio/src/pulses/afhds3.cpp +++ b/radio/src/pulses/afhds3.cpp @@ -33,11 +33,19 @@ #include "hal/module_driver.h" #include "hal/module_port.h" +#define SET_DIRTY() storageDirty(EE_MODEL) + +#define checkDirtyFlag(dirtyCmd) (cfg->others.dirtyFlag & ((uint32_t) 1 << dirtyCmd)) +#define clearDirtyFlag(dirtyCmd) (cfg->others.dirtyFlag &= ~((uint32_t) 1 << dirtyCmd)) + #define FAILSAFE_HOLD 1 #define FAILSAFE_CUSTOM 2 #define FAILSAFE_HOLD_VALUE 0x8000 #define FAILSAFE_NOPULSES_VALUE 0x8001 + +#define MAX_NO_OF_MODELS 20 + //get channel value outside of afhds3 namespace int32_t getChannelValue(uint8_t channel); void processFlySkyAFHDS3Sensor(const uint8_t * packet, uint8_t type); @@ -112,18 +120,18 @@ enum MODULE_READY_E { }; enum ModuleState { - STATE_NOT_READY = 0x00, // virtual + STATE_NOT_READY = 0x00, // virtual, module not ready STATE_HW_ERROR = 0x01, STATE_BINDING = 0x02, - STATE_SYNC_RUNNING = 0x03, - STATE_SYNC_DONE = 0x04, - STATE_STANDBY = 0x05, + STATE_SYNC_RUNNING = 0x03, // sync state, ready to sync settings, receiver not connected + STATE_SYNC_DONE = 0x04, // sync state, ready to sync settings, receiver connected + STATE_STANDBY = 0x05, // standby state, ready to update modelID, and switch to RUN mode STATE_UPDATING_WAIT = 0x06, STATE_UPDATING_MOD = 0x07, STATE_UPDATING_RX = 0x08, STATE_UPDATING_RX_FAILED = 0x09, STATE_RF_TESTING = 0x0a, - STATE_READY = 0x0b, // virtual + STATE_READY = 0x0b, // virtual, module ready awaiting to query module state STATE_HW_TEST = 0xff, }; @@ -270,7 +278,7 @@ class ProtoState bool syncSettings(); - void requestInfoAndRun(bool send = false); + // void requestInfoAndRun(bool send = false); uint8_t setFailSafe(int16_t* target, uint8_t rfchannelcount=AFHDS3_MAX_CHANNELS); @@ -295,8 +303,8 @@ class ProtoState */ ModuleState state; - bool modelIDSet; - bool modelcfgGet; + //bool modelIDSet; + //bool modelcfgGet; uint8_t modelID; uint32_t cmd_flg; /** @@ -347,9 +355,11 @@ static const COMMAND periodicRequestCommands[] = { COMMAND::MODULE_STATE, // COMMAND::MODULE_GET_CONFIG, - COMMAND::VIRTUAL_FAILSAFE + COMMAND::VIRTUAL_FAILSAFE // One way failsafe }; +static const uint16_t AFHDS3_POWER[] = {56, 68, 80, 96, 108, 120, 132}; + //Static collection of afhds3 object instances by module static ProtoState protoState[MAX_MODULES]; @@ -407,16 +417,13 @@ void ProtoState::setupFrame() if (this->state == ModuleState::STATE_NOT_READY) { TRACE("AFHDS3 [GET MODULE READY]"); - trsp.sendFrame(COMMAND::MODULE_READY, FRAME_TYPE::REQUEST_GET_DATA); + trsp.putFrame(COMMAND::MODULE_READY, FRAME_TYPE::REQUEST_GET_DATA); return; } - // process backlog + // Process backlog, not check states if (trsp.processQueue()) return; - // config should be loaded already - if (syncSettings()) { return; } - ::ModuleSettingsMode moduleMode = getModuleMode(module_index); if (moduleMode == ::ModuleSettingsMode::MODULE_MODE_BIND) { @@ -424,7 +431,7 @@ void ProtoState::setupFrame() TRACE("AFHDS3 [BIND]"); applyConfigFromModel(); - trsp.sendFrame(COMMAND::MODULE_SET_CONFIG, + trsp.putFrame(COMMAND::MODULE_SET_CONFIG, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, cfg.buffer, cfg.version == 0 ? sizeof(cfg.v0) : sizeof(cfg.v1)); @@ -438,51 +445,54 @@ void ProtoState::setupFrame() } else if (moduleMode == ::ModuleSettingsMode::MODULE_MODE_NORMAL) { - // if module is ready but not started + // If module is ready but not started if (this->state == ModuleState::STATE_READY) { - trsp.sendFrame(MODULE_STATE, FRAME_TYPE::REQUEST_GET_DATA); + trsp.putFrame(MODULE_STATE, FRAME_TYPE::REQUEST_GET_DATA); return; } - if (!modelIDSet) { + // ModelID change detection, if changed => STATE_STANDBY => Set ModelID => RUN mode => STATE_SYNC_XXX + uint8_t newModelID = g_model.header.modelId[module_index] % MAX_NO_OF_MODELS; // Rotate the model ID when exceed no. of stored models + if (modelID != newModelID) + { if (this->state != ModuleState::STATE_STANDBY) { + TRACE("AFHDS3 [Model ID Changed] Switch to STATE_STANDBY"); auto mode = (uint8_t)MODULE_MODE_E::STANDBY; - trsp.sendFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); + trsp.putFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); return; } else { - modelIDSet = true; - modelID = g_model.header.modelId[module_index]; - trsp.sendFrame(COMMAND::MODEL_ID, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, - &g_model.header.modelId[module_index], 1); + TRACE("AFHDS3 [Model ID Changed] Set ModelID to %d", newModelID); + modelID = newModelID; + trsp.putFrame(COMMAND::MODEL_ID, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, + &modelID, 1); return; } - } else if (modelID != g_model.header.modelId[module_index]) { - modelIDSet = false; - auto mode = (uint8_t)MODULE_MODE_E::STANDBY; - trsp.sendFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); - return; } - if (this->state == ModuleState::STATE_STANDBY) { + // If standby or exit bind => RUN mode => STATE_SYNC_XXX + if (this->state == ModuleState::STATE_STANDBY || this->state == ModuleState::STATE_BINDING) { cmdCount = 0; - requestInfoAndRun(true); +// requestInfoAndRun(true); + auto mode = (uint8_t)MODULE_MODE_E::RUN; + trsp.putFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); return; } - // exit bind - if (this->state == STATE_BINDING) { + // Exit bind +/* if (this->state == STATE_BINDING) { TRACE("AFHDS3 [EXIT BIND]"); - modelcfgGet = true; +// modelcfgGet = true; auto mode = (uint8_t)MODULE_MODE_E::RUN; - trsp.sendFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); + trsp.putFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); + trsp.enqueue(COMMAND::MODULE_GET_CONFIG, FRAME_TYPE::REQUEST_GET_DATA); return; - } + } */ } - if (modelcfgGet){ +/* if (modelcfgGet) { trsp.enqueue(COMMAND::MODULE_GET_CONFIG, FRAME_TYPE::REQUEST_GET_DATA); return; - } + }*/ if (cmdCount++ >= 150) { @@ -500,7 +510,7 @@ void ProtoState::setupFrame() ((AFHDS3_MAX_CHANNELS << 8) | CHANNELS_DATA_MODE::FAIL_SAFE), 0}; setFailSafe((int16_t*)(&failSafe[1]), len); TRACE("AFHDS ONE WAY FAILSAFE"); - trsp.sendFrame(COMMAND::CHANNELS_FAILSAFE_DATA, + trsp.putFrame(COMMAND::CHANNELS_FAILSAFE_DATA, FRAME_TYPE::REQUEST_SET_NO_RESP, (uint8_t*)failSafe, AFHDS3_MAX_CHANNELS * 2 + 2); return; @@ -510,23 +520,27 @@ void ProtoState::setupFrame() int16_t failSafe[18]; setFailSafe(&failSafe[0], len); std::memcpy( &data[3], failSafe, 2*len ); - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, 2*len+3); - return; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, 2*len+3); } } else { - trsp.sendFrame(cmd, FRAME_TYPE::REQUEST_GET_DATA); + trsp.putFrame(cmd, FRAME_TYPE::REQUEST_GET_DATA); return; } } if (isConnected()) { + // Sync config, with commands + if (syncSettings()) { return; } + + // Send channels data sendChannelsData(); } else { //default frame - request state - trsp.sendFrame(MODULE_STATE, FRAME_TYPE::REQUEST_GET_DATA); + trsp.putFrame(MODULE_STATE, FRAME_TYPE::REQUEST_GET_DATA); } } + void ProtoState::init(uint8_t moduleIndex, void* buffer, etx_module_state_t* mod_st, uint8_t fAddr) { @@ -536,7 +550,8 @@ void ProtoState::init(uint8_t moduleIndex, void* buffer, //clear local vars because it is member of union moduleData = &g_model.moduleData[module_index]; state = ModuleState::STATE_NOT_READY; - modelIDSet = false; + modelID = 0xff; // Valid range 0-19 +// modelIDSet = false; clearFrameData(); } @@ -563,6 +578,7 @@ void ProtoState::setState(ModuleState state) if (state == this->state) { return; } + uint8_t oldState = this->state; this->state = state; if (oldState == ModuleState::STATE_BINDING) { @@ -571,8 +587,26 @@ void ProtoState::setState(ModuleState state) if (state == ModuleState::STATE_NOT_READY) { trsp.clear(); } + else if (state == ModuleState::STATE_SYNC_RUNNING || state == ModuleState::STATE_SYNC_DONE) + { + // Get config when switched to STATE_SYNC_XXX + trsp.enqueue(COMMAND::MODULE_GET_CONFIG, FRAME_TYPE::REQUEST_GET_DATA); + + // Change connected state and refresh UI + cfg.others.isConnected = isConnected(); + cfg.others.lastUpdated = get_tmr10ms(); + cfg.others.dirtyFlag = 0U; + + if (state == ModuleState::STATE_SYNC_DONE) + { + // Update power config + TRACE("Added PWM CMD"); + DIRTY_CMD((&cfg), afhds3::DirtyConfig::DC_RX_CMD_TX_PWR); + } + } } +/* void ProtoState::requestInfoAndRun(bool send) { // set model ID @@ -584,7 +618,7 @@ void ProtoState::requestInfoAndRun(bool send) (uint8_t)MODULE_MODE_E::RUN); if (send) { trsp.processQueue(); } -} +}*/ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) { @@ -602,13 +636,17 @@ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) } break; case COMMAND::MODULE_GET_CONFIG: { - modelcfgGet = false; +// modelcfgGet = false; + TRACE("AFHDS3 [MODULE_GET_CONFIG]"); size_t len = min(sizeof(cfg.buffer), rxBufferCount); std::memcpy((void*) cfg.buffer, &responseFrame->value, len); moduleData->afhds3.emi = cfg.v0.EMIStandard; moduleData->afhds3.telemetry = cfg.v0.IsTwoWay; moduleData->afhds3.phyMode = cfg.v0.PhyMode; - cfg.BusType.ExternalBusType = cfg.v0.ExternalBusType; + cfg.others.ExternalBusType = cfg.v0.ExternalBusType; + TRACE("PhyMode %d, emi %d", moduleData->afhds3.phyMode, moduleData->afhds3.emi); + SET_DIRTY(); + cfg.others.lastUpdated = get_tmr10ms(); } break; case COMMAND::MODULE_VERSION: std::memcpy((void*) &version, &responseFrame->value, sizeof(version)); @@ -617,7 +655,7 @@ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) version.bootloaderVersion, version.firmwareVersion); break; case COMMAND::MODULE_STATE: - TRACE("AFHDS3 [MODULE_STATE] %02X", responseFrame->value); +// TRACE("AFHDS3 [MODULE_STATE] %02X", responseFrame->value); setState((ModuleState)responseFrame->value); if(STATE_SYNC_DONE == (ModuleState)responseFrame->value){ if(this->cmd_flg & 0x04) @@ -625,11 +663,16 @@ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) this->cmd_flg &= ~0x04; this->cmd_flg |= 0x02; trsp.enqueue(COMMAND::MODULE_VERSION, FRAME_TYPE::REQUEST_GET_DATA); +// modelcfgGet = true; +// cfg.others.isConnected = true; +// cfg.others.lastUpdated = get_tmr10ms(); } } else { - this->cmd_flg |= 0x04; + this->cmd_flg |= 0x04; +// cfg.others.isConnected = false; +// cfg.others.lastUpdated = get_tmr10ms(); } break; case COMMAND::MODULE_MODE: @@ -645,8 +688,12 @@ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) TRACE("AFHDS3 [MODULE_SET_CONFIG], %02X", responseFrame->value); break; case COMMAND::MODEL_ID: + TRACE("AFHDS3 [MODEL_ID]"); if (responseFrame->value == CMD_RESULT::SUCCESS) { - modelcfgGet = true; + TRACE("Enqueue get config"); +// trsp.enqueue(COMMAND::MODULE_GET_CONFIG, FRAME_TYPE::REQUEST_GET_DATA); +// trsp.enqueue(COMMAND::MODULE_GET_CONFIG, FRAME_TYPE::REQUEST_GET_DATA); +// modelcfgGet = true; } break; case COMMAND::TELEMETRY_DATA: @@ -674,34 +721,57 @@ void ProtoState::parseData(uint8_t* rxBuffer, uint8_t rxBufferCount) uint16_t cmd_code = *data++; cmd_code |= (*data++)<<8; uint8_t result = *data++; + auto *cfg = this->getConfig(); switch (cmd_code) { - case RX_CMD_GET_VERSION : - if(RX_CMDRESULT::RXSUCCESS==result) - { - if(14==*data++) - { - this->cmd_flg &= ~0x02; - std::memcpy((void*) &rx_version, data, sizeof(rx_version)); - this->cmd_flg |= 0x08; - } - }break; + case RX_CMD_RSSI_CHANNEL_SETUP: + if(RX_CMDRESULT::RXSUCCESS==result) { + clearDirtyFlag(DC_RX_CMD_RSSI_CHANNEL_SETUP); + } break; + case RX_CMD_OUT_PWM_PPM_MODE: + if(RX_CMDRESULT::RXSUCCESS==result) { + clearDirtyFlag(DC_RX_CMD_OUT_PWM_PPM_MODE); + } break; + case RX_CMD_FREQUENCY_V0: + if(RX_CMDRESULT::RXSUCCESS==result) { + clearDirtyFlag(DC_RX_CMD_FREQUENCY_V0); + } break; + case RX_CMD_PORT_TYPE_V1: + if(RX_CMDRESULT::RXSUCCESS==result) { + clearDirtyFlag(DC_RX_CMD_PORT_TYPE_V1); + } break; + case RX_CMD_FREQUENCY_V1: + if(RX_CMDRESULT::RXSUCCESS==result) { + if (checkDirtyFlag(DC_RX_CMD_FREQUENCY_V1)) { + clearDirtyFlag(DC_RX_CMD_FREQUENCY_V1); + } else { + clearDirtyFlag(DC_RX_CMD_FREQUENCY_V1_2); + } + } break; case RX_CMD_BUS_TYPE_V0: - if(RX_CMDRESULT::RXSUCCESS==result) - { + if(RX_CMDRESULT::RXSUCCESS==result) { this->cmd_flg &= ~0x28; - }break; + clearDirtyFlag(DC_RX_CMD_BUS_TYPE_V0); + } break; case RX_CMD_IBUS_DIRECTION: - if(RX_CMDRESULT::RXSUCCESS==*data++) - { + if(RX_CMDRESULT::RXSUCCESS==*data++) { this->cmd_flg &= ~0x10; - auto *cfg = this->getConfig(); if( 0==cfg->version && 2==cfg->v0.ExternalBusType) this->cmd_flg |= 0x20; }break; + case RX_CMD_GET_VERSION : + if(RX_CMDRESULT::RXSUCCESS==result) { + if(14==*data++) + { + this->cmd_flg &= ~0x02; + std::memcpy((void*) &rx_version, data, sizeof(rx_version)); + this->cmd_flg |= 0x08; + } + }break; default: break; } + TRACE("AFHDS3 [CMD Result] Cmd: %X, Result: %d, DirtyFlag: %X", cmd_code, result, cfg->others.dirtyFlag); } break; } } @@ -724,36 +794,34 @@ inline bool isPWM(uint8_t mode) bool ProtoState::syncSettings() { -if (this->state != ModuleState::STATE_SYNC_DONE) { - return false; - } + // Handles old receivers bug if(this->cmd_flg&0x02) { uint8_t data[] = { (uint8_t)(RX_CMD_GET_VERSION&0xFF), (uint8_t)((RX_CMD_GET_VERSION>>8)&0xFF), 0x00 }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); return true; } auto *cfg = this->getConfig(); if((this->cmd_flg&0x38) && (!cfg->version) ) { - uint8_t bustype = cfg->BusType.ExternalBusType<=1?0:2; - uint8_t busdir = cfg->BusType.ExternalBusType; + uint8_t bustype = cfg->others.ExternalBusType<=1?0:2; + uint8_t busdir = cfg->others.ExternalBusType; if( 1==receiver_type(rx_version.ProductNumber) ) { if(this->cmd_flg&0x08) { uint8_t data[] = { (uint8_t)(RX_CMD_BUS_TYPE_V0&0xFF), (uint8_t)((RX_CMD_BUS_TYPE_V0>>8)&0xFF), 0x1, bustype }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); if(busdir<2) this->cmd_flg |= 0x10; return true; } if((this->cmd_flg&0x10) && busdir<2) { - cfg->BusType.ExternalBusType = IBUS1_OUT; + cfg->others.ExternalBusType = IBUS1_OUT; busdir = IBUS1_OUT; uint8_t data1[] = { (uint8_t)(RX_CMD_IBUS_DIRECTION&0xFF), (uint8_t)((RX_CMD_IBUS_DIRECTION>>8)&0xFF), 0x1, busdir }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data1, sizeof(data1)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data1, sizeof(data1)); return true; } } @@ -762,7 +830,7 @@ if (this->state != ModuleState::STATE_SYNC_DONE) { if(this->cmd_flg&0x08) { uint8_t data[] = { (uint8_t)(RX_CMD_BUS_TYPE_V0&0xFF), (uint8_t)((RX_CMD_BUS_TYPE_V0>>8)&0xFF), 0x1, 0 }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); this->cmd_flg |= 0x10; return true; } @@ -770,17 +838,90 @@ if (this->state != ModuleState::STATE_SYNC_DONE) { { if(busdir>=2) busdir = 0; //IBUSOUT uint8_t data1[] = { (uint8_t)(RX_CMD_IBUS_DIRECTION&0xFF), (uint8_t)((RX_CMD_IBUS_DIRECTION>>8)&0xFF), 0x1, busdir }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data1, sizeof(data1)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data1, sizeof(data1)); return true; } else if((this->cmd_flg&0x20)) { uint8_t data[] = { (uint8_t)(RX_CMD_BUS_TYPE_V0&0xFF), (uint8_t)((RX_CMD_BUS_TYPE_V0>>8)&0xFF), 0x1, 2 }; - trsp.sendFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); return true; } } } + + // Sync settings when dirty flag is set + if (checkDirtyFlag(DC_RX_CMD_TX_PWR)) + { + TRACE("AFHDS3 [RX_CMD_TX_PWR] %d", AFHDS3_POWER[moduleData->afhds3.rfPower] / 4); + uint8_t data[] = { (uint8_t)(RX_CMD_TX_PWR&0xFF), (uint8_t)((RX_CMD_TX_PWR>>8)&0xFF), 2, + (uint8_t)(AFHDS3_POWER[moduleData->afhds3.rfPower]&0xFF), (uint8_t)((AFHDS3_POWER[moduleData->afhds3.rfPower]>>8)&0xFF)}; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + clearDirtyFlag(DC_RX_CMD_TX_PWR); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_RSSI_CHANNEL_SETUP)) + { + TRACE("AFHDS3 [RX_CMD_RSSI_CHANNEL_SETUP]"); + uint8_t data[] = { (uint8_t)(RX_CMD_RSSI_CHANNEL_SETUP&0xFF), (uint8_t)((RX_CMD_RSSI_CHANNEL_SETUP>>8)&0xFF), 1, cfg->v1.SignalStrengthRCChannelNb }; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_OUT_PWM_PPM_MODE)) + { + TRACE("AFHDS3 [RX_CMD_OUT_PWM_PPM_MODE]"); + uint8_t data[] = { (uint8_t)(RX_CMD_OUT_PWM_PPM_MODE&0xFF), (uint8_t)((RX_CMD_OUT_PWM_PPM_MODE>>8)&0xFF), 1, cfg->v0.AnalogOutput }; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_FREQUENCY_V0)) + { + TRACE("AFHDS3 [RX_CMD_FREQUENCY_V0]"); + uint8_t data[] = { (uint8_t)(RX_CMD_FREQUENCY_V0&0xFF), (uint8_t)((RX_CMD_FREQUENCY_V0>>8)&0xFF), 2, + (uint8_t)(cfg->v0.PWMFrequency.Frequency&0xFF), (uint8_t)((cfg->v0.PWMFrequency.Frequency>>8)&0xFF) }; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_PORT_TYPE_V1)) + { + TRACE("AFHDS3 [RX_CMD_PORT_TYPE_V1]"); + uint8_t data[] = { (uint8_t)(RX_CMD_PORT_TYPE_V1&0xFF), (uint8_t)((RX_CMD_PORT_TYPE_V1>>8)&0xFF), 4, 0, 0, 0, 0 }; + std::memcpy(&data[3], &cfg->v1.NewPortTypes, SES_NPT_NB_MAX_PORTS); + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_FREQUENCY_V1)) + { + TRACE("AFHDS3 [RX_CMD_FREQUENCY_V1]"); + uint8_t data[32 + 3 + 3] = { (uint8_t)(RX_CMD_FREQUENCY_V1&0xFF), (uint8_t)((RX_CMD_FREQUENCY_V1>>8)&0xFF), 32+3}; + data[3] = 0; + std::memcpy(&data[4], &cfg->v1.PWMFrequenciesV1.PWMFrequencies[0], 32); + data[36] = cfg->v1.PWMFrequenciesV1.Synchronized & 0xff; + data[37] = (cfg->v1.PWMFrequenciesV1.Synchronized>>8) & 0xff; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + DIRTY_CMD(cfg, DC_RX_CMD_FREQUENCY_V1_2); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_FREQUENCY_V1_2)) + { + TRACE("AFHDS3 [RX_CMD_FREQUENCY_V1_2]"); + uint8_t data[32 + 3 + 3] = { (uint8_t)(RX_CMD_FREQUENCY_V1_2&0xFF), (uint8_t)((RX_CMD_FREQUENCY_V1_2>>8)&0xFF), 32+3}; + data[3] = 1; + std::memcpy(&data[4], &cfg->v1.PWMFrequenciesV1.PWMFrequencies[16], 32); + data[36] = (cfg->v1.PWMFrequenciesV1.Synchronized>>16) & 0xff; + data[37] = (cfg->v1.PWMFrequenciesV1.Synchronized>>24) & 0xff; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + if (checkDirtyFlag(DC_RX_CMD_BUS_TYPE_V0)) + { + TRACE("AFHDS3 [RX_CMD_BUS_TYPE_V0]"); + uint8_t data[] = { (uint8_t)(RX_CMD_BUS_TYPE_V0&0xFF), (uint8_t)((RX_CMD_BUS_TYPE_V0>>8)&0xFF), 1, cfg->others.ExternalBusType }; + trsp.putFrame(COMMAND::SEND_COMMAND, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, data, sizeof(data)); + return true; + } + + // No need to sync return false; } @@ -804,7 +945,7 @@ void ProtoState::sendChannelsData() buffer[index] = channelValue; } - trsp.sendFrame(COMMAND::CHANNELS_FAILSAFE_DATA, FRAME_TYPE::REQUEST_SET_NO_RESP, + trsp.putFrame(COMMAND::CHANNELS_FAILSAFE_DATA, FRAME_TYPE::REQUEST_SET_NO_RESP, (uint8_t*)buffer, (channels + 1) * 2); } @@ -812,7 +953,7 @@ void ProtoState::stop() { TRACE("AFHDS3 STOP"); auto mode = (uint8_t)MODULE_MODE_E::STANDBY; - trsp.sendFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); + trsp.putFrame(COMMAND::MODULE_MODE, FRAME_TYPE::REQUEST_SET_EXPECT_DATA, &mode, 1); } void ProtoState::resetConfig(uint8_t version) @@ -835,6 +976,10 @@ void ProtoState::resetConfig(uint8_t version) void ProtoState::applyConfigFromModel() { uint8_t version = 0; +#if defined(SIMU) + // TODO: work out why this is not initialised in some cases + if (moduleData == nullptr) return; +#endif if (moduleData->afhds3.phyMode >= ROUTINE_FLCR1_18CH) { version = 1; } @@ -859,7 +1004,7 @@ void ProtoState::applyConfigFromModel() cfg.v0.EMIStandard = moduleData->afhds3.emi; cfg.v0.IsTwoWay = moduleData->afhds3.telemetry; cfg.v0.PhyMode = moduleData->afhds3.phyMode; - cfg.v0.ExternalBusType = cfg.BusType.ExternalBusType==1?0:cfg.BusType.ExternalBusType; + cfg.v0.ExternalBusType = cfg.others.ExternalBusType==1?0:cfg.others.ExternalBusType; // Failsafe setFailSafe(cfg.v0.FailSafe); if (moduleData->failsafeMode != FAILSAFE_NOPULSES) { diff --git a/radio/src/pulses/afhds3_config.h b/radio/src/pulses/afhds3_config.h index e7fb04d1d..40da44edd 100644 --- a/radio/src/pulses/afhds3_config.h +++ b/radio/src/pulses/afhds3_config.h @@ -80,6 +80,29 @@ enum eSES_NewPortType { SES_NPT_NONE=0xFF }; +enum DirtyConfig { + DC_RX_CMD_TX_PWR, + DC_RX_CMD_FAILSAFE_VALUE, + DC_RX_CMD_FAILSAFE_TIME, + DC_RX_CMD_RSSI_CHANNEL_SETUP, + DC_RX_CMD_RANGE, + DC_RX_CMD_GET_CAPABILITIES, + DC_RX_CMD_OUT_PWM_PPM_MODE, + DC_RX_CMD_FREQUENCY_V0, + DC_RX_CMD_PORT_TYPE_V1, + DC_RX_CMD_FREQUENCY_V1, + DC_RX_CMD_FREQUENCY_V1_2, + DC_RX_CMD_BUS_TYPE_V0, + DC_RX_CMD_IBUS_SETUP, + DC_RX_CMD_IBUS_DIRECTION, + DC_RX_CMD_BUS_FAILSAFE, + DC_RX_CMD_GET_VERSION +}; + +#define SET_AND_SYNC(cfg, value, dirtyCmd) [=](int32_t newValue) { value = newValue; cfg->others.dirtyFlag |= (uint32_t) 1 << dirtyCmd; } +#define GET_SET_AND_SYNC(cfg, value, dirtyCmd) GET_DEFAULT(value), SET_AND_SYNC(cfg, value, dirtyCmd) +#define DIRTY_CMD(cfg, dirtyCmd) cfg->others.dirtyFlag |= (uint32_t) 1 << dirtyCmd; + PACK(struct sSES_PWMFrequenciesAPPV1 { // One unsigned short per // channel, From 50 to 400Hz, @@ -104,9 +127,12 @@ PACK(struct sDATA_ConfigV1 { sSES_PWMFrequenciesAPPV1 PWMFrequenciesV1; }); -PACK(struct sDATA_BusType { +PACK(struct sDATA_Others { uint8_t buffer[sizeof(sDATA_ConfigV1)]; - uint8_t ExternalBusType; // eEB_BusType + uint8_t ExternalBusType; // eEB_BusType + tmr10ms_t lastUpdated; // last updated time + bool isConnected; // specify if receiver is connected + uint32_t dirtyFlag; // mapped to commands that need to be issued to sync settings }); union Config_u @@ -115,7 +141,7 @@ union Config_u sDATA_ConfigV0 v0; sDATA_ConfigV1 v1; uint8_t buffer[sizeof(sDATA_ConfigV1)]; - sDATA_BusType BusType; + sDATA_Others others; }; Config_u* getConfig(uint8_t moduleIdx); diff --git a/radio/src/pulses/afhds3_transport.cpp b/radio/src/pulses/afhds3_transport.cpp index 2442dfa65..8647ed926 100644 --- a/radio/src/pulses/afhds3_transport.cpp +++ b/radio/src/pulses/afhds3_transport.cpp @@ -67,7 +67,7 @@ void FrameTransport::clear() esc_state = 0; } -void FrameTransport::sendByte(uint8_t b) +void FrameTransport::putByte(uint8_t b) { *(data_ptr++) = b; } @@ -78,15 +78,15 @@ void FrameTransport::putBytes(uint8_t* data, int length) uint8_t byte = data[i]; crc += byte; if (END == byte) { - sendByte(ESC); - sendByte(ESC_END); + putByte(ESC); + putByte(ESC_END); } else if (ESC == byte) { - sendByte(ESC); - sendByte(ESC_ESC); + putByte(ESC); + putByte(ESC_ESC); } else { - sendByte(byte); + putByte(byte); } } } @@ -99,7 +99,7 @@ void FrameTransport::putFrame(COMMAND command, FRAME_TYPE frameType, data_ptr = trsp_buffer; crc = 0; - sendByte(START); + putByte(START); uint8_t buffer[] = {frameAddress, frameIndex, frameType, command}; putBytes(buffer, 4); @@ -112,7 +112,7 @@ void FrameTransport::putFrame(COMMAND command, FRAME_TYPE frameType, // footer uint8_t crcValue = crc ^ 0xff; putBytes(&crcValue, 1); - sendByte(END); + putByte(END); } uint32_t FrameTransport::getFrameSize() @@ -236,7 +236,7 @@ void Transport::clear() operationState = State::UNKNOWN; } -void Transport::sendFrame(COMMAND command, FRAME_TYPE frameType, uint8_t* data, +void Transport::putFrame(COMMAND command, FRAME_TYPE frameType, uint8_t* data, uint8_t dataLength) { operationState = State::SENDING_COMMAND; @@ -264,9 +264,11 @@ void Transport::enqueue(COMMAND command, FRAME_TYPE frameType, bool useData, void Transport::sendBuffer() { +#if !defined(SIMU) auto drv = modulePortGetSerialDrv(mod_st->tx); auto ctx = modulePortGetCtx(mod_st->tx); drv->sendBuffer(ctx, (uint8_t*)trsp.trsp_buffer, trsp.getFrameSize()); +#endif } bool Transport::processQueue() diff --git a/radio/src/pulses/afhds3_transport.h b/radio/src/pulses/afhds3_transport.h index 3a02aef22..e562f13b8 100644 --- a/radio/src/pulses/afhds3_transport.h +++ b/radio/src/pulses/afhds3_transport.h @@ -54,10 +54,11 @@ enum COMMAND : uint8_t { UNDEFINED = 0xFF }; -#define RX_CMD_RANGE ( 0x7013 ) +#define RX_CMD_TX_PWR ( 0x2013 ) #define RX_CMD_FAILSAFE_VALUE ( 0x6011 ) #define RX_CMD_FAILSAFE_TIME ( 0x6012 ) #define RX_CMD_RSSI_CHANNEL_SETUP ( 0x602B ) +#define RX_CMD_RANGE ( 0x7013 ) #define RX_CMD_GET_CAPABILITIES ( 0x7015 ) #define RX_CMD_OUT_PWM_PPM_MODE ( 0x7016 ) //PWM or PPM #define RX_CMD_FREQUENCY_V0 ( 0x7017 ) @@ -149,7 +150,7 @@ struct FrameTransport { void init(void* buffer, uint8_t fAddr); void clear(); - void sendByte(uint8_t b); + void putByte(uint8_t b); void putBytes(uint8_t* data, int length); void putFrame(COMMAND command, FRAME_TYPE frameType, uint8_t* data, @@ -195,7 +196,7 @@ class Transport void clear(); - void sendFrame(COMMAND command, FRAME_TYPE frameType, uint8_t* data = nullptr, + void putFrame(COMMAND command, FRAME_TYPE frameType, uint8_t* data = nullptr, uint8_t dataLength = 0); void enqueue(COMMAND command, FRAME_TYPE frameType, bool useData = false, diff --git a/radio/src/pulses/modules_constants.h b/radio/src/pulses/modules_constants.h index 4c177927e..a9aba6294 100644 --- a/radio/src/pulses/modules_constants.h +++ b/radio/src/pulses/modules_constants.h @@ -87,6 +87,17 @@ enum R9MLBTPowerValues { R9M_LBT_POWER_MAX = R9M_LBT_POWER_500_16CH_NOTELEM }; +enum AFHDS3PowerValues { + AFHDS3_POWER_25 = 0, + AFHDS3_POWER_50, + AFHDS3_POWER_100, + AFHDS3_POWER_250, + AFHDS3_POWER_500, + AFHDS3_POWER_1000, + AFHDS3_POWER_2000, + AFHDS3_FRM303_POWER_MAX = AFHDS3_POWER_2000, +}; + enum AntennaTypes { XJT_INTERNAL_ANTENNA = 0, XJT_EXTERNAL_ANTENNA diff --git a/radio/src/storage/yaml/yaml_datastructs_boxer.cpp b/radio/src/storage/yaml/yaml_datastructs_boxer.cpp index 13911880b..fccdafaa8 100644 --- a/radio/src/storage/yaml/yaml_datastructs_boxer.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_boxer.cpp @@ -663,6 +663,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -687,7 +688,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_lr3pro.cpp b/radio/src/storage/yaml/yaml_datastructs_lr3pro.cpp index 5b15ea139..64acd6958 100644 --- a/radio/src/storage/yaml/yaml_datastructs_lr3pro.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_lr3pro.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_nv14.cpp b/radio/src/storage/yaml/yaml_datastructs_nv14.cpp index a40f11c8d..779669bff 100644 --- a/radio/src/storage/yaml/yaml_datastructs_nv14.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_nv14.cpp @@ -698,6 +698,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -722,7 +723,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_t12.cpp b/radio/src/storage/yaml/yaml_datastructs_t12.cpp index d001b282c..afdfd8a95 100644 --- a/radio/src/storage/yaml/yaml_datastructs_t12.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_t12.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_t8.cpp b/radio/src/storage/yaml/yaml_datastructs_t8.cpp index 5b15ea139..64acd6958 100644 --- a/radio/src/storage/yaml/yaml_datastructs_t8.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_t8.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_tlite.cpp b/radio/src/storage/yaml/yaml_datastructs_tlite.cpp index 5b15ea139..64acd6958 100644 --- a/radio/src/storage/yaml/yaml_datastructs_tlite.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_tlite.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_tpro.cpp b/radio/src/storage/yaml/yaml_datastructs_tpro.cpp index 3b2ef0ab8..0bba48ce7 100644 --- a/radio/src/storage/yaml/yaml_datastructs_tpro.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_tpro.cpp @@ -668,6 +668,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -692,7 +693,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_tx12.cpp b/radio/src/storage/yaml/yaml_datastructs_tx12.cpp index 9c8de8b26..731459f2c 100644 --- a/radio/src/storage/yaml/yaml_datastructs_tx12.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_tx12.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_tx12mk2.cpp b/radio/src/storage/yaml/yaml_datastructs_tx12mk2.cpp index 6fdb56524..0918d6f2e 100755 --- a/radio/src/storage/yaml/yaml_datastructs_tx12mk2.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_tx12mk2.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x10.cpp b/radio/src/storage/yaml/yaml_datastructs_x10.cpp index 8772e70df..d776b82d8 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x10.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x10.cpp @@ -729,6 +729,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -753,7 +754,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x12s.cpp b/radio/src/storage/yaml/yaml_datastructs_x12s.cpp index 513a41b80..4dd1085a8 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x12s.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x12s.cpp @@ -727,6 +727,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -751,7 +752,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x7.cpp b/radio/src/storage/yaml/yaml_datastructs_x7.cpp index 5b15ea139..64acd6958 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x7.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x7.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x9d.cpp b/radio/src/storage/yaml/yaml_datastructs_x9d.cpp index 51e214d85..4bef7243c 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x9d.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x9d.cpp @@ -670,6 +670,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -694,7 +695,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x9e.cpp b/radio/src/storage/yaml/yaml_datastructs_x9e.cpp index 9429640fb..6b4941346 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x9e.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x9e.cpp @@ -709,6 +709,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -733,7 +734,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x9lite.cpp b/radio/src/storage/yaml/yaml_datastructs_x9lite.cpp index 8d086e763..7bb91b9f3 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x9lite.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x9lite.cpp @@ -647,6 +647,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -671,7 +672,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_x9lites.cpp b/radio/src/storage/yaml/yaml_datastructs_x9lites.cpp index 23d13ecd8..b33ff4bb1 100644 --- a/radio/src/storage/yaml/yaml_datastructs_x9lites.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_x9lites.cpp @@ -657,6 +657,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -681,7 +682,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_xlite.cpp b/radio/src/storage/yaml/yaml_datastructs_xlite.cpp index 29f7c5dd8..506b14fc0 100644 --- a/radio/src/storage/yaml/yaml_datastructs_xlite.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_xlite.cpp @@ -654,6 +654,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -678,7 +679,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_xlites.cpp b/radio/src/storage/yaml/yaml_datastructs_xlites.cpp index 2e2e366be..204c0e353 100644 --- a/radio/src/storage/yaml/yaml_datastructs_xlites.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_xlites.cpp @@ -658,6 +658,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -682,7 +683,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/storage/yaml/yaml_datastructs_zorro.cpp b/radio/src/storage/yaml/yaml_datastructs_zorro.cpp index 6fdb56524..0918d6f2e 100644 --- a/radio/src/storage/yaml/yaml_datastructs_zorro.cpp +++ b/radio/src/storage/yaml/yaml_datastructs_zorro.cpp @@ -662,6 +662,7 @@ static const struct YamlNode struct_anonymous_10[] = { YAML_UNSIGNED( "telemetry", 1 ), YAML_UNSIGNED( "phyMode", 3 ), YAML_UNSIGNED( "reserved", 2 ), + YAML_UNSIGNED( "rfPower", 8 ), YAML_END }; static const struct YamlNode struct_anonymous_11[] = { @@ -686,7 +687,7 @@ static const struct YamlNode union_anonymous_4_elmts[] = { YAML_STRUCT("sbus", 16, struct_anonymous_7, NULL), YAML_STRUCT("pxx2", 200, struct_anonymous_8, NULL), YAML_STRUCT("flysky", 56, struct_anonymous_9, NULL), - YAML_STRUCT("afhds3", 8, struct_anonymous_10, NULL), + YAML_STRUCT("afhds3", 16, struct_anonymous_10, NULL), YAML_STRUCT("ghost", 8, struct_anonymous_11, NULL), YAML_STRUCT("crsf", 8, struct_anonymous_12, NULL), YAML_STRUCT("dsmp", 8, struct_anonymous_13, NULL), diff --git a/radio/src/telemetry/flysky_ibus.cpp b/radio/src/telemetry/flysky_ibus.cpp index cf885e1c0..e78fd7d57 100644 --- a/radio/src/telemetry/flysky_ibus.cpp +++ b/radio/src/telemetry/flysky_ibus.cpp @@ -58,6 +58,8 @@ enum SENSOR_TYPE_RF_MODULE = 0x56, // Ext flysky rf module sensor(voltage and temperature) SENSOR_TYPE_RF_MODULE_TEMP = 0x1056, // virtual SENSOR_TYPE_RF_MODULE_VOL = 0x2056, // virtual + SENSOR_TYPE_RF_MODULE_POWER = 0x3056, // virtual +// SENSOR_TYPE_RF_MODULE_RAW = 0x4056, // virtual SENSOR_TYPE_TX_V = 0x7F, // TX Voltage @@ -156,6 +158,8 @@ const FlySkySensor flySkySensors[] = { { SENSOR_TYPE_ALT, STR_SENSOR_ALT, UNIT_METERS, 2 }, { SENSOR_TYPE_RF_MODULE_TEMP, STR_SENSOR_TEMP2, UNIT_CELSIUS, 0 }, // 1 bytes temperature { SENSOR_TYPE_RF_MODULE_VOL, STR_SENSOR_TXV, UNIT_VOLTS, 2 }, // 2 bytes voltage + { SENSOR_TYPE_RF_MODULE_POWER, STR_SENSOR_TX_POWER, UNIT_DBM, 0 }, // 2 bytes DBM +// { SENSOR_TYPE_RF_MODULE_RAW, STR_SENSOR_TX_POWER, UNIT_RAW, 0 }, // 2 bytes DBM { SENSOR_TYPE_TX_V, STR_SENSOR_TXV, UNIT_VOLTS, 2 }, // TX Voltage { SENSOR_TYPE_RX_SNR, STR_SENSOR_RX_SNR, UNIT_DB, 0 }, // RX SNR { SENSOR_TYPE_RX_NOISE, STR_SENSOR_RX_NOISE, UNIT_DBM, 0 }, // RX Noise @@ -232,8 +236,13 @@ void processFlySkyAFHDS3Sensor(const uint8_t * packet, uint8_t len ) { uint8_t data1[] = { (uint8_t)(SENSOR_TYPE_RF_MODULE_TEMP>>8), (uint8_t)SENSOR_TYPE_RF_MODULE_TEMP, id, packet[3] }; uint8_t data2[] = { (uint8_t)(SENSOR_TYPE_RF_MODULE_VOL>>8), (uint8_t)SENSOR_TYPE_RF_MODULE_VOL, id, packet[4], packet[5] }; + uint8_t data3[] = { (uint8_t)(SENSOR_TYPE_RF_MODULE_POWER>>8), (uint8_t)SENSOR_TYPE_RF_MODULE_POWER, id, packet[8], packet[9] }; +// uint8_t data4[] = { (uint8_t)(SENSOR_TYPE_RF_MODULE_RAW>>8), (uint8_t)SENSOR_TYPE_RF_MODULE_RAW, id, packet[6] & 0x07}; + processFlySkyAFHDS3Sensor(data1, 1 ); processFlySkyAFHDS3Sensor(data2, 2 ); + processFlySkyAFHDS3Sensor(data3, 2 ); +// processFlySkyAFHDS3Sensor(data4, 1 ); return; } else @@ -243,7 +252,7 @@ void processFlySkyAFHDS3Sensor(const uint8_t * packet, uint8_t len ) if (SENSOR_TYPE_RX_NOISE == type || SENSOR_TYPE_RX_RSSI == type) { value = -value; - } + } if ( (SENSOR_TYPE_EXT_VOL == type) ) { @@ -252,7 +261,7 @@ void processFlySkyAFHDS3Sensor(const uint8_t * packet, uint8_t len ) type = SENSOR_TYPE_BVD; } } - else if(SENSOR_TYPE_RX_RSSI == type || SENSOR_TYPE_RX_NOISE == type || SENSOR_TYPE_RX_SNR == type) + else if(SENSOR_TYPE_RX_RSSI == type || SENSOR_TYPE_RX_NOISE == type || SENSOR_TYPE_RX_SNR == type || SENSOR_TYPE_RF_MODULE_POWER == type) { if( value>=0 ) value = (value+2)/4; @@ -278,7 +287,7 @@ void processFlySkyAFHDS3Sensor(const uint8_t * packet, uint8_t len ) if(SENSOR_TYPE_TEMPERATURE == type) { - value -= 400;// Temperature sensors have 40 degree offset + value -= 400; // Temperature sensors have 40 degree offset } for (const FlySkySensor * sensor = flySkySensors; sensor->type; sensor++) diff --git a/radio/src/translations/untranslated.h b/radio/src/translations/untranslated.h index 0687e0f40..4f1148a95 100644 --- a/radio/src/translations/untranslated.h +++ b/radio/src/translations/untranslated.h @@ -147,7 +147,7 @@ #define TR_MULTI_WBUS_MODE "WBUS","PPM" #define TR_AFHDS3_PROTOCOLS "PWM/IBUS","PWM/SBUS","PPM/IBUS","PPM/SBUS" -#define TR_AFHDS3_POWERS "25 mW","100 mW","500 mW","1 W","2 W" +#define TR_AFHDS3_POWERS "25mW","50mW","100mW","250mW","500mW","1W","2W" #define TR_FLYSKY_PULSE_PROTO "PWM","PPM" #define TR_FLYSKY_SERIAL_PROTO "iBUS","SBUS" #define TR_PPM_POL "-","+"