[fdb] move the db oldest_addr definition into struct fdb_db.

This commit is contained in:
朱天龙 (Armink) 2023-04-21 23:55:31 +08:00
parent 04a3f475e2
commit 7fd3db6740
3 changed files with 53 additions and 58 deletions

View File

@ -264,6 +264,7 @@ struct fdb_db {
} 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 */
uint32_t oldest_addr; /**< the oldest sector start address */
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 */
@ -301,7 +302,7 @@ struct fdb_kvdb {
#ifdef FDB_KV_AUTO_UPDATE
uint32_t ver_num; /**< setting version number for update */
#endif
uint32_t oldest_addr;
void *user_data;
};
typedef struct fdb_kvdb *fdb_kvdb_t;
@ -313,7 +314,6 @@ struct fdb_tsdb {
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;
@ -336,4 +336,5 @@ typedef struct fdb_blob *fdb_blob_t;
}
#endif
#endif /* _FDB_DEF_H_ */
#endif /* _FDB_DEF_H_ */

View File

@ -81,6 +81,7 @@
#define db_init_ok(db) (((fdb_db_t)db)->init_ok)
#define db_sec_size(db) (((fdb_db_t)db)->sec_size)
#define db_max_size(db) (((fdb_db_t)db)->max_size)
#define db_oldest_addr(db) (((fdb_db_t)db)->oldest_addr)
#define db_lock(db) \
do { \
@ -125,6 +126,7 @@ struct gc_cb_args {
fdb_kvdb_t db;
size_t cur_free_size;
size_t setting_free_size;
uint32_t traversed_len;
};
struct check_oldest_addr_cb_args {
@ -468,27 +470,27 @@ static fdb_err_t read_sector_info(fdb_kvdb_t db, uint32_t addr, kv_sec_info_t se
return result;
}
static uint32_t get_next_sector_addr(fdb_kvdb_t db, kv_sec_info_t pre_sec)
static uint32_t get_next_sector_addr(fdb_kvdb_t db, kv_sec_info_t pre_sec, uint32_t traversed_len)
{
uint32_t next_addr;
uint32_t cur_block_size;
if (pre_sec->addr == FAILED_ADDR) {
/* the next sector is on the top of the database */
return 0;
if (pre_sec->combined == SECTOR_NOT_COMBINED) {
cur_block_size = db_sec_size(db);
} else {
/* check KV sector combined */
if (pre_sec->combined == SECTOR_NOT_COMBINED) {
next_addr = pre_sec->addr + db_sec_size(db);
cur_block_size = pre_sec->combined * db_sec_size(db);
}
if (traversed_len + cur_block_size <= db_max_size(db)) {
/* if reach to the end, roll back to the first sector */
if (pre_sec->addr + cur_block_size < db_max_size(db)) {
return pre_sec->addr + cur_block_size;
} else {
next_addr = pre_sec->addr + pre_sec->combined * db_sec_size(db);
}
/* check range */
if (next_addr < db_max_size(db)) {
return next_addr;
} else {
/* no sector */
return FAILED_ADDR;
/* the next sector is on the top of the database */
return 0;
}
} else {
/* finished */
return FAILED_ADDR;
}
}
@ -496,11 +498,12 @@ static void kv_iterator(fdb_kvdb_t db, fdb_kv_t kv, void *arg1, void *arg2,
bool (*callback)(fdb_kv_t kv, void *arg1, void *arg2))
{
struct kvdb_sec_info sector;
uint32_t sec_addr;
uint32_t sec_addr, traversed_len = 0;
sec_addr = 0;
sec_addr = db_oldest_addr(db);
/* search all sectors */
do {
traversed_len += db_sec_size(db);
if (read_sector_info(db, sec_addr, &sector, false) != FDB_NO_ERR) {
continue;
}
@ -519,7 +522,7 @@ static void kv_iterator(fdb_kvdb_t db, fdb_kv_t kv, void *arg1, void *arg2,
}
} while ((kv->addr.start = get_next_kv_addr(db, &sector, kv)) != FAILED_ADDR);
}
} while ((sec_addr = get_next_sector_addr(db, &sector)) != FAILED_ADDR);
} while ((sec_addr = get_next_sector_addr(db, &sector, traversed_len)) != FAILED_ADDR);
}
static bool find_kv_cb(fdb_kv_t kv, void *arg1, void *arg2)
@ -822,13 +825,12 @@ static fdb_err_t update_sec_status(fdb_kvdb_t db, kv_sec_info_t sector, size_t n
static void sector_iterator(fdb_kvdb_t db, kv_sec_info_t sector, fdb_sector_store_status_t status, void *arg1, void *arg2,
bool (*callback)(kv_sec_info_t sector, void *arg1, void *arg2), bool traversal_kv)
{
uint32_t sec_addr;
uint32_t sec_iterate_end_addr;
uint32_t sec_addr, traversed_len = 0;
/* search all sectors */
sec_addr = db->oldest_addr;
sec_iterate_end_addr = db->oldest_addr;
sec_addr = db_oldest_addr(db);
do {
traversed_len += db_sec_size(db);
read_sector_info(db, sec_addr, sector, false);
if (status == FDB_SECTOR_STORE_UNUSED || status == sector->status.store) {
if (traversal_kv) {
@ -839,12 +841,7 @@ static void sector_iterator(fdb_kvdb_t db, kv_sec_info_t sector, fdb_sector_stor
return;
}
}
/* if reach to the end, roll back to the first sector */
if ((sec_addr = get_next_sector_addr(db, sector)) == FAILED_ADDR) {
sec_addr = 0;
}
} while (sec_addr != sec_iterate_end_addr);
} while ((sec_addr = get_next_sector_addr(db, sector, traversed_len)) != FAILED_ADDR);
}
static bool sector_statistics_cb(kv_sec_info_t sector, void *arg1, void *arg2)
@ -906,6 +903,7 @@ static fdb_err_t del_kv(fdb_kvdb_t db, const char *key, fdb_kv_t old_kv, bool co
{
fdb_err_t result = FDB_NO_ERR;
uint32_t dirty_status_addr;
struct fdb_kv kv = { 0 };
#if (KV_STATUS_TABLE_SIZE >= FDB_DIRTY_STATUS_TABLE_SIZE)
uint8_t status_table[KV_STATUS_TABLE_SIZE];
@ -915,7 +913,6 @@ static fdb_err_t del_kv(fdb_kvdb_t db, const char *key, fdb_kv_t old_kv, bool co
/* need find KV */
if (!old_kv) {
struct fdb_kv kv;
/* find KV */
if (find_kv(db, key, &kv)) {
old_kv = &kv;
@ -1069,8 +1066,8 @@ static bool do_gc(kv_sec_info_t sector, void *arg1, void *arg2)
struct fdb_kv kv;
struct gc_cb_args *gc = (struct gc_cb_args *)arg1;
fdb_kvdb_t db = gc->db;
uint32_t sec_addr;
gc->traversed_len += db_sec_size(db);
if (sector->check_ok && (sector->status.dirty == FDB_SECTOR_DIRTY_TRUE || sector->status.dirty == FDB_SECTOR_DIRTY_GC)) {
uint8_t status_table[FDB_DIRTY_STATUS_TABLE_SIZE];
/* change the sector status to GC */
@ -1090,14 +1087,7 @@ static bool do_gc(kv_sec_info_t sector, void *arg1, void *arg2)
gc->cur_free_size += db_sec_size(db) - SECTOR_HDR_DATA_SIZE;
FDB_DEBUG("Collect a sector @0x%08" PRIX32 "\n", sector->addr);
/* update oldest_addr for next GC sector format */
sec_addr = get_next_sector_addr(db, sector);
/*sec_addr reached db_max_size(db), roll back to the first sector*/
if (sec_addr == FAILED_ADDR) {
db->oldest_addr = 0;
} else {
db->oldest_addr = sec_addr;
}
FDB_DEBUG("oldest_addr is @0x%08" PRIX32 "\n", db->oldest_addr);
db_oldest_addr(db) = get_next_sector_addr(db, sector, gc->traversed_len);
if (gc->cur_free_size >= gc->setting_free_size)
return true;
}
@ -1109,7 +1099,7 @@ static void gc_collect_by_free_size(fdb_kvdb_t db, size_t free_size)
{
struct kvdb_sec_info sector;
size_t empty_sec = 0;
struct gc_cb_args arg = { db, 0, free_size };
struct gc_cb_args arg = { db, 0, free_size, 0 };
/* GC check the empty sector number */
sector_iterator(db, &sector, FDB_SECTOR_STORE_EMPTY, &empty_sec, NULL, gc_check_cb, false);
@ -1749,10 +1739,10 @@ fdb_err_t fdb_kvdb_init(fdb_kvdb_t db, const char *name, const char *path, struc
db->default_kvs.kvs = NULL;
}
db->oldest_addr = 0;
db_oldest_addr(db) = 0;
sector_iterator(db, &sector, FDB_SECTOR_STORE_UNUSED, &arg, NULL, check_oldest_addr_cb, false);
db->oldest_addr = arg.sector_oldest_addr;
FDB_DEBUG("oldest_addr is @0x%08" PRIX32 "\n", db->oldest_addr);
db_oldest_addr(db) = arg.sector_oldest_addr;
FDB_DEBUG("The oldest addr is @0x%08" PRIX32 "\n", db_oldest_addr(db));
/* there is at least one empty sector for GC. */
FDB_ASSERT((FDB_GC_EMPTY_SEC_THRESHOLD > 0 && FDB_GC_EMPTY_SEC_THRESHOLD < SECTOR_NUM))
@ -1828,7 +1818,10 @@ bool fdb_kv_iterate(fdb_kvdb_t db, fdb_kv_iterator_t itr)
{
struct kvdb_sec_info sector;
fdb_kv_t kv = &(itr->curr_kv);
uint32_t traversed_len = 0;
do {
traversed_len += db_sec_size(db);
if (read_sector_info(db, itr->sector_addr, &sector, false) == FDB_NO_ERR) {
if (sector.status.store == FDB_SECTOR_STORE_USING || sector.status.store == FDB_SECTOR_STORE_FULL) {
if (kv->addr.start == 0) {
@ -1854,7 +1847,7 @@ bool fdb_kv_iterate(fdb_kvdb_t db, fdb_kv_iterator_t itr)
* the kv->addr.start is set to the new sector.addr + SECTOR_HDR_DATA_SIZE.
*/
kv->addr.start = 0;
} while ((itr->sector_addr = get_next_sector_addr(db, &sector)) != FAILED_ADDR);
} while ((itr->sector_addr = get_next_sector_addr(db, &sector, traversed_len)) != FAILED_ADDR);
/* Finally we have iterated all the KVs. */
return false;
}

View File

@ -53,6 +53,7 @@
#define db_init_ok(db) (((fdb_db_t)db)->init_ok)
#define db_sec_size(db) (((fdb_db_t)db)->sec_size)
#define db_max_size(db) (((fdb_db_t)db)->max_size)
#define db_oldest_addr(db) (((fdb_db_t)db)->oldest_addr)
#define db_lock(db) \
do { \
@ -356,9 +357,9 @@ static fdb_err_t update_sec_status(fdb_tsdb_t db, tsdb_sec_info_t sector, fdb_bl
if (sector->status != FDB_SECTOR_STORE_EMPTY) {
/* calculate the oldest sector address */
if (new_sec_addr + db_sec_size(db) < db_max_size(db)) {
db->oldest_addr = new_sec_addr + db_sec_size(db);
db_oldest_addr(db) = new_sec_addr + db_sec_size(db);
} else {
db->oldest_addr = 0;
db_oldest_addr(db) = 0;
}
format_sector(db, new_sec_addr);
read_sector_info(db, new_sec_addr, &db->cur_sec, false);
@ -461,8 +462,8 @@ void fdb_tsl_iter(fdb_tsdb_t db, fdb_tsl_cb cb, void *arg)
return;
}
sec_addr = db->oldest_addr;
db_lock(db);
sec_addr = db_oldest_addr(db);
db_lock(db);
/* search all sectors */
do {
traversed_len += db_sec_size(db);
@ -597,7 +598,7 @@ void fdb_tsl_iter_by_time(fdb_tsdb_t db, fdb_time_t from, fdb_time_t to, fdb_tsl
}
if(from <= to) {
start_addr = db->oldest_addr;
start_addr = db_oldest_addr(db);
get_sector_addr = get_next_sector_addr;
get_tsl_addr = get_next_tsl_addr;
} else {
@ -777,7 +778,7 @@ static void tsl_format_all(fdb_tsdb_t db)
sector.addr = 0;
sector_iterator(db, &sector, FDB_SECTOR_STORE_UNUSED, db, NULL, format_all_cb, false);
db->oldest_addr = 0;
db_oldest_addr(db) = 0;
db->cur_sec.addr = 0;
db->last_time = 0;
/* read the current using sector info */
@ -904,7 +905,7 @@ fdb_err_t fdb_tsdb_init(fdb_tsdb_t db, const char *name, const char *path, fdb_g
db->max_len = max_len;
/* default rollover flag is true */
db->rollover = true;
db->oldest_addr = FDB_DATA_UNUSED;
db_oldest_addr(db) = FDB_DATA_UNUSED;
db->cur_sec.addr = FDB_DATA_UNUSED;
/* must less than sector size */
FDB_ASSERT(max_len < db_sec_size(db));
@ -935,19 +936,19 @@ fdb_err_t fdb_tsdb_init(fdb_tsdb_t db, const char *name, const char *path, fdb_g
/* db->cur_sec is the latest sector, and the next is the oldest sector */
if (latest_addr + db_sec_size(db) >= db_max_size(db)) {
/* db->cur_sec is the the bottom of the database */
db->oldest_addr = 0;
db_oldest_addr(db) = 0;
} else {
db->oldest_addr = latest_addr + db_sec_size(db);
db_oldest_addr(db) = latest_addr + db_sec_size(db);
}
}
FDB_DEBUG("TSDB (%s) oldest sectors is 0x%08" PRIX32 ", current using sector is 0x%08" PRIX32 ".\n", db_name(db), db->oldest_addr,
FDB_DEBUG("TSDB (%s) oldest sectors is 0x%08" PRIX32 ", current using sector is 0x%08" PRIX32 ".\n", db_name(db), db_oldest_addr(db),
db->cur_sec.addr);
/* read the current using sector info */
read_sector_info(db, db->cur_sec.addr, &db->cur_sec, true);
/* get last save time */
if (db->cur_sec.status == FDB_SECTOR_STORE_USING) {
db->last_time = db->cur_sec.end_time;
} else if (db->cur_sec.status == FDB_SECTOR_STORE_EMPTY && db->oldest_addr != db->cur_sec.addr) {
} else if (db->cur_sec.status == FDB_SECTOR_STORE_EMPTY && db_oldest_addr(db) != db->cur_sec.addr) {
struct tsdb_sec_info sec;
uint32_t addr = db->cur_sec.addr;