你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

关于FATFS写操作的问题

[复制链接]
meixu 提问时间:2017-6-11 21:21 /
悬赏10ST金币未解决
关于fatfs文件写操作,有个小问题困扰我很长时间了,请教一下

      f_open(&MyFile, (char *)Node, FA_WRITE);
      f_write(&MyFile, UID, 5, (void *)&byteswritten);
      f_write(&MyFile, ID,  9, (void *)&byteswritten);  
      f_write(&MyFile, Msg, 9, (void *)&byteswritten);  
      f_write(&MyFile, &myGPS, 39, (void *)&byteswritten);  
      f_write(&MyFile, "\r\n", 2, (void *)&byteswritten);            
      f_close(&MyFile);
      f_open(&MyFile, (char *)Node, FA_WRITE);
      f_lseek(&MyFile,f_size(&MyFile));

      f_write(&MyFile, UID, 5, (void *)&byteswritten);
      f_write(&MyFile, ID,  9, (void *)&byteswritten);  
      f_write(&MyFile, Msg, 9, (void *)&byteswritten);  
      f_write(&MyFile, &myGPS, 39, (void *)&byteswritten);  
      f_write(&MyFile, "\r\n", 2, (void *)&byteswritten);            
      f_close(&MyFile);

其实我主要是想用f_lseek函数,关闭文件之后下次再写时从结尾开始写,但是我才用上面的方法测试了好几遍,关闭文件前的内容能写进去,但是关闭之后再打开怎么也写不进去,调试时我在每行语句前加了res=  ,来看res,都返回FR_OK,但是U盘里没有后面的内容,请问是什么情况?
Node="0:/BJUT/TEST.TXT"

收藏 评论11 发布时间:2017-6-11 21:21

举报

11个回答
taonsh 回答时间:2017-6-11 21:39:12
本帖最后由 taonsh 于 2017-6-11 21:43 编辑

查一下f_size(&MyFile)是多少?还有你写的东西宏定义还是啥,没看到。
奏奏奏 回答时间:2017-6-12 09:42:39
这是我项目中相关的参考代码:
  1.                         res_debug= f_open(&fsrc3,"历史.csv",FA_OPEN_EXISTING | FA_WRITE);
  2.                         res_debug=f_lseek(&fsrc3,fsrc3.fsize);
  3.                         res_debug=f_write(&fsrc3,"16/08/03 06:26:36,1234567890,阳性,0.777\r\n17/08/03 06:26:36,1234567890,阳性,0.777\r\n18/08/03 06:26:36,1234567890,阳性,0.777\r\n",123,&bw);
复制代码
我觉得你可以消化一下
先用f_open打开
再用f_lseek找到并定位到文件尾部,注意fsrc3.fsize这个输入形参
然后就可以f_write将数据写到文件尾部接着了
meixu 回答时间:2017-6-12 10:39:03
taonsh 发表于 2017-6-11 21:39
查一下f_size(&MyFile)是多少?还有你写的东西宏定义还是啥,没看到。

不是宏定义,那是字符数组的名字
meixu 回答时间:2017-6-12 10:58:10
第一张图片是我调试时的截图,我每次写64个字节,f_size是对的,两个就是128个字节,0x80,第二张图是我U盘的截图,可以看到只有第一次写的64个字节,第二次写的就没有。
123.png
456.png
奏奏奏 回答时间:2017-6-12 11:15:20
打包一个工程你自己看一下吧

我觉得关键在于:f_open(&fsrc3,"历史.csv",FA_OPEN_EXISTING | FA_WRITE)
这里形参要多加一个 FA_OPEN_EXISTING |
因为可能如果不加这个,就会每次都新建一个这个文件

高速写入CSV与XLS表格测试DEMO金龙板.zip

下载

3.51 MB, 下载次数: 1894, 下载积分: ST金币 -1

meixu 回答时间:2017-6-12 16:48:51
奏奏奏 发表于 2017-6-12 11:15
打包一个工程你自己看一下吧

我觉得关键在于:f_open(&fsrc3,"历史.csv",FA_OPEN_EXISTING | FA_WRITE)

嗯嗯,我在官方的例程中试了试,关闭之后能写进去,但是这段程序一到我自己的工程中就不行了,不知道哪儿出了点问题,我再看看。
bwu 回答时间:2017-6-13 09:45:41
你第二次打开的模式可能不对,试下 f_open(&MyFile, (char *)Node, FA_WRITE|FA_READ);   
以只写的方式打开,是先把内容清空,然后再写吧。PC上是这样,FATFS 上不知道是不是这样,我是没有遇到 过。
我是这么做的:
fr = f_open(&file, pathbuf, FA_OPEN_EXISTING|FA_WRITE|FA_READ);     

连续打开写入关闭 30次不会有问题
bwu 回答时间:2017-6-13 09:50:58
下面这个函数中也用到了f_lseek 函数

/*********************************************************************************
向指定文件中添加一条记录
返回值: 0 成功,1 失败
*********************************************************************************/
u8 write_record(record_t *record, u8 wtype, u8 n)
{
    u8 res = 0;

    char *path="0:";
    char pathbuf[48];
    //float dat;
    u32 wr;
   
    FRESULT fr;
    FIL file;  

    if( (record->date.year < 2017 || record->date.year > 2026) ||
        (record->date.mon < 1 || record->date.mon > 12) ||
        (record->date.day < 1 || record->date.day > 31))
    {
        Printf("ERROR: write_record 记录日期错误\r\n");
        return 2;
    }

    memset(pathbuf, 0, sizeof(pathbuf));

    switch(wtype)
    {
        case RECORD_TYPE_YEAR: //年记录
            sprintf(pathbuf, "%s/%d/year.re", path, record->date.year);
            break;
        case RECORD_TYPE_MON:
            sprintf(pathbuf, "%s/%d/%d/mon.re", path,record->date.year, record->date.mon);
            break;
        case RECORD_TYPE_DAY:
            sprintf(pathbuf, "%s/%d/%d/day%d.re", path, record->date.year, record->date.mon, record->date.day);
            break;
        default:
            break;
    }

    //return 0;

    fr = f_open(&file, pathbuf, FA_OPEN_EXISTING|FA_WRITE|FA_READ);        
    if (fr == FR_OK)
    {
        Printf("f_open  %s OK \r\n", pathbuf );  

        //写入内容 -- 24小时,第0条写入日累计数据,共25条数据
        switch(wtype)
        {
            case RECORD_TYPE_YEAR: //年记录
                #if 1
                f_lseek(&file, n*4);
                fr = f_write(&file, &record->yearflow[n], 4, &wr);         

                if (fr == FR_OK)
                {
                    Printf("year: write_record %d,%.2f, %d byte \r\n", n,record->yearflow[n], wr);  
                    res = 0;
                }
                else
                {         
                    Printf("write_record failed(year)!!\r\n");
                                        res = 4;
                }  

                #else  //PC上需要这样做
                dat = record->yearflow[n];
                fread(record->yearflow , sizeof(record->yearflow[0]) , 13 , pFile );
                record->yearflow[n] = dat;
                fwrite(&record->yearflow[n] , sizeof(record->yearflow[n]) , 13 , pFile );
                #endif
                break;
            case RECORD_TYPE_MON: //月记录
                #if 1
                f_lseek(&file, n*4);
                fr = f_write(&file, &record->monflow[n], 4, &wr);         

                if (fr == FR_OK)
                {
                    Printf("mon: write_record %d,%.2f, %d byte \r\n", n,record->monflow[n], wr);  
                    res = 0;
                }
                else
                {         
                    Printf("write_record failed(mon)!!\r\n");
                                         res = 3;
                }  
                #else //PC上需要这样做
                dat = record->monflow[n];
                fread(record->monflow , sizeof(record->monflow[0]) , 32 , pFile );
                record->monflow[n] = dat;
                fwrite(record->monflow , sizeof(record->monflow[0]) , 32 , pFile );
                #endif
                break;
            case RECORD_TYPE_DAY:// 日记录
                #if 1
                f_lseek(&file, n*4);
                fr = f_write(&file, &record->dayflow[n], 4, &wr);         

                if (fr == FR_OK)
                {
                    Printf("day: write_record %d,%.2f, %d byte \r\n", n,record->dayflow[n], wr);  
                    res = 0;
                }
                else
                {         
                    Printf("write_record failed(day)!!\r\n");
                                         res = 2;
                }
                #else //PC上需要这样做
                dat = record->dayflow[n];
                fread(record->dayflow , sizeof(record->dayflow[0]) , 25 , pFile );
                record->dayflow[n] = dat;
                fwrite(record->dayflow , sizeof(record->dayflow[0]) , 25 , pFile );
                #endif // 0
                break;
            default:
                                res = 5;
                break;
        }

        f_close(&file);   
    }
    else
    {
        Printf("f_open %s failed\r\n", pathbuf);  
        res = 1;
    }
   
    return res;
}
meixu 回答时间:2017-6-15 15:52:05
bwu 发表于 2017-6-13 09:45
你第二次打开的模式可能不对,试下 f_open(&MyFile, (char *)Node, FA_WRITE|FA_READ);   
以只写的方式打 ...

试了试,不是这的问题,如上楼所言,我在别的工程里是没有问题的,不知道问什么在现在的工程里就有问题,还得再找找是怎么回事。
12下一页

所属标签

相似问题

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
微信公众号二维码 微信公众号
手机版二维码 手机版