From 454144f46ca9a9e212a854054bacfe74e7d0fd5a Mon Sep 17 00:00:00 2001 From: Brian Webb Date: Sun, 6 May 2012 20:47:21 -0700 Subject: [PATCH] Pairing and saving settings working. --- .../Modules/RadioComBridge/RadioComBridge.c | 102 ++++++++++++++---- flight/PiOS/Common/pios_rfm22b.c | 17 ++- flight/PipXtreme/Makefile | 1 + flight/PipXtreme/System/pios_board.c | 68 +++++++++++- .../board_hw_defs/pipxtreme/board_hw_defs.c | 10 -- .../plugins/config/configpipxtremewidget.cpp | 37 ++++++- shared/uavobjectdefinition/pipxsettings.xml | 4 +- 7 files changed, 192 insertions(+), 47 deletions(-) mode change 100644 => 100755 ground/openpilotgcs/src/plugins/config/configpipxtremewidget.cpp diff --git a/flight/Modules/RadioComBridge/RadioComBridge.c b/flight/Modules/RadioComBridge/RadioComBridge.c index c55685f54..05dd08c52 100644 --- a/flight/Modules/RadioComBridge/RadioComBridge.c +++ b/flight/Modules/RadioComBridge/RadioComBridge.c @@ -40,6 +40,9 @@ #include #include #include +#if defined(PIOS_INCLUDE_FLASH_EEPROM) +#include +#endif #include @@ -54,7 +57,7 @@ #define REQ_TIMEOUT_MS 10 #define STATS_UPDATE_PERIOD_MS 2000 #define RADIOSTATS_UPDATE_PERIOD_MS 1000 -#define MAX_LOST_CONTACT_TIME 10 +#define MAX_LOST_CONTACT_TIME 4 #define PACKET_QUEUE_SIZE 10 #define MAX_PORT_DELAY 200 #define EV_PACKET_RECEIVED 0x20 @@ -182,6 +185,11 @@ static int32_t RadioComBridgeInitialize(void) // Initialize the UAVObjects that we use GCSReceiverInitialize(); PipXStatusInitialize(); + ObjectPersistenceInitialize(); + + // Get the settings. + PipXSettingsData pipxSettings; + PipXSettingsGet(&pipxSettings); // TODO: Get from settings object data->com_port = PIOS_COM_BRIDGE_COM; @@ -196,7 +204,8 @@ static int32_t RadioComBridgeInitialize(void) data->objEventQueue = xQueueCreate(PACKET_QUEUE_SIZE, sizeof(UAVObjEvent)); // Initialize the destination ID - data->destination_id = 0xffffffff; + data->destination_id = pipxSettings.PairID ? pipxSettings.PairID : 0xffffffff; + DEBUG_PRINTF(2, "PairID: %x\n\r", data->destination_id); // Initialize the statistics. data->radioTxErrors = 0; @@ -296,7 +305,8 @@ static void comUAVTalkTask(void *parameters) // Keep reading until we receive a completed packet. UAVTalkRxState state = UAVTalkProcessInputStreamQuiet(data->inUAVTalkCon, rx_byte); - UAVTalkInputProcessor *iproc = &(((UAVTalkConnectionData*)(data->inUAVTalkCon))->iproc); + UAVTalkConnectionData *connection = (UAVTalkConnectionData*)(data->inUAVTalkCon); + UAVTalkInputProcessor *iproc = &(connection->iproc); if (state == UAVTALK_STATE_COMPLETE) { // Is this a local UAVObject? @@ -305,19 +315,65 @@ static void comUAVTalkTask(void *parameters) // We treat the ObjectPersistance object differently if(iproc->objId == OBJECTPERSISTENCE_OBJID) { - // Queue the packet for transmission. - xQueueSend(data->sendPacketQueue, &p, MAX_PORT_DELAY); - p = NULL; + // Unpack object, if the instance does not exist it will be created! + UAVObjUnpack(iproc->obj, iproc->instId, connection->rxBuffer); + + // Get the ObjectPersistance object. + ObjectPersistenceData obj_per; + ObjectPersistenceGet(&obj_per); + + // Is this concerning or setting object? + if (obj_per.ObjectID == PIPXSETTINGS_OBJID) + { + UAVObjEvent ev; + ev.obj = iproc->obj; + ev.instId = 0; + ev.event = EV_SEND_ACK; + + // Is this a save, load, or delete? + switch (obj_per.Operation) + { + case OBJECTPERSISTENCE_OPERATION_LOAD: + DEBUG_PRINTF(2, "Load\n\r"); + break; + case OBJECTPERSISTENCE_OPERATION_SAVE: +#if defined(PIOS_INCLUDE_FLASH_EEPROM) + { + // Save the settings. + PipXSettingsData pipxSettings; + PipXSettingsGet(&pipxSettings); + if (PIOS_EEPROM_Save((uint8_t*)&pipxSettings, sizeof(PipXSettingsData)) != 0) + ev.event = EV_SEND_NACK; + break; + } +#endif + case OBJECTPERSISTENCE_OPERATION_DELETE: + DEBUG_PRINTF(2, "Delete\n\r"); + break; + default: + DEBUG_PRINTF(2, "Other\n\r"); + break; + } + + // Queue up the ACK/NACK + xQueueSend(data->objEventQueue, &ev, MAX_PORT_DELAY); + } + else { + // Otherwise, queue the packet for transmission. + xQueueSend(data->sendPacketQueue, &p, MAX_PORT_DELAY); + p = NULL; + } } else { UAVObjEvent ev; ev.obj = iproc->obj; + ev.instId = 0; switch (iproc->type) { case UAVTALK_TYPE_OBJ: // Unpack object, if the instance does not exist it will be created! - UAVObjUnpack(iproc->obj, iproc->instId, p->data); + UAVObjUnpack(iproc->obj, iproc->instId, connection->rxBuffer); break; case UAVTALK_TYPE_OBJ_REQ: // Queue up an object send request. @@ -327,7 +383,7 @@ static void comUAVTalkTask(void *parameters) case UAVTALK_TYPE_OBJ_ACK: // Queue up an ACK ev.event = EV_SEND_ACK; - xQueueSend(data->objEventQueue, &ev, MAX_PORT_DELAY); + UAVObjUnpack(iproc->obj, iproc->instId, connection->rxBuffer); break; } } @@ -582,6 +638,7 @@ static void radioStatusTask(void *parameters) { pipxStatus.PairIDs[i] = data->pairStats[i].pairID; pipxStatus.PairSignalStrengths[i] = data->pairStats[i].rssi; + data->pairStats[i].lastContact++; } // Update the object @@ -663,19 +720,21 @@ static void receiveData(uint8_t *buf, uint8_t len) static void StatusHandler(PHPacketHandle status) { uint32_t id = status->header.source_id; - + bool found = false; // Have we seen this device recently? uint8_t id_idx = 0; for ( ; id_idx < PIPXSTATUS_PAIRIDS_NUMELEM; ++id_idx) if(data->pairStats[id_idx].pairID == id) + { + found = true; break; + } // If we have seen it, update the RSSI and reset the last contact couter - if(id_idx < PIPXSTATUS_PAIRIDS_NUMELEM) + if(found) { data->pairStats[id_idx].rssi = status->header.rssi; data->pairStats[id_idx].lastContact = 0; - return; } // Remove any contacts that we haven't seen for a while. @@ -690,19 +749,22 @@ static void StatusHandler(PHPacketHandle status) } // If we haven't seen it, find a slot to put it in. - uint8_t min_idx = 0; - int8_t min_rssi = data->pairStats[0].rssi; - for (id_idx = 1; id_idx < PIPXSTATUS_PAIRIDS_NUMELEM; ++id_idx) + if (!found) { - if(data->pairStats[id_idx].rssi < min_rssi) + uint8_t min_idx = 0; + int8_t min_rssi = data->pairStats[0].rssi; + for (id_idx = 1; id_idx < PIPXSTATUS_PAIRIDS_NUMELEM; ++id_idx) { - min_rssi = data->pairStats[id_idx].rssi; - min_idx = id_idx; + if(data->pairStats[id_idx].rssi < min_rssi) + { + min_rssi = data->pairStats[id_idx].rssi; + min_idx = id_idx; + } } + data->pairStats[min_idx].pairID = id; + data->pairStats[min_idx].rssi = status->header.rssi; + data->pairStats[min_idx].lastContact = 0; } - data->pairStats[min_idx].pairID = id; - data->pairStats[min_idx].rssi = status->header.rssi; - data->pairStats[min_idx].lastContact = 0; } /** diff --git a/flight/PiOS/Common/pios_rfm22b.c b/flight/PiOS/Common/pios_rfm22b.c index 93c941be5..872ddbb96 100644 --- a/flight/PiOS/Common/pios_rfm22b.c +++ b/flight/PiOS/Common/pios_rfm22b.c @@ -152,7 +152,7 @@ enum pios_rfm22b_dev_magic { struct pios_rfm22b_dev { enum pios_rfm22b_dev_magic magic; - const struct pios_rfm22b_cfg *cfg; + struct pios_rfm22b_cfg cfg; uint32_t deviceID; @@ -448,7 +448,7 @@ int32_t PIOS_RFM22B_Init(uint32_t *rfm22b_id, const struct pios_rfm22b_cfg *cfg) return(-1); // Bind the configuration to the device instance - rfm22b_dev->cfg = cfg; + rfm22b_dev->cfg = *cfg; *rfm22b_id = (uint32_t)rfm22b_dev; @@ -853,7 +853,7 @@ void rfm22_setNominalCarrierFrequency(uint32_t frequency_hz) // ******* #if defined(RFM22_DEBUG) - DEBUG_PRINTF(2, "rf setFreq: %u\n\r", carrier_frequency_hz); + //DEBUG_PRINTF(2, "rf setFreq: %u\n\r", carrier_frequency_hz); // DEBUG_PRINTF(2, "rf setFreq frequency_step_size: %0.2f\n\r", frequency_step_size); #endif @@ -912,13 +912,6 @@ void rfm22_setDatarate(uint32_t datarate_bps, bool data_whitening) rf_bandwidth_used = rx_bandwidth[lookup_index]; - // ******************************** - -#if defined(RFM22_DEBUG) - uint32_t frequency_deviation = freq_deviation[lookup_index]; // Hz - uint32_t modulation_bandwidth = datarate_bps + (2 * frequency_deviation); -#endif - // rfm22_if_filter_bandwidth rfm22_write(0x1C, reg_1C[lookup_index]); @@ -1028,11 +1021,15 @@ void rfm22_setDatarate(uint32_t datarate_bps, bool data_whitening) // ******************************** #if defined(RFM22_DEBUG) +/* DEBUG_PRINTF(2, "rf datarate_bps: %d\n\r", datarate_bps); DEBUG_PRINTF(2, "rf frequency_deviation: %d\n\r", frequency_deviation); + uint32_t frequency_deviation = freq_deviation[lookup_index]; // Hz + uint32_t modulation_bandwidth = datarate_bps + (2 * frequency_deviation); DEBUG_PRINTF(2, "rf modulation_bandwidth: %u\n\r", modulation_bandwidth); DEBUG_PRINTF(2, "rf_rx_bandwidth[%u]: %u\n\r", lookup_index, rx_bandwidth[lookup_index]); DEBUG_PRINTF(2, "rf est rx sensitivity[%u]: %ddBm\n\r", lookup_index, est_rx_sens_dBm[lookup_index]); +*/ #endif // ******* diff --git a/flight/PipXtreme/Makefile b/flight/PipXtreme/Makefile index f9a99e4bc..3123cacc2 100755 --- a/flight/PipXtreme/Makefile +++ b/flight/PipXtreme/Makefile @@ -140,6 +140,7 @@ ifndef TESTAPP SRC += $(OPUAVSYNTHDIR)/gcsreceiver.c SRC += $(OPUAVSYNTHDIR)/pipxstatus.c SRC += $(OPUAVSYNTHDIR)/pipxsettings.c +SRC += $(OPUAVSYNTHDIR)/objectpersistence.c endif diff --git a/flight/PipXtreme/System/pios_board.c b/flight/PipXtreme/System/pios_board.c index 74933bb3d..da9954f26 100755 --- a/flight/PipXtreme/System/pios_board.c +++ b/flight/PipXtreme/System/pios_board.c @@ -214,12 +214,72 @@ void PIOS_Board_Init(void) { PIOS_Assert(0); } } - PIOS_COM_SendString(PIOS_COM_DEBUG, "Hello DEBUG\n\r"); - PIOS_COM_SendString(PIOS_COM_FLEXI, "Hello Flexi\n\r"); - PIOS_COM_SendString(PIOS_COM_TELEM_SERIAL, "Hello Telem Serial\n\r"); - PIOS_COM_SendString(PIOS_COM_VCP_USB, "Hello VCP\n\r"); #if defined(PIOS_INCLUDE_RFM22B) + struct pios_rfm22b_cfg pios_rfm22b_cfg = { + .frequencyHz = 434000000, + .minFrequencyHz = 434000000 - 2000000, + .maxFrequencyHz = 434000000 + 2000000, + .RFXtalCap = 0x7f, + .maxRFBandwidth = 128000, + .maxTxPower = RFM22_tx_pwr_txpow_7, // +20dBm .. 100mW + }; + + /* Retrieve hardware settings. */ + pios_rfm22b_cfg.frequencyHz = pipxSettings.Frequency; + pios_rfm22b_cfg.RFXtalCap = pipxSettings.FrequencyCalibration; + switch (pipxSettings.RFSpeed) + { + case PIPXSETTINGS_RFSPEED_2400: + pios_rfm22b_cfg.maxRFBandwidth = 2000; + break; + case PIPXSETTINGS_RFSPEED_4800: + pios_rfm22b_cfg.maxRFBandwidth = 4000; + break; + case PIPXSETTINGS_RFSPEED_9600: + pios_rfm22b_cfg.maxRFBandwidth = 9600; + break; + case PIPXSETTINGS_RFSPEED_19200: + pios_rfm22b_cfg.maxRFBandwidth = 19200; + break; + case PIPXSETTINGS_RFSPEED_38400: + pios_rfm22b_cfg.maxRFBandwidth = 32000; + break; + case PIPXSETTINGS_RFSPEED_57600: + pios_rfm22b_cfg.maxRFBandwidth = 64000; + break; + case PIPXSETTINGS_RFSPEED_115200: + pios_rfm22b_cfg.maxRFBandwidth = 128000; + break; + } + switch (pipxSettings.RFSpeed) + { + case PIPXSETTINGS_MAXRFPOWER_125: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_0; + break; + case PIPXSETTINGS_MAXRFPOWER_16: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_1; + break; + case PIPXSETTINGS_MAXRFPOWER_316: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_2; + break; + case PIPXSETTINGS_MAXRFPOWER_63: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_3; + break; + case PIPXSETTINGS_MAXRFPOWER_126: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_4; + break; + case PIPXSETTINGS_MAXRFPOWER_25: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_5; + break; + case PIPXSETTINGS_MAXRFPOWER_50: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_6; + break; + case PIPXSETTINGS_MAXRFPOWER_100: + pios_rfm22b_cfg.maxTxPower = RFM22_tx_pwr_txpow_7; + break; + } + /* Initalize the RFM22B radio COM device. */ { if (PIOS_RFM22B_Init(&pios_rfm22b_id, &pios_rfm22b_cfg)) { diff --git a/flight/board_hw_defs/pipxtreme/board_hw_defs.c b/flight/board_hw_defs/pipxtreme/board_hw_defs.c index 7b5557d49..02ee81013 100644 --- a/flight/board_hw_defs/pipxtreme/board_hw_defs.c +++ b/flight/board_hw_defs/pipxtreme/board_hw_defs.c @@ -494,16 +494,6 @@ const struct pios_eeprom_cfg pios_eeprom_cfg = { #if defined(PIOS_INCLUDE_RFM22B) #include -const struct pios_rfm22b_cfg pios_rfm22b_cfg = { - .frequencyHz = 434000000, - .minFrequencyHz = 434000000 - 2000000, - .maxFrequencyHz = 434000000 + 2000000, - .RFXtalCap = 0x7f, - .maxRFBandwidth = 128000, - //.maxTxPower = RFM22_tx_pwr_txpow_0, // +1dBm ... 1.25mW - .maxTxPower = RFM22_tx_pwr_txpow_7, // +20dBm .. 100mW -}; - #endif /* PIOS_INCLUDE_RFM22B */ #if defined(PIOS_INCLUDE_PACKET_HANDLER) diff --git a/ground/openpilotgcs/src/plugins/config/configpipxtremewidget.cpp b/ground/openpilotgcs/src/plugins/config/configpipxtremewidget.cpp old mode 100644 new mode 100755 index 19ad9cd0f..57cf28fd8 --- a/ground/openpilotgcs/src/plugins/config/configpipxtremewidget.cpp +++ b/ground/openpilotgcs/src/plugins/config/configpipxtremewidget.cpp @@ -46,6 +46,8 @@ ConfigPipXtremeWidget::ConfigPipXtremeWidget(QWidget *parent) : ConfigTaskWidget } addApplySaveButtons(m_pipx->Apply, m_pipx->Save); + connect(m_pipx->Apply, SIGNAL(clicked()), this, SLOT(applySettings())); + connect(m_pipx->Save, SIGNAL(clicked()), this, SLOT(saveSettings())); } ConfigPipXtremeWidget::~ConfigPipXtremeWidget() @@ -61,6 +63,19 @@ void ConfigPipXtremeWidget::applySettings() { PipXSettings *pipxSettings = PipXSettings::GetInstance(getObjectManager()); PipXSettings::DataFields pipxSettingsData = pipxSettings->getData(); + + // Get the pair ID. + quint32 pairID = 0; + bool okay; + if (m_pipx->PairSelect1->isChecked()) + pairID = m_pipx->PairID1->text().toUInt(&okay, 16); + else if (m_pipx->PairSelect2->isChecked()) + pairID = m_pipx->PairID2->text().toUInt(&okay, 16); + else if (m_pipx->PairSelect3->isChecked()) + pairID = m_pipx->PairID3->text().toUInt(&okay, 16); + else if (m_pipx->PairSelect4->isChecked()) + pairID = m_pipx->PairID4->text().toUInt(&okay, 16); + pipxSettingsData.PairID = pairID; pipxSettings->setData(pipxSettingsData); } @@ -76,13 +91,33 @@ void ConfigPipXtremeWidget::saveSettings() */ void ConfigPipXtremeWidget::updateStatus(UAVObject *object) { + // Get the settings object. + PipXSettings *pipxSettings = PipXSettings::GetInstance(getObjectManager()); + PipXSettings::DataFields pipxSettingsData = pipxSettings->getData(); + // Update the detected devices. UAVObjectField* pairIdField = object->getField("PairIDs"); if (pairIdField) { - m_pipx->PairID1->setText(QString::number(pairIdField->getValue(0).toUInt(), 16).toUpper()); + quint32 pairid1 = pairIdField->getValue(0).toUInt(); + m_pipx->PairID1->setText(QString::number(pairid1, 16).toUpper()); + m_pipx->PairID1->setEnabled(false); + m_pipx->PairSelect1->setChecked(pipxSettingsData.PairID == pairid1); + m_pipx->PairSelect1->setEnabled(pairid1); + quint32 pairid2 = pairIdField->getValue(1).toUInt(); m_pipx->PairID2->setText(QString::number(pairIdField->getValue(1).toUInt(), 16).toUpper()); + m_pipx->PairID2->setEnabled(false); + m_pipx->PairSelect2->setChecked(pipxSettingsData.PairID == pairid2); + m_pipx->PairSelect2->setEnabled(pairid2); + quint32 pairid3 = pairIdField->getValue(2).toUInt(); m_pipx->PairID3->setText(QString::number(pairIdField->getValue(2).toUInt(), 16).toUpper()); + m_pipx->PairID3->setEnabled(false); + m_pipx->PairSelect3->setChecked(pipxSettingsData.PairID == pairid3); + m_pipx->PairSelect3->setEnabled(pairid3); + quint32 pairid4 = pairIdField->getValue(3).toUInt(); m_pipx->PairID4->setText(QString::number(pairIdField->getValue(3).toUInt(), 16).toUpper()); + m_pipx->PairID4->setEnabled(false); + m_pipx->PairSelect4->setChecked(pipxSettingsData.PairID == pairid4); + m_pipx->PairSelect4->setEnabled(pairid4); } else { qDebug() << "PipXtremeGadgetWidget: Count not read PairID field."; } diff --git a/shared/uavobjectdefinition/pipxsettings.xml b/shared/uavobjectdefinition/pipxsettings.xml index 3763127ab..6cd51c96b 100644 --- a/shared/uavobjectdefinition/pipxsettings.xml +++ b/shared/uavobjectdefinition/pipxsettings.xml @@ -16,9 +16,9 @@ - + - +