Skip to content

Commit

Permalink
Logging Updates (#978)
Browse files Browse the repository at this point in the history
* log_file ensures directory exists
* Fix audio timestamp path
* Fix auto inc, add subfolder for recordings
* Fix auto inc and support subfolder
  • Loading branch information
kallanreed committed May 12, 2023
1 parent 8b39523 commit a8cdde7
Show file tree
Hide file tree
Showing 22 changed files with 132 additions and 62 deletions.
3 changes: 1 addition & 2 deletions firmware/application/apps/acars_app.cpp
Expand Up @@ -98,10 +98,9 @@ ACARSAppView::ACARSAppView(NavigationView& nav) {
logging = v;
};

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<ACARSLogger>();
if (logger)
logger->append( LOG_ROOT_DIR "/ACARS.TXT" );
logger->append(LOG_ROOT_DIR "/ACARS.TXT");
}

ACARSAppView::~ACARSAppView() {
Expand Down
1 change: 0 additions & 1 deletion firmware/application/apps/ais_app.cpp
Expand Up @@ -397,7 +397,6 @@ AISAppView::AISAppView(NavigationView& nav) : nav_ { nav } {
this->on_show_list();
};

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<AISLogger>();
if( logger ) {
logger->append( LOG_ROOT_DIR "/AIS.TXT" );
Expand Down
2 changes: 1 addition & 1 deletion firmware/application/apps/analog_audio_app.hpp
Expand Up @@ -232,7 +232,7 @@ class AnalogAudioView : public View {

RecordView record_view {
{ 0 * 8, 2 * 16, 30 * 8, 1 * 16 },
u"AUD",
u"AUD", u"AUDIO",
RecordView::FileType::WAV,
4096,
4
Expand Down
2 changes: 1 addition & 1 deletion firmware/application/apps/capture_app.hpp
Expand Up @@ -108,7 +108,7 @@ class CaptureAppView : public View {

RecordView record_view {
{ 0 * 8, 2 * 16, 30 * 8, 1 * 16 },
u"BBD_????", RecordView::FileType::RawS16, 16384, 3
u"BBD_????.*", u"CAPTURES", RecordView::FileType::RawS16, 16384, 3
};

spectrum::WaterfallWidget waterfall { };
Expand Down
1 change: 0 additions & 1 deletion firmware/application/apps/ert_app.cpp
Expand Up @@ -130,7 +130,6 @@ ERTAppView::ERTAppView(NavigationView&) {
static_cast<int8_t>(receiver_model.vga()),
}); */

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<ERTLogger>();
if( logger ) {
logger->append( LOG_ROOT_DIR "/ERT.TXT" );
Expand Down
3 changes: 1 addition & 2 deletions firmware/application/apps/pocsag_app.cpp
Expand Up @@ -129,10 +129,9 @@ POCSAGAppView::POCSAGAppView(NavigationView& nav) {
ignore_address /= 10;
}

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<POCSAGLogger>();
if (logger)
logger->append( LOG_ROOT_DIR "/POCSAG.TXT" );
logger->append(LOG_ROOT_DIR "/POCSAG.TXT");

audio::output::start();
audio::output::unmute();
Expand Down
1 change: 0 additions & 1 deletion firmware/application/apps/tpms_app.cpp
Expand Up @@ -194,7 +194,6 @@ TPMSAppView::TPMSAppView(NavigationView&) {

options_temperature.set_selected_index(0, true);

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<TPMSLogger>();
if( logger ) {
logger->append( LOG_ROOT_DIR "/TPMS.TXT" );
Expand Down
2 changes: 0 additions & 2 deletions firmware/application/apps/ui_adsb_rx.cpp
Expand Up @@ -117,8 +117,6 @@ ADSBRxAircraftDetailsView::ADSBRxAircraftDetailsView(

std::unique_ptr<ADSBLogger> logger { };

make_new_directory(LOG_ROOT_DIR);

icao_code = to_string_hex(entry_copy.ICAO_address, 6);
text_icao_address.set(to_string_hex(entry_copy.ICAO_address, 6));

Expand Down
3 changes: 1 addition & 2 deletions firmware/application/apps/ui_afsk_rx.cpp
Expand Up @@ -107,10 +107,9 @@ AFSKRxView::AFSKRxView(NavigationView& nav) {
nav.push<ModemSetupView>();
};

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<AFSKLogger>();
if (logger)
logger->append( LOG_ROOT_DIR "/AFSK.TXT" );
logger->append(LOG_ROOT_DIR "/AFSK.TXT");

// Auto-configure modem for LCR RX (will be removed later)
baseband::set_afsk(persistent_memory::modem_baudrate(), 8, 0, false);
Expand Down
3 changes: 1 addition & 2 deletions firmware/application/apps/ui_aprs_rx.cpp
Expand Up @@ -141,10 +141,9 @@ APRSRxView::APRSRxView(NavigationView& nav, Rect parent_rect) : View(parent_rect

options_region.set_selected_index(0, true);

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<APRSLogger>();
if (logger)
logger->append( LOG_ROOT_DIR "/APRS.TXT" );
logger->append(LOG_ROOT_DIR "/APRS.TXT");

baseband::set_aprs(1200);

Expand Down
2 changes: 1 addition & 1 deletion firmware/application/apps/ui_aprs_rx.hpp
Expand Up @@ -235,7 +235,7 @@ class APRSRxView : public View {
// DEBUG
RecordView record_view {
{ 0 * 8, 1 * 16, 30 * 8, 1 * 16 },
u"AFS_????", RecordView::FileType::WAV, 4096, 4
u"AFS_????.WAV", u"APRS", RecordView::FileType::WAV, 4096, 4
};

Console console {
Expand Down
3 changes: 1 addition & 2 deletions firmware/application/apps/ui_fileman.cpp
Expand Up @@ -42,8 +42,7 @@ bool is_hidden_file(const fs::path& path) {

// Gets a truncated name from a path for display.
std::string truncate(const fs::path& path, size_t max_length) {
auto name = path.string();
return name.length() <= max_length ? name : name.substr(0, max_length);
return ::truncate(path.string(), max_length);
}

// Gets a human readable file size string.
Expand Down
1 change: 0 additions & 1 deletion firmware/application/apps/ui_sonde.cpp
Expand Up @@ -133,7 +133,6 @@ SondeView::SondeView(NavigationView& nav) {
999); //set a dummy heading out of range to draw a cross...probably not ideal?
};

make_new_directory(LOG_ROOT_DIR);
logger = std::make_unique<SondeLogger>();
if (logger)
logger->append( LOG_ROOT_DIR "/SONDE.TXT" );
Expand Down
1 change: 0 additions & 1 deletion firmware/application/apps/ui_test.cpp
Expand Up @@ -79,7 +79,6 @@ TestView::TestView(NavigationView& nav) {
cal_value = raw_alt - 0x80;
};


logger = std::make_unique<TestLogger>();
if (logger)
logger->append("saucepan.txt");
Expand Down
108 changes: 79 additions & 29 deletions firmware/application/file.cpp
Expand Up @@ -124,50 +124,85 @@ Optional<File::Error> File::sync() {
}
}

static std::filesystem::path find_last_file_matching_pattern(const std::filesystem::path& pattern) {
std::filesystem::path last_match;
for(const auto& entry : std::filesystem::directory_iterator(u"", pattern)) {
if( std::filesystem::is_regular_file(entry.status()) ) {
/* Range used for filename matching.
* Start and end are inclusive positions of "???" */
struct pattern_range {
size_t start;
size_t end;
};

/* Finds the last file matching the specified pattern that
* can be automatically incremented (digits in pattern).
* NB: assumes a patten with contiguous '?' like "FOO_???.txt". */
static std::filesystem::path find_last_ordinal_match(
const std::filesystem::path& folder,
const std::filesystem::path& pattern,
pattern_range range
) {
auto last_match = std::filesystem::path();
auto can_increment = [range](const auto& path) {
for (auto i = range.start; i <= range.end; ++i)
if (!isdigit(path.native()[i]))
return false;

return true;
};

for (const auto& entry : std::filesystem::directory_iterator(folder, pattern)) {
if (std::filesystem::is_regular_file(entry.status()) && can_increment(entry.path())) {
const auto& match = entry.path();
if( match > last_match ) {
last_match = match;
}
}
}

return last_match;
}

static std::filesystem::path increment_filename_stem_ordinal(std::filesystem::path path) {
auto t = path.replace_extension().native();
auto it = t.rbegin();
/* Given a file path like "FOO_0001.txt" increment it to "FOO_0002.txt". */
static std::filesystem::path increment_filename_ordinal(
const std::filesystem::path& path, pattern_range range
) {
auto name = path.filename().native();

// Increment decimal number before the extension.
for(; it != t.rend(); ++it) {
const auto c = *it;
if( c < '0' ) {
for (auto i = range.end; i >= range.start; --i) {
auto& c = name[i];

// Not a digit or would overflow the counter.
if (c < u'0' || c > u'9' || (c == u'9' && i == range.start))
return { };
} else if( c < '9' ) {
*it += 1;

if (c == u'9')
c = '0';
else {
c++;
break;
} else if( c == '9' ) {
*it = '0';
} else {
return { };
}
}

return t;
return { name };
}

std::filesystem::path next_filename_stem_matching_pattern(std::filesystem::path filename_pattern) {
const auto next_filename = find_last_file_matching_pattern(filename_pattern.replace_extension(u".*"));
if( next_filename.empty() ) {
auto pattern_s = filename_pattern.replace_extension().native();
std::replace(std::begin(pattern_s), std::end(pattern_s), '?', '0');
return pattern_s;
} else {
return increment_filename_stem_ordinal(next_filename);
std::filesystem::path next_filename_matching_pattern(const std::filesystem::path& filename_pattern) {
auto path = filename_pattern.parent_path();
auto pattern = filename_pattern.filename();
auto range = pattern_range {
pattern.native().find_first_of(u'?'),
pattern.native().find_last_of(u'?')
};

const auto match = find_last_ordinal_match(path, pattern, range);

if (match.empty()) {
auto pattern_str = pattern.native();
for (auto i = range.start; i <= range.end; ++i)
pattern_str[i] = u'0';
return path / pattern_str;
}

auto next_name = increment_filename_ordinal(match, range);
return next_name.empty() ? next_name : path / next_name;
}

std::vector<std::filesystem::path> scan_root_files(const std::filesystem::path& directory,
Expand Down Expand Up @@ -214,7 +249,7 @@ std::filesystem::filesystem_error copy_file(
) {
File src;
File dst;
constexpr size_t buffer_size = 512;
constexpr size_t buffer_size = 128;
uint8_t buffer[buffer_size];

auto error = src.open(file_path);
Expand Down Expand Up @@ -261,6 +296,19 @@ std::filesystem::filesystem_error make_new_directory(
return { f_mkdir(reinterpret_cast<const TCHAR*>(dir_path.c_str())) };
}

std::filesystem::filesystem_error ensure_directory(
const std::filesystem::path& dir_path
) {
if (dir_path.empty() || std::filesystem::file_exists(dir_path))
return { };

auto result = ensure_directory(dir_path.parent_path());
if (result.code())
return result;

return make_new_directory(dir_path);
}

namespace std {
namespace filesystem {

Expand Down Expand Up @@ -383,8 +431,10 @@ directory_iterator::directory_iterator(
) : pattern { wild }
{
impl = std::make_shared<Impl>();
const auto result = f_findfirst(&impl->dir, &impl->filinfo, reinterpret_cast<const TCHAR*>(path.c_str()), reinterpret_cast<const TCHAR*>(pattern.c_str()));
if( result != FR_OK || impl->filinfo.fname[0] == (TCHAR)'\0') {
const auto result = f_findfirst(&impl->dir, &impl->filinfo,
reinterpret_cast<const TCHAR*>(path.c_str()),
reinterpret_cast<const TCHAR*>(pattern.c_str()));
if (result != FR_OK || impl->filinfo.fname[0] == (TCHAR)'\0') {
impl.reset();
// TODO: Throw exception if/when I enable exceptions...
}
Expand Down
13 changes: 11 additions & 2 deletions firmware/application/file.hpp
Expand Up @@ -59,6 +59,10 @@ struct filesystem_error {

std::string what() const;

bool ok() const {
return err == FR_OK;
}

private:
uint32_t err { FR_OK };
};
Expand Down Expand Up @@ -258,12 +262,17 @@ std::filesystem::filesystem_error copy_file(const std::filesystem::path& file_pa
FATTimestamp file_created_date(const std::filesystem::path& file_path);
std::filesystem::filesystem_error make_new_file(const std::filesystem::path& file_path);
std::filesystem::filesystem_error make_new_directory(const std::filesystem::path& dir_path);
std::filesystem::filesystem_error ensure_directory(const std::filesystem::path& dir_path);

std::vector<std::filesystem::path> scan_root_files(const std::filesystem::path& directory, const std::filesystem::path& extension);
std::vector<std::filesystem::path> scan_root_directories(const std::filesystem::path& directory);

/* Gets an auto incrementing filename. */
std::filesystem::path next_filename_stem_matching_pattern(std::filesystem::path filename_stem_pattern);
/* Gets an auto incrementing filename stem.
* Pattern should be like "FOO_???.txt" where ??? will be replaced by digits.
* Pattern may also contain a folder path like "LOGS/FOO_???.txt".
* Pattern '?' must be contiguous (bad: "FOO?_??")
* Returns empty path if a filename could not be created. */
std::filesystem::path next_filename_matching_pattern(const std::filesystem::path& pattern);

/* Values added to FatFs FRESULT enum, values outside the FRESULT data type */
static_assert(sizeof(FIL::err) == 1, "FatFs FIL::err size not expected.");
Expand Down
4 changes: 4 additions & 0 deletions firmware/application/log_file.hpp
Expand Up @@ -35,6 +35,10 @@ using namespace lpc43xx;
class LogFile {
public:
Optional<File::Error> append(const std::filesystem::path& filename) {
auto result = ensure_directory(filename.parent_path());
if (result.code())
return { result };

return file.append(filename);
}

Expand Down
13 changes: 11 additions & 2 deletions firmware/application/string_format.cpp
Expand Up @@ -256,8 +256,17 @@ double get_decimals(double num, int16_t mult, bool round) {
return intnum;
}

std::string trimr(std::string str)
{
std::string trim(const std::string& str) {
auto first = str.find_first_not_of(' ');
auto last = str.find_last_not_of(' ');
return str.substr(first, last - first);
}

std::string trimr(std::string str) {
size_t last = str.find_last_not_of(' ');
return (last!=std::string::npos) ? str.substr(0, last+1) : ""; // Remove the trailing spaces
}

std::string truncate(const std::string& str, size_t length) {
return str.length() <= length ? str : str.substr(0, length);
}
2 changes: 2 additions & 0 deletions firmware/application/string_format.hpp
Expand Up @@ -59,6 +59,8 @@ std::string to_string_FAT_timestamp(const FATTimestamp& timestamp);
std::string unit_auto_scale(double n, const uint32_t base_nano, uint32_t precision);
double get_decimals(double num, int16_t mult, bool round = false); //euquiq added

std::string trim(const std::string& str); // Remove whitespace at ends.
std::string trimr(std::string str); // Remove trailing spaces
std::string truncate(const std::string& str, size_t length);

#endif/*__STRING_FORMAT_H__*/
6 changes: 4 additions & 2 deletions firmware/application/ui_navigation.cpp
Expand Up @@ -367,13 +367,15 @@ void SystemStatusView::on_bias_tee() {
}*/

void SystemStatusView::on_camera() {
auto path = next_filename_stem_matching_pattern(u"SCR_????");
ensure_directory("SCREENSHOTS");
auto path = next_filename_matching_pattern(u"SCREENSHOTS/SCR_????.PNG");

if( path.empty() ) {
return;
}

PNGWriter png;
auto create_error = png.create(path.replace_extension(u".PNG"));
auto create_error = png.create(path);
if( create_error.is_valid() ) {
return;
}
Expand Down

0 comments on commit a8cdde7

Please sign in to comment.