summaryrefslogtreecommitdiff
path: root/Mode
diff options
context:
space:
mode:
authorMike Fiore <mfiore@multitech.com>2015-11-23 12:25:51 -0600
committerMike Fiore <mfiore@multitech.com>2015-11-23 12:25:51 -0600
commit3ad4a2fde749077bce94115902ab9c6e9760a2f8 (patch)
treef365f002a85f374513029a78522c0037cd1ba1e9 /Mode
parent4166bbd0ff84397f31d4928c2ebe6d9a57c3694d (diff)
downloadmtdot-box-evb-factory-firmware-3ad4a2fde749077bce94115902ab9c6e9760a2f8.tar.gz
mtdot-box-evb-factory-firmware-3ad4a2fde749077bce94115902ab9c6e9760a2f8.tar.bz2
mtdot-box-evb-factory-firmware-3ad4a2fde749077bce94115902ab9c6e9760a2f8.zip
save survey data to file, start adding support for sending data packet, misc tweaks and fixes
Diffstat (limited to 'Mode')
-rw-r--r--Mode/Mode.cpp104
-rw-r--r--Mode/Mode.h9
-rw-r--r--Mode/ModeSingle.cpp108
-rw-r--r--Mode/ModeSingle.h2
4 files changed, 202 insertions, 21 deletions
diff --git a/Mode/Mode.cpp b/Mode/Mode.cpp
index 64a8e53..ba60c01 100644
--- a/Mode/Mode.cpp
+++ b/Mode/Mode.cpp
@@ -1,4 +1,5 @@
#include "Mode.h"
+#include "MTSLog.h"
const char* Mode::_file_name = "SurveyData.txt";
@@ -10,7 +11,7 @@ Mode::Mode(DOGS102* lcd, ButtonHandler* buttons, mDot* dot, LoRaHandler* lora)
_main_id(Thread::gettid()),
_index(0),
_band(_dot->getFrequencyBand()),
- _sub_band(0),
+ _sub_band(_dot->getFrequencySubBand()),
_data_rate(mDot::SF_7),
_power(2),
_next_tx(0),
@@ -20,10 +21,109 @@ Mode::Mode(DOGS102* lcd, ButtonHandler* buttons, mDot* dot, LoRaHandler* lora)
Mode::~Mode() {}
bool Mode::deleteDataFile() {
- return true;
+ bool ret = true;
+
+ // if survey data file exists, attempt to delete it
+ std::vector<mDot::mdot_file> files = _dot->listUserFiles();
+ for (std::vector<mDot::mdot_file>::iterator it = files.begin(); it != files.end(); it++)
+ if (it->name == _file_name) {
+ if (! _dot->deleteUserFile(_file_name))
+ ret = false;
+ break;
+ }
+
+ return ret;
}
+// ID, Status, Lock, Lat, Long, Alt, Time, RSSIup, SNRup, RSSIdown, SNRdown, DataRate, Power
bool Mode::appendDataFile(const DataItem& data) {
+ char main_buf[256];
+ char id_buf[16];
+ char lat_buf[32];
+ char lon_buf[32];
+ char alt_buf[16];
+ char time_buf[32];
+ char stats_buf[32];
+ size_t size;
+
+ memset(main_buf, 0, sizeof(main_buf));
+ memset(id_buf, 0, sizeof(id_buf));
+ memset(lat_buf, 0, sizeof(lat_buf));
+ memset(lon_buf, 0, sizeof(lon_buf));
+ memset(alt_buf, 0, sizeof(alt_buf));
+ memset(time_buf, 0, sizeof(time_buf));
+ memset(stats_buf, 0, sizeof(stats_buf));
+
+ snprintf(id_buf, sizeof(id_buf), "%c%ld", (data.type == single) ? 'P' : 'S', data.index);
+
+ // if we had GPS lock, format GPS data
+ if (data.lock > 0) {
+ snprintf(lat_buf, sizeof(lat_buf), "%d %d %d.%03d %c",
+ abs(data.gps_latitude.degrees),
+ data.gps_latitude.minutes,
+ (data.gps_latitude.seconds * 6) / 1000,
+ (data.gps_latitude.seconds % 6) / 1000,
+ (data.gps_latitude.degrees > 0) ? 'N' : 'S');
+ snprintf(lon_buf, sizeof(lon_buf), "%d %d %d.%03d %c",
+ abs(data.gps_longitude.degrees),
+ data.gps_longitude.minutes,
+ (data.gps_longitude.seconds * 6) / 1000,
+ (data.gps_longitude.seconds % 6) / 1000,
+ (data.gps_longitude.degrees > 0) ? 'E' : 'W');
+ snprintf(alt_buf, sizeof(alt_buf), "%d",
+ data.gps_altitude);
+ snprintf(time_buf, sizeof(time_buf), "%02d:%02d:%02d %02d/%02d/%04d",
+ data.gps_time.tm_hour,
+ data.gps_time.tm_min,
+ data.gps_time.tm_sec,
+ data.gps_time.tm_mon + 1,
+ data.gps_time.tm_mday,
+ data.gps_time.tm_year + 1900);
+ }
+
+ if (data.status) {
+ snprintf(stats_buf, sizeof(stats_buf), "%d,%d.%ld,%d,%d.%ld",
+ data.ping.up.rssi,
+ data.ping.up.snr / 10, abs(data.ping.up.snr) % 10,
+ data.ping.down.rssi,
+ data.ping.down.snr / 4, (abs(data.ping.down.snr) % 10) * 25);
+ }
+
+ size = snprintf(main_buf, sizeof(main_buf), "%s,%c,%ld,%s,%s,%s,%s,%s,%s,%lu\n",
+ id_buf,
+ data.status ? 'S' : 'F',
+ data.lock,
+ (data.lock > 0) ? lat_buf : "",
+ (data.lock > 0) ? lon_buf : "",
+ (data.lock > 0) ? alt_buf : "",
+ (data.lock > 0) ? time_buf : "",
+ data.status ? stats_buf : ",,,",
+ _dot->DataRateStr(data.data_rate).substr(3).c_str(),
+ data.power);
+
+ if (size < 0) {
+ logError("failed to format survey data");
+ return false;
+ }
+
+ if (! _dot->appendUserFile(_file_name, (void*)main_buf, size)) {
+ logError("failed to write survey data to file");
+ return false;
+ } else {
+ logInfo("successfully wrote survey data to file");
+ }
+
return true;
}
+void Mode::updateData(DataItem& data, DataType type, bool status) {
+ data.type = type;
+ data.index = _index;
+ data.status = status;
+ data.lock = 0;
+ // TODO add GPS info
+ data.ping = _ping_result;
+ data.data_rate = _data_rate;
+ data.power = _power;
+}
+
diff --git a/Mode/Mode.h b/Mode/Mode.h
index 903d9c8..8a4f030 100644
--- a/Mode/Mode.h
+++ b/Mode/Mode.h
@@ -23,12 +23,9 @@ class Mode {
GPSPARSER::latitude gps_latitude;
int16_t gps_altitude;
struct tm gps_time;
- int16_t rssi_up;
- int16_t snr_up;
- int16_t rssi_down;
- int16_t snr_down;
+ LoRaHandler::LoRaPing ping;
uint8_t data_rate;
- uint8_t power;
+ uint32_t power;
} DataItem;
Mode(DOGS102* lcd, ButtonHandler* buttons, mDot* dot, LoRaHandler* lora);
@@ -39,6 +36,7 @@ class Mode {
protected:
bool deleteDataFile();
bool appendDataFile(const DataItem& data);
+ void updateData(DataItem& data, DataType type, bool status);
DOGS102* _lcd;
ButtonHandler* _buttons;
@@ -54,6 +52,7 @@ class Mode {
uint32_t _next_tx;
ButtonHandler::ButtonEvent _be;
LoRaHandler::LoRaStatus _ls;
+ LoRaHandler::LoRaPing _ping_result;
uint8_t _state;
bool _send_data;
};
diff --git a/Mode/ModeSingle.cpp b/Mode/ModeSingle.cpp
index 75bcdb9..5609bab 100644
--- a/Mode/ModeSingle.cpp
+++ b/Mode/ModeSingle.cpp
@@ -19,13 +19,10 @@ bool ModeSingle::start() {
bool send_data = false;
bool no_channel_ping = false;
bool no_channel_data = false;
- LoRaHandler::LoRaPing ping_result;
// clear any stale signals
osSignalClear(_main_id, buttonSignal | loraSignal);
- _sub_band = _dot->getFrequencySubBand();
-
// see if we're supposed to send the data packet after success
// that item is stored in the mDot::StartUpMode config field
_send_data = _dot->getStartUpMode();
@@ -33,7 +30,7 @@ bool ModeSingle::start() {
// see if survey data file exists
std::vector<mDot::mdot_file> files = _dot->listUserFiles();
for (std::vector<mDot::mdot_file>::iterator it = files.begin(); it != files.end(); it++) {
- if (it->name == _file_name) {
+ if (strcmp(it->name, _file_name) == 0) {
logInfo("found survey data file");
data_file = true;
break;
@@ -94,6 +91,7 @@ bool ModeSingle::start() {
break;
case confirm:
_state = show_help;
+ logInfo("deleting survey data file");
_dot->deleteUserFile(_file_name);
_index = 0;
displayHelp();
@@ -145,16 +143,21 @@ bool ModeSingle::start() {
case show_help:
break;
case in_progress:
- _state = success;
- ping_result = _lora->getPingResults();
- _success.display();
- _success.updateId(_index);
- // mDot::DataRateStr returns format SF_XX - we only want to display the XX part
- _success.updateRate(_dot->DataRateStr(_data_rate).substr(3));
- _success.updatePower(_power);
- _success.updateStats(ping_result);
- _success.updateInfo("No GPS Lock");
- _success.updateSw2("Survey");
+ _ping_result = _lora->getPingResults();
+ displaySuccess();
+ updateData(_data, single, true);
+ appendDataFile(_data);
+ if (_send_data) {
+ _state = data;
+ if (_lora->getNextTx() > 0)
+ no_channel_data = true;
+ else
+ send_data = true;
+ } else {
+ _state = success;
+ _success.updateSw1(" Power");
+ _success.updateSw2("Survey");
+ }
break;
case success:
break;
@@ -179,6 +182,8 @@ bool ModeSingle::start() {
_failure.updateId(_index);
// mDot::DataRateStr returns format SF_XX - we only want to display the XX part
_success.updateRate(_dot->DataRateStr(_data_rate).substr(3));
+ updateData(_data, single, false);
+ appendDataFile(_data);
_failure.updatePower(_power);
break;
case success:
@@ -189,6 +194,52 @@ bool ModeSingle::start() {
break;
}
break;
+
+ case LoRaHandler::send_success:
+ switch (_state) {
+ case check_file:
+ break;
+ case confirm:
+ break;
+ case show_help:
+ break;
+ case in_progress:
+ break;
+ case success:
+ break;
+ case data:
+ _state = success;
+ _success.updateInfo("Data Send Success");
+ _success.updateSw1(" Power");
+ _success.updateSw2("Survey");
+ break;
+ case failure:
+ break;
+ }
+ break;
+
+ case LoRaHandler::send_failure:
+ switch (_state) {
+ case check_file:
+ break;
+ case confirm:
+ break;
+ case show_help:
+ break;
+ case in_progress:
+ break;
+ case success:
+ break;
+ case data:
+ _state = success;
+ _success.updateInfo("Data Send Failure");
+ _success.updateSw1(" Power");
+ _success.updateSw2("Survey");
+ break;
+ case failure:
+ break;
+ }
+ break;
}
}
}
@@ -205,6 +256,15 @@ bool ModeSingle::start() {
}
}
if (no_channel_data) {
+ uint32_t t = _lora->getNextTx();
+ if (t > 0) {
+ logInfo("next tx %lu ms", t);
+ _success.updateCountdown(t / 1000);
+ } else {
+ displaySuccess();
+ no_channel_ping = false;
+ send_ping = true;
+ }
}
if (send_ping) {
logInfo("sending ping");
@@ -215,6 +275,12 @@ bool ModeSingle::start() {
_index++;
}
if (send_data) {
+ std::vector<uint8_t> s_data;
+ logInfo("sending data");
+ _success.updateInfo("Data Sending...");
+ _lora->setDataRate(_data_rate);
+ _lora->setPower(_power);
+ _lora->send(s_data);
}
}
}
@@ -226,6 +292,20 @@ void ModeSingle::displayHelp() {
_help.updateSw2("Survey");
}
+void ModeSingle::displaySuccess() {
+ _success.display();
+ _success.updateId(_index);
+ // mDot::DataRateStr returns format SF_XX - we only want to display the XX part
+ _success.updateRate(_dot->DataRateStr(_data_rate).substr(3));
+ _success.updatePower(_power);
+ _success.updateStats(_ping_result);
+ // if GPS lock
+ // display GPS latitude, longitude, and time
+ // else
+ // display "no lock"
+ _success.updateInfo("No GPS Lock");
+}
+
std::string ModeSingle::formatNewRatePower() {
std::string msg;
char buf[8];
diff --git a/Mode/ModeSingle.h b/Mode/ModeSingle.h
index 125e496..df656ba 100644
--- a/Mode/ModeSingle.h
+++ b/Mode/ModeSingle.h
@@ -18,6 +18,7 @@ class ModeSingle : public Mode {
private:
void displayHelp();
+ void displaySuccess();
std::string formatNewRatePower();
void incrementRatePower();
@@ -37,6 +38,7 @@ class ModeSingle : public Mode {
LayoutSurveyProgress _progress;
LayoutSurveySuccess _success;
LayoutSurveyFailure _failure;
+ DataItem _data;
};
#endif