33 for (
int k = 0; k < 8; ++k) c = (uint8_t)((c & 0x80u) ? ((
unsigned)c << 1) ^ 0x07u : ((unsigned)c << 1));
42 c ^= (uint16_t)(*p++) << 8;
43 for (
int k = 0; k < 8; ++k) c = (uint16_t)((c & 0x8000u) ? ((
unsigned)c << 1) ^ 0x1021u : ((unsigned)c << 1));
50static uint16_t
next(uint16_t
s) {
return (uint16_t)((
s + 1u) %
s_nsect); }
53 if (
on)
s_used[
s >> 3] |= (uint8_t)(1u << (
s & 7u));
else s_used[
s >> 3] &= (uint8_t)~(1u << (
s & 7u));
55static uint8_t
is_used(uint16_t
s) {
return (uint8_t)((
s_used[
s >> 3] >> (
s & 7u)) & 1u); }
113 memset(e, 0,
sizeof *e);
126 for (uint8_t i = 0; i <
s_n; ++i)
if (
s_list[i].
id ==
id)
return &
s_list[i];
142 if (
used == 0u)
return 0;
162 memset(&h, 0,
sizeof h);
167 memcpy(
s_page, &h,
sizeof h);
173 memset(e, 0,
sizeof *e);
193int log_append(uint8_t type,
const void *payload, uint8_t len)
197 rec[0] = type; rec[1] = len;
198 memcpy(&rec[2], payload, len);
199 rec[2u + len] =
log_crc8(rec, 2u + len);
206 for (uint32_t k = 0; k <
n; ++k) {
234 uint8_t *
b = (uint8_t *)buf;
241 b += k;
off += k;
n -= k;
static int hdr_ok(const log_sector_hdr_t *h)
static log_entry_t s_list[LOG_LIST_MAX]
const log_entry_t * log_find(uint16_t id)
static uint8_t is_used(uint16_t s)
static uint16_t s_last_id
int log_append(uint8_t type, const void *payload, uint8_t len)
int log_read(uint16_t id, uint32_t off, void *buf, uint32_t n)
bytes of a closed log 'id' from 'offset' (sectors concatenated, headers included)
static uint32_t s_page_base
static uint32_t addr(uint16_t sect)
static uint8_t s_used[4096/8]
static int flush_page(void)
static void forget_sector(uint16_t sect)
int log_open(uint32_t t0)
0 = ok
int log_mount(const log_flash_t *f)
0 = ok (empty flash is ok)
uint16_t log_crc16(const uint8_t *p, uint32_t n)
static uint8_t s_page[LOG_PAGE]
const log_entry_t * log_entry(uint8_t i)
oldest first
uint8_t log_used_pct(void)
uint32_t log_size(uint16_t id)
nsect × LOG_SECTOR, 0 unknown
uint8_t log_crc8(const uint8_t *p, uint32_t n)
static uint16_t next(uint16_t s)
uint8_t log_is_open(void)
static int read_hdr(uint16_t s, log_sector_hdr_t *h)
static void set_used(uint16_t s, uint8_t on)
static int start_sector(void)
int log_erase_all(void)
erases every sector that holds data; logs restart from id 1
static const log_flash_t * F
Flight-log store: ring of sectors on a NOR flash (format in log_format.h).
uint16_t first
sector of the lowest seq still present
uint8_t active
being written now
uint8_t truncated
seq 0 overwritten
flash backend; addresses in bytes from the start of the log area
int(* erase)(void *ctx, uint32_t addr)
one 4 KB sector, blocking
uint32_t size
multiple of LOG_SECTOR
int(* read)(void *ctx, uint32_t addr, void *buf, uint32_t n)
int(* prog)(void *ctx, uint32_t addr, const void *buf, uint32_t n)
inside one 256-byte page
uint16_t log_id
increments for every new log
uint16_t crc
CRC-16/CCITT-FALSE of the 18 bytes above
uint32_t serial
global sector write counter: the newest sector has the highest
uint16_t seq
sector index inside the log, 0 = first
uint32_t t0_ms
uptime when the log started