Skip to content

Commit 93818fc

Browse files
committed
enabled the SD card for the system - now can save/restore prefs from sd card, and log to sd card
1 parent d3deaca commit 93818fc

7 files changed

+137
-25
lines changed

CMakeLists.txt

+3
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,11 @@ flux_sdk_add_module(
2828
flux_logging
2929
flux_system
3030
flux_prefs
31+
flux_prefs_json
3132
flux_prefs_serial
3233
flux_network
34+
flux_sdcard
35+
flux_file
3336
device_bme280
3437
device_bme68x
3538
device_bmp384

sfeIoTNodeLoRaWAN/sfeIoTNodeLoRaWAN.cpp

+38-1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
#include "sfeNLCommands.h"
1313
#include "sfeNLLed.h"
1414
#include "sfeNLVersion.h"
15+
#include "sfeNLBoard.h"
1516
#include <Arduino.h>
1617

1718
#include <Flux/flxDevButton.h>
@@ -74,7 +75,7 @@ static const uint8_t _app_jump[] = {104, 72, 67, 51, 74, 67, 108, 99, 104, 11
7475
#define kAppClassPrefix "INLW"
7576
//---------------------------------------------------------------------------
7677
//
77-
sfeIoTNodeLoRaWAN::sfeIoTNodeLoRaWAN() : _opFlags{0}
78+
sfeIoTNodeLoRaWAN::sfeIoTNodeLoRaWAN() : _logTypeSD{kAppLogTypeNone}, _logTypeSer{kAppLogTypeNone}, _opFlags{0}
7879
{
7980
// Constructor
8081
}
@@ -214,8 +215,10 @@ void sfeIoTNodeLoRaWAN::onInit()
214215
// flxLog_I("in onInit()");
215216

216217
_logTypeSer = kAppLogTypeNone;
218+
_logTypeSD = kAppLogTypeNone;
217219
serialLogType.setTitle("Output");
218220
flxRegister(serialLogType, "Serial Console Format", "Enable and set the output format");
221+
flxRegister(sdCardLogType, "SD Card Format", "Enable and set the output format");
219222
flxRegister(jsonBufferSize, "JSON Buffer Size", "Output buffer size in bytes");
220223

221224
// Terminal Serial Baud Rate
@@ -241,6 +244,12 @@ void sfeIoTNodeLoRaWAN::onInit()
241244
_sysStorageDevice.initialize(preStart, kSegmentSize, 10);
242245
_sysStorage.setStorageDevice(&_sysStorageDevice);
243246
flxSettings.setStorage(&_sysStorage);
247+
flxSettings.setFallback(&_jsonStorage);
248+
249+
_jsonStorage.setFileSystem(&_theSDCard);
250+
_jsonStorage.setFilename("iot-node-lorawan.json");
251+
252+
_theSDCard.setCSPin(kNLBoardSDCardCSPin);
244253

245254
// Did the user set a serial value?
246255
uint32_t theRate;
@@ -323,6 +332,11 @@ bool sfeIoTNodeLoRaWAN::onSetup()
323332
// was list device divers set by startup commands?
324333
if (inOpMode(kAppOpStartListDevices))
325334
flux.dumpDeviceAutoLoadTable();
335+
// setup SD card. Do this before calling start - so prefs can be read off SD if needed
336+
if (!setupSDCard())
337+
{
338+
flxLog_W(F("Unable to initialize the SD Card. Is an SD card installed on the board?"));
339+
}
326340

327341
// Button events we're listening on
328342
_boardButton.on_momentaryPress.call(this, &sfeIoTNodeLoRaWAN::onLogEvent);
@@ -508,6 +522,29 @@ void sfeIoTNodeLoRaWAN::set_jsonBufferSize(uint32_t new_size)
508522
_fmtJSON.setBufferSize(new_size);
509523
}
510524

525+
uint8_t sfeIoTNodeLoRaWAN::get_logTypeSD(void)
526+
{
527+
return _logTypeSD;
528+
}
529+
//---------------------------------------------------------------------------
530+
void sfeIoTNodeLoRaWAN::set_logTypeSD(uint8_t logType)
531+
{
532+
if (logType == _logTypeSD)
533+
return;
534+
535+
if (_logTypeSD == kAppLogTypeCSV)
536+
_fmtCSV.remove(&_theOutputFile);
537+
else if (_logTypeSD == kAppLogTypeJSON)
538+
_fmtJSON.remove(&_theOutputFile);
539+
540+
_logTypeSD = logType;
541+
542+
if (_logTypeSD == kAppLogTypeCSV)
543+
_fmtCSV.add(&_theOutputFile);
544+
else if (_logTypeSD == kAppLogTypeJSON)
545+
_fmtJSON.add(&_theOutputFile);
546+
}
547+
511548
//---------------------------------------------------------------------------
512549
uint8_t sfeIoTNodeLoRaWAN::get_logTypeSer(void)
513550
{

sfeIoTNodeLoRaWAN/sfeIoTNodeLoRaWAN.h

+22
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@
2424
#include <Flux/flxSettingsSerial.h>
2525
#include <Flux/flxStorageKVPPref.h>
2626
#include <Flux/flxSystem.h>
27+
#include <Flux/flxFSSDCard.h>
28+
#include <Flux/flxFileRotate.h>
29+
#include <Flux/flxStorageJSONPref.h>
2730

2831
#include "flxLoRaWANDigi.h"
2932
#include "flxLoRaWANLogger.h"
@@ -78,6 +81,14 @@ class sfeIoTNodeLoRaWAN : public flxApplication
7881
static constexpr uint8_t kAppLogTypeJSON = 0x2;
7982

8083
static constexpr const char *kLogFormatNames[] = {"Disabled", "CSV Format", "JSON Format"};
84+
85+
86+
//---------------------------------------------------------------------------
87+
uint8_t get_logTypeSD(void);
88+
89+
//---------------------------------------------------------------------------
90+
void set_logTypeSD(uint8_t logType);
91+
uint8_t _logTypeSD;
8192
uint8_t _logTypeSer; // type of serial log output format
8293
//---------------------------------------------------------------------------
8394
uint8_t get_logTypeSer(void);
@@ -157,6 +168,12 @@ class sfeIoTNodeLoRaWAN : public flxApplication
157168
&sfeIoTNodeLoRaWAN::set_verbose_dev_name>
158169
verboseDevNames;
159170

171+
flxPropertyRWUInt8<sfeIoTNodeLoRaWAN, &sfeIoTNodeLoRaWAN::get_logTypeSD, &sfeIoTNodeLoRaWAN::set_logTypeSD> sdCardLogType = {
172+
kAppLogTypeCSV,
173+
{{kLogFormatNames[kAppLogTypeNone], kAppLogTypeNone},
174+
{kLogFormatNames[kAppLogTypeCSV], kAppLogTypeCSV},
175+
{kLogFormatNames[kAppLogTypeJSON], kAppLogTypeJSON}}};
176+
160177
flxPropertyRWUInt8<sfeIoTNodeLoRaWAN, &sfeIoTNodeLoRaWAN::get_logTypeSer, &sfeIoTNodeLoRaWAN::set_logTypeSer>
161178
serialLogType = {kAppLogTypeCSV,
162179
{{kLogFormatNames[kAppLogTypeNone], kAppLogTypeNone},
@@ -204,6 +221,7 @@ class sfeIoTNodeLoRaWAN : public flxApplication
204221
// setup routines
205222
bool setupTime();
206223
void setupENS160(void);
224+
bool setupSDCard(void);
207225

208226
// Our LoRaWAN network/connection object
209227
flxLoRaWANDigi _loraWANConnection;
@@ -220,6 +238,10 @@ class sfeIoTNodeLoRaWAN : public flxApplication
220238
flxFormatJSON<kAppJSONDocSize> _fmtJSON;
221239
flxFormatCSV _fmtCSV;
222240

241+
flxFSSDCard _theSDCard;
242+
flxFileRotate _theOutputFile;
243+
flxStorageJSONPrefFile _jsonStorage;
244+
223245
// Serial Settings editor
224246
flxSettingsSerial _serialSettings;
225247

sfeIoTNodeLoRaWAN/sfeIoTNodeLoRaWANAbout.cpp

+34-21
Original file line numberDiff line numberDiff line change
@@ -115,24 +115,37 @@ void sfeIoTNodeLoRaWAN::displayAppStatus(bool useInfo)
115115
flxSerial.textToWhite();
116116
flxLog_N(" System:");
117117
flxSerial.textToNormal();
118+
flxSerial.flush();
118119
}
119-
// if (_theSDCard.enabled())
120-
// {
121-
122-
// char szSize[32];
123-
// char szCap[32];
124-
// char szAvail[32];
125-
126-
// flx_utils::formatByteString(_theSDCard.size(), 2, szSize, sizeof(szSize));
127-
// flx_utils::formatByteString(_theSDCard.total(), 2, szCap, sizeof(szCap));
128-
// flx_utils::formatByteString(_theSDCard.total() - _theSDCard.used(), 2, szAvail, sizeof(szAvail));
120+
if (_theSDCard.enabled())
121+
{
129122

130-
// flxLog__(logLevel, "%cSD Card - Type: %s Size: %s Capacity: %s Free: %s (%.1f%%)", pre_ch,
131-
// _theSDCard.type(),
132-
// szSize, szCap, szAvail, 100. - (_theSDCard.used() / (float)_theSDCard.total() * 100.));
133-
// }
134-
// else
135-
// flxLog__(logLevel, "%cSD card not available", pre_ch);
123+
char szSize[32];
124+
char szCap[32];
125+
char szAvail[32];
126+
127+
uint64_t sd_size = _theSDCard.size();
128+
uint64_t sd_total = _theSDCard.total();
129+
130+
flx_utils::formatByteString(sd_size, 2, szSize, sizeof(szSize));
131+
flx_utils::formatByteString(sd_total, 2, szCap, sizeof(szCap));
132+
133+
flxLog___(logLevel, "%cSD Card - Type: %s Size: %s Capacity: %s ", pre_ch, _theSDCard.type(), szSize, szCap);
134+
135+
// Getting about used can take time -- so only do if about is called (use info is false)
136+
if (!useInfo)
137+
{
138+
flxLog_N_("...");
139+
flxSerial.flush();
140+
// This call can take some time .. .so
141+
uint64_t sd_used = _theSDCard.used();
142+
flx_utils::formatByteString(sd_total - sd_used, 2, szAvail, sizeof(szAvail));
143+
flxLog_N("Free: %s (%.1f%%)", szAvail, 100. - (sd_used / (float)sd_total * 100.));
144+
}else
145+
flxLog_N("");
146+
}
147+
else
148+
flxLog__(logLevel, "%cSD card not available", pre_ch);
136149

137150
// show heap level
138151
flxLog__(logLevel, "%cSystem Heap - Total: %dB Free: %dB (%.1f%%)", pre_ch, flxPlatform::heap_size(),
@@ -167,15 +180,15 @@ void sfeIoTNodeLoRaWAN::displayAppStatus(bool useInfo)
167180
flxLog__(logLevel, "%cJSON Buffer - Size: %dB Max Used: %dB", pre_ch, jsonBufferSize(), _fmtJSON.getMaxSizeUsed());
168181
flxLog__(logLevel, "%cSerial Output: %s", pre_ch, kLogFormatNames[serialLogType()]);
169182
flxLog_N("%c Baud Rate: %d", pre_ch, serialBaudRate());
183+
flxLog__(logLevel, "%cSD Card Output: %s", pre_ch, kLogFormatNames[sdCardLogType()]);
170184

171185
// flxLog__(logLevel, "%cSD Card Output: %s", pre_ch, kLogFormatNames[sdCardLogType()]);
172186

173187
// at startup, useInfo == true, the file isn't known, so skip output
174-
// if (!useInfo)
175-
// flxLog_N("%c Current Filename: \t%s", pre_ch,
176-
// _theOutputFile.currentFilename().length() == 0 ? "<none>" :
177-
// _theOutputFile.currentFilename().c_str());
178-
// flxLog_N("%c Rotate Period: %d Hours", pre_ch, _theOutputFile.rotatePeriod());
188+
if (!useInfo)
189+
flxLog_N("%c Current Filename: \t%s", pre_ch,
190+
_theOutputFile.currentFilename().length() == 0 ? "<none>" : _theOutputFile.currentFilename().c_str());
191+
flxLog_N("%c Rotate Period: %d Hours", pre_ch, _theOutputFile.rotatePeriod());
179192

180193
flxLog_N("");
181194

sfeIoTNodeLoRaWAN/sfeIoTNodeLoRaWANSetup.cpp

+34
Original file line numberDiff line numberDiff line change
@@ -88,4 +88,38 @@ void sfeIoTNodeLoRaWAN::setupENS160(void)
8888
flxLog_I(F("%s: compensation values applied from %s"), pENS160->name(), pSHTC3->name());
8989
return;
9090
}
91+
}
92+
93+
//---------------------------------------------------------------------------
94+
// setupSDCard()
95+
//
96+
// Set's up the SD card subsystem and the objects/systems that use it.
97+
bool sfeIoTNodeLoRaWAN::setupSDCard(void)
98+
{
99+
100+
// setup output to the SD card
101+
if (_theSDCard.initialize())
102+
{
103+
104+
_theOutputFile.setName("Data File", "Output file rotation manager");
105+
106+
// SD card is available - lets setup output for it
107+
// Add the filesystem to the file output/rotation object
108+
_theOutputFile.setFileSystem(_theSDCard);
109+
110+
// setup our file rotation parameters
111+
_theOutputFile.filePrefix = "sfe";
112+
_theOutputFile.startNumber = 1;
113+
_theOutputFile.rotatePeriod(24); // one day
114+
115+
// add the file output to the CSV output.
116+
//_fmtCSV.add(_theOutputFile);
117+
118+
// have the CSV format driver listen to the new file event. This
119+
// will cause a header to be written next cycle.
120+
flxRegisterEventCB(flxEvent::kOnNewFile, &_fmtCSV, &flxFormatCSV::output_header);
121+
122+
return true;
123+
}
124+
return false;
91125
}

sfeIoTNodeLoRaWAN/sfeNLBoard.h

+3
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,9 @@ const uint8_t kNLBoardUserButton = 24;
1919
// 3v3 pin
2020
// const uint8_t kNLBoardEn3v3_SW = 32;
2121

22+
// SD Card CS Ping
23+
const uint8_t kNLBoardSDCardCSPin = 13;
24+
2225
// LED Built in
2326
const uint8_t kNLBoardLEDBuiltin = 25;
2427

sfeIoTNodeLoRaWAN/sfeNLVersion.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,13 @@
1616
#define kDLVersionNumberMajor 1
1717

1818
// Minor version number
19-
#define kDLVersionNumberMinor 0
19+
#define kDLVersionNumberMinor 1
2020

2121
// Point version number
22-
#define kDLVersionNumberPoint 1
22+
#define kDLVersionNumberPoint 0
2323

2424
// Version string description
25-
#define kDLVersionDescriptor "RC4"
25+
#define kDLVersionDescriptor "RC1"
2626

2727
// app name/class ID string
2828
#define kDLAppClassNameID "SFE-IOT-NODE_LORAWAN"

0 commit comments

Comments
 (0)