35#include "generated/airframe.h"
52#define SDLOG_DIR "/data/ftp/internal_000/sdlog"
57#ifndef SDLOG_AUTO_FLUSH_PERIOD
59#define SDLOG_AUTO_FLUSH_PERIOD 1
61#define SDLOG_AUTO_FLUSH_PERIOD 10
65#define SDLOG_MAX_FILES 4
66#define SDLOG_MAX_MSG_LEN 512
74#define SDLOG_CONF TRUE
77#include "generated/aircraft_conf.h"
81#if FLIGHTRECORDER_SDLOG
82static const char FLIGHTRECORDER_LOG_NAME[] =
"fr_";
83static const char FR_LOG_DIR[] =
"FLIGHT_RECORDER";
84FileDes flightRecorderLogFile = -1;
138 if (fwrite(data, 1,
len,
f) !=
len) {
158 int len = vsnprintf(
buf,
sizeof(
buf), fmt, ap);
163 if ((
size_t)
len >=
sizeof(
buf)) {
248 sdlog->
device.periph = (
void *)(sdlog);
263 snprintf(tmp,
sizeof(tmp),
"%s", path);
264 for (
char *c = tmp + 1; *c; c++) {
267 if (mkdir(tmp, 0755) != 0 && errno != EEXIST) {
273 if (mkdir(tmp, 0755) != 0 && errno != EEXIST) {
283 size_t plen = strlen(prefix);
284 DIR *d = opendir(
dir);
289 while ((e = readdir(d)) != NULL) {
292 if (strncmp(e->d_name, prefix, plen) != 0 ||
293 sscanf(e->d_name + plen,
"%d.%7s", &num, ext) != 2 || strcmp(ext,
"LOG") != 0) {
298 snprintf(path,
sizeof(path),
"%s/%s",
dir, e->d_name);
299 if (stat(path, &st) == 0 && st.st_size == 0) {
301 }
else if (num >= next) {
326 if (snprintf(path,
sizeof(path),
"%s/%s", base,
dir) >= (
int)
sizeof(path) ||
sdlog_mkdir(path) != 0) {
336 snprintf(name, name_len,
"%s%04d.LOG", prefix, num);
339 snprintf(filename,
sizeof(filename),
"%s/%s", path, name);
345 printf(
"[sdlog] Logging to %s\n", filename);
351static SdioError sdlog_write_conf(
const char *base,
const char *
dir)
353 char path[512], tmp[520];
355 if (snprintf(path,
sizeof(path),
"%s/%s/%s", base,
dir, AIRCRAFT_CONF_NAME) >= (
int)
sizeof(path)) {
358 if (stat(path, &st) == 0) {
361 snprintf(tmp,
sizeof(tmp),
"%s.tmp", path);
362 FILE *
f = fopen(tmp,
"wb");
367 if (fwrite(aircraft_conf_gz, 1,
sizeof(aircraft_conf_gz),
f) !=
sizeof(aircraft_conf_gz)) {
370 if (fclose(
f) != 0 && err == 0) {
377 if (rename(tmp, path) != 0) {
393#ifdef SDLOG_PREFLIGHT_ERROR
404#if PERIODIC_TELEMETRY
431 len =
Min(len, (
int)
sizeof(
msg) - 1);
432 pprz_msg_send_INFO_MSG(trans,
dev, AC_ID, len,
msg);
443 if (strlen(filenames) == 0) {
446 pprz_msg_send_LOGGER_STATUS(trans,
dev, AC_ID, &
status, &err, &used, strlen(filenames), filenames);
457#if PERIODIC_TELEMETRY
469 const char *home = getenv(
"PAPARAZZI_HOME");
470 snprintf(base,
sizeof(base),
"%s/var/logs/sdlog/%s", home ? home :
".", AIRFRAME_NAME);
472 snprintf(base,
sizeof(base),
"%s",
dir);
484#if FLIGHTRECORDER_SDLOG
485 flightRecorderLogFile =
sdlog_open(base, FR_LOG_DIR, FLIGHTRECORDER_LOG_NAME, name,
sizeof(name));
486 if (flightRecorderLogFile != -1) {
495 printf(
"[sdlog] Could not open the log files in %s (error %d)\n", base,
sdlog_error);
505#if FLIGHTRECORDER_SDLOG
506 flightRecorderLogFile = -1;
522 uint8_t ac_id = pprzlink_get_DL_INFO_MSG_UP_ac_id(buf);
523 if (ac_id != AC_ID && ac_id != 0xFF) {
526 uint8_t fd = pprzlink_get_DL_INFO_MSG_UP_fd(buf);
528 uint8_t len = pprzlink_get_INFO_MSG_UP_msg_length(buf);
static struct uart_periph * dev
uint8_t msg[10]
Buffer used for general comunication over SPI (out buffer).
static FILE * pprzLogFile
static uint8_t null_byte_function(struct SuperbitRF *p)
static int null_function(struct SuperbitRF *p)
void preflight_error(struct preflight_result_t *result, const char *fmt,...)
Register a preflight error used inside the preflight checking functions.
void preflight_success(struct preflight_result_t *result, const char *fmt,...)
Register a preflight success used inside the preflight checking functions.
void preflight_warning(struct preflight_result_t *result, const char *fmt,...)
Register a preflight warning used inside the preflight checking functions.
void preflight_check_register(struct preflight_check_t *check, preflight_check_f func)
Register a preflight check and add it to the linked list.
static void sdlog_send(struct chibios_sdlog *p, long fd)
static volatile SdioError sdlog_conf_error
Result of writing the configuration, reported to the GCS.
static void send_sdlog_status(struct transport_tx *trans, struct link_device *dev)
static int sdlog_check_free_space(struct chibios_sdlog *p, long *fd, uint16_t len)
#define SDLOG_AUTO_FLUSH_PERIOD
static const char PPRZ_LOG_DIR[]
static const char PPRZ_LOG_NAME[]
#define DEST_INFO_MSG_PPRZLOG
#define DEST_INFO_MSG_ALL
struct link_device device
Generic device interface.
static const char * sdlog_error_string(SdioError error)
Human readable cause of a logger error, for the messages to the GCS.
static FILE * sdlog_files[SDLOG_MAX_FILES]
static size_t sdlog_bytes
static void sdlog_send(struct chibios_sdlog *p, long fd)
uint8_t buf[SDLOG_MAX_MSG_LEN]
static enum @245305264037150143222225356213155240245213073102 sdlog_status
static int null_function(struct chibios_sdlog *p)
static SdioError sdlog_errno_error(int err)
Error of a failed write or close: only a full disk is "SD card full".
SdioError sdLogFlushAllLogs(void)
static FILE * sdlog_file(FileDes fd)
static char sdlog_filenames[68]
static void sdlog_write(FileDes fd, const uint8_t *data, size_t len)
#define SDLOG_MAX_MSG_LEN
static void send_sdlog_status(struct transport_tx *trans, struct link_device *dev)
#define SDLOG_DIR
Directory where the logs are stored, the default in simulation is $PAPARAZZI_HOME/var/logs/sdlog/<AIR...
SdioError sdLogWriteLog(const FileDes fd, const char *fmt,...)
static int sdlog_check_free_space(struct chibios_sdlog *p, long *fd, uint16_t len)
void logger_log_msg_up(uint8_t *buf)
static void sdlog_put_byte(struct chibios_sdlog *p, long fd, uint8_t byte)
SdioError sdLogWriteByte(const FileDes fd, const uint8_t value)
static float sdlog_last_flush
static SdioError sdlog_error
void usbStorage_enable_usb_storage(float e)
static void sdlog_report_status(struct transport_tx *trans, struct link_device *dev)
Tell the GCS in words why the logger does not run (no SD card, card full, ...): at the start and ever...
static int sdlog_next_number(const char *dir, const char *prefix)
Remove the empty logs and get the next free log number.
void sdlog_chibios_finish(const bool flush)
SdioError sdLogGetStorageStatus(void)
SdioError sdLogWriteRaw(const FileDes fd, const uint8_t *buffer, const size_t len)
size_t sdLogGetNbBytesWrittenToStorage(void)
static int sdlog_mkdir(const char *path)
Create a directory and its parents.
static void sdlog_atexit(void)
SdioError sdLogFlushLog(const FileDes fd)
void chibios_sdlog_init(struct chibios_sdlog *sdlog, FileDes *file)
init chibios_sdlog structure
static FileDes sdlog_open(const char *base, const char *dir, const char *prefix, char *name, size_t name_len)
Open the next log file in base/dir, returns the descriptor or -1.
static void sdlog_put_buffer(struct chibios_sdlog *p, long fd, const uint8_t *data, uint16_t len)
static uint8_t null_byte_function(struct chibios_sdlog *p)
void sdlog_chibios_init(void)
Message under construction, one per thread so threads can't mix messages (the fd argument of the devi...
Architecture independent timing functions.
static float get_sys_time_float(void)
Get the time in seconds since startup.
int16_t register_periodic_telemetry(struct periodic_telemetry *_pt, uint16_t _id, telemetry_cb _cb)
Register a telemetry callback function.
Periodic telemetry system header (includes downlink utility and generated code).
#define DefaultPeriodic
Set default periodic telemetry.
unsigned short uint16_t
Typedef defining 16 bit unsigned short type.
unsigned int uint32_t
Typedef defining 32 bit unsigned int type.
unsigned char uint8_t
Typedef defining 8 bit unsigned char type.
uint16_t f
Camera baseline, in meters (i.e. horizontal distance between the two cameras of the stereo setup).