armink / EasyFlash

Lightweight IoT device information storage solution: KV/IAP/LOG. | 轻量级物联网设备信息存储方案:参数存储、在线升级及日志存储 ,全新一代版本请移步至 https://github.com/armink/FlashDB
MIT License
1.99k stars 760 forks source link

V4.0 读取不到,写入时返回为0 #142

Closed Moliam97 closed 2 years ago

Moliam97 commented 2 years ago

armink 你好,我现在在另一款芯片(Wifi Soc)上使用easy flash V4.0。在最开始得时候使用easyflash_init返回为NO_ERR,再调用get时,发现返回为0,在使用set也不行。目前不知道是什么问题,看flash内容似乎是没有存进去,但是可以正常写扇区前的标志位。

目前进度

  1. 我查看了STMF1的demo,demo是使用的4.0以前的版本,看到了有save的函数,但是对比4.0的代码就没有save函数。
  2. 我移植了 这几个文件
  3. ef_port.c 中配置了read、erase、write函数,读取扇区头是对的
  4. 遍历时,4页全部有遍历,find_ok一直返回false
  5. cfg.h 配置如下

    define EF_USING_ENV

    ifdef EF_USING_ENV

    define EF_ENV_VER_NUM 0

    endif

    define EF_ERASE_MIN_SIZE (4*1024)

    define EF_WRITE_GRAN (32)

    define EF_START_ADDR 0

    define ENV_AREA_SIZE (16*1024)

    define LOG_AREA_SIZE

    define PRINT_DEBUG

初始化值

wifi_reboot_info_t wifi_reboot_info = { .reboot_params = 3, .reboot_total_cnt = 5, }; static const ef_env default_env_set[] = { "reboot",&wifi_reboot_info,sizeof(wifi_reboot_info_t) }; 此处看文档说,是可以为空没有默认值的,但是后面为了测试,这里还是加上了。

具体代码

代码使用循环调用,记录设备重启次数 ` EfErrCode ret = easyflash_init(); printf("flash init result %d\n", ret);

size_t len = 0;
while(1)
{
    wifi_reboot_info.reboot_total_cnt = 0;
    printf("#########read env\n");
    if (ef_get_env_blob("reboot", &wifi_reboot_info, sizeof(wifi_reboot_info), NULL) == 0)
    {
        printf("########read env end,reboot cnt %d\n", wifi_reboot_info.reboot_total_cnt);
        wifi_reboot_info.reboot_total_cnt++;
        ret = ef_set_env_blob("reboot", &wifi_reboot_info, sizeof(wifi_reboot_info));
        hal_sleep(1000);
        printf("@@@@@@@@ret %d!!!!!!!!!!!!!!!!!!!!\n", ret);
        wifi_reboot_info.reboot_total_cnt = 100000;
        ef_get_env_blob("reboot", &wifi_reboot_info, sizeof(wifi_reboot_info), NULL);
        printf("$$$$$$$$$$read env end,reboot cnt %d\n", wifi_reboot_info.reboot_total_cnt);
        hal_sleep(1000);
    }
    else
    {
        ret = ef_set_env_blob("reboot", &wifi_reboot_info, sizeof(wifi_reboot_info));
        printf("cnt %d,ret %d!!!!!!!!!!!!!!!!!!!!\n", wifi_reboot_info.reboot_total_cnt, ret);
        hal_sleep(1000);
    }
}`

具体打印

循环打印如下数据 #########read env ########read env end,reboot cnt 0 @@@@@@@@ret 0!!!!!!!!!!!!!!!!!!!! $$$$$$$$$$read env end,reboot cnt 100000

Moliam97 commented 2 years ago

EF_ERASE_MIN_SIZE 是4K ENV_AREA_SIZE 是16K,上面显示有误

Moliam97 commented 2 years ago

感谢armink的easy flash,这个问题我已经解决了。是因为变量key定义时并不是4字节对齐。所以在create_env_blob函数中,使用uint32_t *强转的key出现了问题,数据是对的,但是写入flash时,被写入了随机数据。我加了解决办法, static uint32_t user_key[16] = {0}; memset(&user_key, 0, sizeof(user_key)); memcpy(user_key, key, strlen(key)); 定义一个uint32_t的函数在附近,然后每次写入时,进行赋值,在alige_write的时候,key改为user_key解决

Moliam97 commented 2 years ago

解决办法有点粗糙,但是对于目前我使用的场景,是不会有64字节的名字的