123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340 |
- /*
- * Copyright (c) 2020, Armink, <armink.ztl@gmail.com>
- *
- * SPDX-License-Identifier: Apache-2.0
- */
- /**
- * @file
- * @brief Public definition.
- */
- #ifndef _FDB_DEF_H_
- #define _FDB_DEF_H_
- #ifdef __cplusplus
- extern "C" {
- #endif
- /* software version number */
- #define FDB_SW_VERSION "1.2.0"
- #define FDB_SW_VERSION_NUM 0x10200
- /* the KV max name length must less then it */
- #ifndef FDB_KV_NAME_MAX
- #define FDB_KV_NAME_MAX 64
- #endif
- /* the KV cache table size, it will improve KV search speed when using cache */
- #ifndef FDB_KV_CACHE_TABLE_SIZE
- #define FDB_KV_CACHE_TABLE_SIZE 64
- #endif
- /* the sector cache table size, it will improve KV save speed when using cache */
- #ifndef FDB_SECTOR_CACHE_TABLE_SIZE
- #define FDB_SECTOR_CACHE_TABLE_SIZE 4
- #endif
- #if (FDB_KV_CACHE_TABLE_SIZE > 0) && (FDB_SECTOR_CACHE_TABLE_SIZE > 0)
- #define FDB_KV_USING_CACHE
- #endif
- #if defined(FDB_USING_FILE_LIBC_MODE) || defined(FDB_USING_FILE_POSIX_MODE)
- #define FDB_USING_FILE_MODE
- #endif
- #ifndef FDB_WRITE_GRAN
- #define FDB_WRITE_GRAN 1
- #endif
- /* log function. default FDB_PRINT macro is printf() */
- #ifndef FDB_PRINT
- #define FDB_PRINT(...) printf(__VA_ARGS__)
- #endif
- #define FDB_LOG_PREFIX1() FDB_PRINT("[FlashDB]" FDB_LOG_TAG)
- #define FDB_LOG_PREFIX2() FDB_PRINT(" ")
- #define FDB_LOG_PREFIX() FDB_LOG_PREFIX1();FDB_LOG_PREFIX2()
- #ifdef FDB_DEBUG_ENABLE
- #define FDB_DEBUG(...) FDB_LOG_PREFIX();FDB_PRINT("(%s:%d) ", __FILE__, __LINE__);FDB_PRINT(__VA_ARGS__)
- #else
- #define FDB_DEBUG(...)
- #endif
- /* routine print function. Must be implement by user. */
- #define FDB_INFO(...) FDB_LOG_PREFIX();FDB_PRINT(__VA_ARGS__)
- /* assert for developer. */
- #define FDB_ASSERT(EXPR) \
- if (!(EXPR)) \
- { \
- FDB_DEBUG("(%s) has assert failed at %s.\n", #EXPR, __func__); \
- while (1); \
- }
- #define FDB_KVDB_CTRL_SET_SEC_SIZE 0x00 /**< set sector size control command, this change MUST before database initialization */
- #define FDB_KVDB_CTRL_GET_SEC_SIZE 0x01 /**< get sector size control command */
- #define FDB_KVDB_CTRL_SET_LOCK 0x02 /**< set lock function control command */
- #define FDB_KVDB_CTRL_SET_UNLOCK 0x03 /**< set unlock function control command */
- #define FDB_KVDB_CTRL_SET_FILE_MODE 0x09 /**< set file mode control command, this change MUST before database initialization */
- #define FDB_KVDB_CTRL_SET_MAX_SIZE 0x0A /**< set database max size in file mode control command, this change MUST before database initialization */
- #define FDB_KVDB_CTRL_SET_NOT_FORMAT 0x0B /**< set database NOT format mode control command, this change MUST before database initialization */
- #define FDB_TSDB_CTRL_SET_SEC_SIZE 0x00 /**< set sector size control command, this change MUST before database initialization */
- #define FDB_TSDB_CTRL_GET_SEC_SIZE 0x01 /**< get sector size control command */
- #define FDB_TSDB_CTRL_SET_LOCK 0x02 /**< set lock function control command */
- #define FDB_TSDB_CTRL_SET_UNLOCK 0x03 /**< set unlock function control command */
- #define FDB_TSDB_CTRL_SET_ROLLOVER 0x04 /**< set rollover control command, this change MUST after database initialization */
- #define FDB_TSDB_CTRL_GET_ROLLOVER 0x05 /**< get rollover control command */
- #define FDB_TSDB_CTRL_GET_LAST_TIME 0x06 /**< get last save time control command */
- #define FDB_TSDB_CTRL_SET_FILE_MODE 0x09 /**< set file mode control command, this change MUST before database initialization */
- #define FDB_TSDB_CTRL_SET_MAX_SIZE 0x0A /**< set database max size in file mode control command, this change MUST before database initialization */
- #define FDB_TSDB_CTRL_SET_NOT_FORMAT 0x0B /**< set database NOT formatable mode control command, this change MUST before database initialization */
- #ifdef FDB_USING_TIMESTAMP_64BIT
- typedef int64_t fdb_time_t;
- #else
- typedef int32_t fdb_time_t;
- #endif /* FDB_USING_TIMESTAMP_64BIT */
- typedef fdb_time_t (*fdb_get_time)(void);
- struct fdb_default_kv_node {
- char *key;
- void *value;
- size_t value_len;
- };
- struct fdb_default_kv {
- struct fdb_default_kv_node *kvs;
- size_t num;
- };
- /* error code */
- typedef enum {
- FDB_NO_ERR,
- FDB_ERASE_ERR,
- FDB_READ_ERR,
- FDB_WRITE_ERR,
- FDB_PART_NOT_FOUND,
- FDB_KV_NAME_ERR,
- FDB_KV_NAME_EXIST,
- FDB_SAVED_FULL,
- FDB_INIT_FAILED,
- } fdb_err_t;
- enum fdb_kv_status {
- FDB_KV_UNUSED,
- FDB_KV_PRE_WRITE,
- FDB_KV_WRITE,
- FDB_KV_PRE_DELETE,
- FDB_KV_DELETED,
- FDB_KV_ERR_HDR,
- #define FDB_KV_STATUS_NUM 6
- };
- typedef enum fdb_kv_status fdb_kv_status_t;
- enum fdb_tsl_status {
- FDB_TSL_UNUSED,
- FDB_TSL_PRE_WRITE,
- FDB_TSL_WRITE,
- FDB_TSL_USER_STATUS1,
- FDB_TSL_DELETED,
- FDB_TSL_USER_STATUS2,
- #define FDB_TSL_STATUS_NUM 6
- };
- typedef enum fdb_tsl_status fdb_tsl_status_t;
- /* key-value node object */
- struct fdb_kv {
- fdb_kv_status_t status; /**< node status, @see fdb_kv_status_t */
- bool crc_is_ok; /**< node CRC32 check is OK */
- uint8_t name_len; /**< name length */
- uint32_t magic; /**< magic word(`K`, `V`, `4`, `0`) */
- uint32_t len; /**< node total length (header + name + value), must align by FDB_WRITE_GRAN */
- uint32_t value_len; /**< value length */
- char name[FDB_KV_NAME_MAX]; /**< name */
- struct {
- uint32_t start; /**< node start address */
- uint32_t value; /**< value start address */
- } addr;
- };
- typedef struct fdb_kv *fdb_kv_t;
- struct fdb_kv_iterator {
- struct fdb_kv curr_kv; /**< Current KV we get from the iterator */
- uint32_t iterated_cnt; /**< How many KVs have we iterated already */
- size_t iterated_obj_bytes; /**< Total storage size of KVs we have iterated. */
- size_t iterated_value_bytes; /**< Total value size of KVs we have iterated. */
- uint32_t sector_addr; /**< Current sector address we're iterating. DO NOT touch it. */
- };
- typedef struct fdb_kv_iterator *fdb_kv_iterator_t;
- /* time series log node object */
- struct fdb_tsl {
- fdb_tsl_status_t status; /**< node status, @see fdb_log_status_t */
- fdb_time_t time; /**< node timestamp */
- uint32_t log_len; /**< log length, must align by FDB_WRITE_GRAN */
- struct {
- uint32_t index; /**< node index address */
- uint32_t log; /**< log data address */
- } addr;
- };
- typedef struct fdb_tsl *fdb_tsl_t;
- typedef bool (*fdb_tsl_cb)(fdb_tsl_t tsl, void *arg);
- typedef enum {
- FDB_DB_TYPE_KV,
- FDB_DB_TYPE_TS,
- } fdb_db_type;
- /* the flash sector store status */
- enum fdb_sector_store_status {
- FDB_SECTOR_STORE_UNUSED,
- FDB_SECTOR_STORE_EMPTY,
- FDB_SECTOR_STORE_USING,
- FDB_SECTOR_STORE_FULL,
- #define FDB_SECTOR_STORE_STATUS_NUM 4
- };
- typedef enum fdb_sector_store_status fdb_sector_store_status_t;
- /* the flash sector dirty status */
- enum fdb_sector_dirty_status {
- FDB_SECTOR_DIRTY_UNUSED,
- FDB_SECTOR_DIRTY_FALSE,
- FDB_SECTOR_DIRTY_TRUE,
- FDB_SECTOR_DIRTY_GC,
- #define FDB_SECTOR_DIRTY_STATUS_NUM 4
- };
- typedef enum fdb_sector_dirty_status fdb_sector_dirty_status_t;
- /* KVDB section information */
- struct kvdb_sec_info {
- bool check_ok; /**< sector header check is OK */
- struct {
- fdb_sector_store_status_t store; /**< sector store status @see fdb_sector_store_status_t */
- fdb_sector_dirty_status_t dirty; /**< sector dirty status @see sector_dirty_status_t */
- } status;
- uint32_t addr; /**< sector start address */
- uint32_t magic; /**< magic word(`E`, `F`, `4`, `0`) */
- uint32_t combined; /**< the combined next sector number, 0xFFFFFFFF: not combined */
- size_t remain; /**< remain size */
- uint32_t empty_kv; /**< the next empty KV node start address */
- };
- typedef struct kvdb_sec_info *kv_sec_info_t;
- /* TSDB section information */
- struct tsdb_sec_info {
- bool check_ok; /**< sector header check is OK */
- fdb_sector_store_status_t status; /**< sector store status @see fdb_sector_store_status_t */
- uint32_t addr; /**< sector start address */
- uint32_t magic; /**< magic word(`T`, `S`, `L`, `0`) */
- fdb_time_t start_time; /**< the first start node's timestamp, 0xFFFFFFFF: unused */
- fdb_time_t end_time; /**< the last end node's timestamp, 0xFFFFFFFF: unused */
- uint32_t end_idx; /**< the last end node's index, 0xFFFFFFFF: unused */
- fdb_tsl_status_t end_info_stat[2]; /**< the last end node's info status */
- size_t remain; /**< remain size */
- uint32_t empty_idx; /**< the next empty node index address */
- uint32_t empty_data; /**< the next empty node's data end address */
- };
- typedef struct tsdb_sec_info *tsdb_sec_info_t;
- struct kv_cache_node {
- uint16_t name_crc; /**< KV name's CRC32 low 16bit value */
- uint16_t active; /**< KV node access active degree */
- uint32_t addr; /**< KV node address */
- };
- typedef struct kv_cache_node *kv_cache_node_t;
- struct sector_cache_node {
- uint32_t addr; /**< sector start address */
- uint32_t empty_addr; /**< sector empty address */
- };
- typedef struct sector_cache_node *sector_cache_node_t;
- /* database structure */
- typedef struct fdb_db *fdb_db_t;
- struct fdb_db {
- const char *name; /**< database name */
- fdb_db_type type; /**< database type */
- union {
- #ifdef FDB_USING_FAL_MODE
- const struct fal_partition *part; /**< flash partition for saving database */
- #endif
- #ifdef FDB_USING_FILE_MODE
- const char *dir; /**< directory path for saving database */
- #endif
- } storage;
- uint32_t sec_size; /**< flash section size. It's a multiple of block size */
- uint32_t max_size; /**< database max size. It's a multiple of section size */
- bool init_ok; /**< initialized successfully */
- bool file_mode; /**< is file mode, default is false */
- bool not_formatable; /**< is can NOT be formated mode, default is false */
- #ifdef FDB_USING_FILE_MODE
- #if defined(FDB_USING_FILE_POSIX_MODE)
- int cur_file; /**< current file object */
- #elif defined(FDB_USING_FILE_LIBC_MODE)
- FILE *cur_file; /**< current file object */
- #endif
- uint32_t cur_sec; /**< current operate sector address */
- #endif
- void (*lock)(fdb_db_t db); /**< lock the database operate */
- void (*unlock)(fdb_db_t db); /**< unlock the database operate */
- void *user_data;
- };
- /* KVDB structure */
- struct fdb_kvdb {
- struct fdb_db parent; /**< inherit from fdb_db */
- struct fdb_default_kv default_kvs; /**< default KV */
- bool gc_request; /**< request a GC check */
- bool in_recovery_check; /**< is in recovery check status when first reboot */
- struct fdb_kv cur_kv;
- struct kvdb_sec_info cur_sector;
- bool last_is_complete_del;
- #ifdef FDB_KV_USING_CACHE
- /* KV cache table */
- struct kv_cache_node kv_cache_table[FDB_KV_CACHE_TABLE_SIZE];
- /* sector cache table, it caching the sector info which status is current using */
- struct sector_cache_node sector_cache_table[FDB_SECTOR_CACHE_TABLE_SIZE];
- #endif /* FDB_KV_USING_CACHE */
- #ifdef FDB_KV_AUTO_UPDATE
- uint32_t ver_num; /**< setting version number for update */
- #endif
- void *user_data;
- };
- typedef struct fdb_kvdb *fdb_kvdb_t;
- /* TSDB structure */
- struct fdb_tsdb {
- struct fdb_db parent; /**< inherit from fdb_db */
- struct tsdb_sec_info cur_sec; /**< current using sector */
- fdb_time_t last_time; /**< last TSL timestamp */
- fdb_get_time get_time; /**< the current timestamp get function */
- size_t max_len; /**< the maximum length of each log */
- uint32_t oldest_addr; /**< the oldest sector start address */
- bool rollover; /**< the oldest data will rollover by newest data, default is true */
- void *user_data;
- };
- typedef struct fdb_tsdb *fdb_tsdb_t;
- /* blob structure */
- struct fdb_blob {
- void *buf; /**< blob data buffer */
- size_t size; /**< blob data buffer size */
- struct {
- uint32_t meta_addr; /**< saved KV or TSL index address */
- uint32_t addr; /**< blob data saved address */
- size_t len; /**< blob data saved length */
- } saved;
- };
- typedef struct fdb_blob *fdb_blob_t;
- #ifdef __cplusplus
- }
- #endif
- #endif /* _FDB_DEF_H_ */
|