/* * Copyright (c) Hisilicon Technologies Co., Ltd.. 2021-2021. All rights reserved. * Description: baseparam database operation function * Author: huanglong * Create: 2021-4-6 */ #include #include #include "securec.h" #include "soc_module.h" #include "soc_errno.h" #include "db_ext.h" /* * the db struct: * DB : | dbcheck | datalen | table 0 | ... ... | table n | * TABLE: | name | datasize | key 0 | ... ...| key n | * KEY: | name | valuelen | value | */ static td_char g_db_check[EXT_DB_CHECK_LEN] = {"###"}; td_s32 ext_db_create(ext_db *db) { td_s32 ret; if (db == TD_NULL) { soc_log_err("ERR: para is null\n"); return TD_FAILURE; } db->data = malloc(EXT_DB_MAX_SIZE); if (db->data == TD_NULL) { soc_log_err("ERR: malloc error\n"); return TD_FAILURE; } memset_s(db->data, EXT_DB_MAX_SIZE, 0x00, EXT_DB_MAX_SIZE); ret = memcpy_s(db->data, EXT_DB_MAX_SIZE, (td_u8 *)g_db_check, EXT_DB_CHECK_LEN); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); free(db->data); db->data = TD_NULL; return ret; } db->data_len = EXT_DB_CHECK_LEN + sizeof(td_u32); ret = memcpy_s((db->data + EXT_DB_CHECK_LEN), (EXT_DB_MAX_SIZE - EXT_DB_CHECK_LEN), (td_u8 *)(&(db->data_len)), sizeof(td_u32)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); free(db->data); db->data = TD_NULL; return ret; } return TD_SUCCESS; } td_s32 ext_db_destroy(ext_db *db) { if (db == TD_NULL) { soc_log_err("ERR: para is null\n"); return TD_FAILURE; } if (db->data_len > EXT_DB_MAX_SIZE) { soc_log_err("ERR: data len too large\n"); return TD_FAILURE; } db->data_len = 0; if (db->data != TD_NULL) { free(db->data); db->data = TD_NULL; } return TD_SUCCESS; } td_s32 ext_db_get_db_from_mem(td_u8 *db_mem, ext_db *db) { td_s32 ret; td_char db_check[EXT_DB_CHECK_LEN] = {0}; if ((db_mem == TD_NULL) || (db == TD_NULL)) { soc_log_err("ERR: para is null\n"); return TD_FAILURE; } ret = memcpy_s(db_check, sizeof(db_check), (td_char *)db_mem, EXT_DB_CHECK_LEN); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } if (strncmp(db_check, g_db_check, strlen(g_db_check)) != 0) { soc_log_err("ERR: this is not a db\n"); return TD_FAILURE; } db->data_len = *(td_u32 *)(db_mem + EXT_DB_CHECK_LEN); if (db->data_len > EXT_DB_MAX_SIZE) { soc_log_err("ERR: db size is error\n"); return TD_FAILURE; } db->data = db_mem; return TD_SUCCESS; } td_s32 ext_db_insert_table(ext_db *db, ext_db_table *table) { td_u32 need_len; td_s32 ret; if ((db == TD_NULL) || (table == TD_NULL)) { soc_log_err("ERR: para is null\n"); return TD_FAILURE; } need_len = EXT_DB_MAX_NAME_LEN + sizeof(td_u32); if (db->data_len + need_len > EXT_DB_MAX_SIZE) { soc_log_err("ERR: db is full\n"); return TD_FAILURE; } table->db = db; ret = memcpy_s((db->data + db->data_len), (EXT_DB_MAX_SIZE - db->data_len), table->name, EXT_DB_MAX_NAME_LEN); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } db->data_len += EXT_DB_MAX_NAME_LEN; table->data_size = 0; ret = memcpy_s((db->data + db->data_len), (EXT_DB_MAX_SIZE - db->data_len), (td_u8 *)(&(table->data_size)), sizeof(td_u32)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } db->data_len += sizeof(td_u32); /* we need to update db datalen */ ret = memcpy_s(db->data + EXT_DB_CHECK_LEN, sizeof(td_u32), (td_u8 *)(&(db->data_len)), sizeof(db->data_len)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } table->data = db->data + db->data_len; return TD_SUCCESS; } td_s32 ext_db_delete_table(const ext_db *db, const td_char table_name[]) { TD_UNUSED(db); TD_UNUSED(table_name); soc_log_err("ERR: delete table is not support\n"); return TD_FAILURE; } td_s32 ext_db_get_table_by_name(ext_db *db, td_char table_name[], ext_db_table *table) { ext_db_table table_tmp; td_u8 *data = TD_NULL; td_s32 ret; if ((db == TD_NULL) || (table == TD_NULL) || (table_name == TD_NULL)) { soc_log_err("ERR: para is null\n"); return TD_FAILURE; } data = db->data + EXT_DB_CHECK_LEN + sizeof(td_u32); while ((td_u32)(data - db->data) < db->data_len) { table_tmp.db = db; ret = memset_s(table_tmp.name, sizeof(table_tmp.name), 0, sizeof(table_tmp.name)); if (ret != TD_SUCCESS) { soc_log_err("ERR: memset_s failed !\n"); return ret; } ret = memcpy_s(table_tmp.name, sizeof(table_tmp.name), data, EXT_DB_MAX_NAME_LEN - 1); if (ret != TD_SUCCESS) { soc_log_err("ERR: memcpy_s failed !\n"); return ret; } data += EXT_DB_MAX_NAME_LEN; if ((td_u32)(data - db->data + sizeof(td_u32)) > db->data_len) { soc_log_err("ERR: pointer has been damaged! data isn't in db now!"); return TD_FAILURE; } table_tmp.data_size = *((td_u32 *)(data)); if ((td_u32)(data - db->data + sizeof(td_u32)) + table_tmp.data_size > db->data_len) { soc_log_err("ERR: got bad data size!"); return TD_FAILURE; } data += sizeof(td_u32); table_tmp.data = data; /* find the table */ if (strncmp(table_tmp.name, table_name, strlen(table_name)) == 0) { *table = table_tmp; break; } else { data += table_tmp.data_size; } } if ((td_u32)(data - db->data) >= db->data_len) { soc_log_err("ERR: can not find table %s\n", table_name); return TD_FAILURE; } return TD_SUCCESS; } td_s32 ext_db_insert_key(ext_db_table *table, ext_db_key *key) { td_u32 need_len; td_s32 ret; if ((table == TD_NULL) || (table->db == TD_NULL) || (key == TD_NULL) || (key->value == TD_NULL)) { soc_log_err("ERR: para is null\n"); return SOC_ERR_PDM_PTR_NULL; } need_len = EXT_DB_MAX_NAME_LEN + sizeof(td_u32) + key->value_size; if (table->db->data_len + need_len > EXT_DB_MAX_SIZE) { soc_log_err("ERR: db is full\n"); return TD_FAILURE; } ret = memcpy_s((table->data + table->data_size), (EXT_DB_MAX_SIZE - table->db->data_len), key->name, EXT_DB_MAX_NAME_LEN); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } table->data_size += EXT_DB_MAX_NAME_LEN; ret = memcpy_s((table->data + table->data_size), (EXT_DB_MAX_SIZE - table->db->data_len - EXT_DB_MAX_NAME_LEN), (td_u8 *)(&(key->value_size)), sizeof(td_u32)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } table->data_size += sizeof(td_u32); ret = memcpy_s((table->data + table->data_size), (EXT_DB_MAX_SIZE - table->db->data_len - EXT_DB_MAX_NAME_LEN - sizeof(td_u32)), (td_u8 *)(key->value), key->value_size); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } table->data_size += key->value_size; /* we need update table datasize */ ret = memcpy_s(table->data - sizeof(td_u32), sizeof(td_u32), (td_u8 *)(&(table->data_size)), sizeof(table->data_size)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } /* we need update db datalen */ table->db->data_len += need_len; ret = memcpy_s(table->db->data + EXT_DB_CHECK_LEN, sizeof(td_u32), (td_u8 *)(&(table->db->data_len)), sizeof(table->db->data_len)); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } return TD_SUCCESS; } td_s32 ext_db_delete_key(const ext_db_table *table, const td_char key_name[]) { TD_UNUSED(table); TD_UNUSED(key_name); soc_log_err("ERR: delete key is not support\n"); return TD_FAILURE; } td_s32 ext_db_get_key_by_name(const ext_db_table *table, td_char *key_name, td_u32 key_len, ext_db_key *key) { ext_db_key key_tmp; td_u8 *data = TD_NULL; td_s32 ret; td_u32 str_len; if ((table == TD_NULL) || (key == TD_NULL) || (key_name == TD_NULL) || (key_len == 0)) { soc_log_err("ERR: para is null\n"); return SOC_ERR_PDM_PTR_NULL; } data = table->data; if (data == TD_NULL) { soc_log_err("data is null\n"); return SOC_ERR_PDM_PTR_NULL; } while ((td_u32)(data - table->data) < table->data_size) { memset_s(key_tmp.name, sizeof(key_tmp.name), 0, sizeof(key_tmp.name)); ret = memcpy_s(key_tmp.name, sizeof(key_tmp.name) - 1, data, EXT_DB_MAX_NAME_LEN - 1); if (ret != TD_SUCCESS) { soc_log_err("memcpy_s failed !\n"); return ret; } data += EXT_DB_MAX_NAME_LEN; key_tmp.value_size = *((td_u32 *)data); data += sizeof(td_u32); key_tmp.value = data; str_len = strlen(key_tmp.name) > key_len ? strlen(key_tmp.name) : key_len; /* find the key */ if (strncmp(key_tmp.name, key_name, str_len) == 0) { *key = key_tmp; break; } else { data += key_tmp.value_size; } } if ((td_u32)(data - table->data) >= table->data_size) { soc_log_info("ERR: can not find key %s\n", key_name); return TD_FAILURE; } return TD_SUCCESS; }