嵌入式内部使用文件系统是必须的选项,但是如果不是arm芯片一般都没有完整的带文件系统的操作系统,例如Linux,对于裸机和ucos之类的系统有必要移植嵌入式操作系统,目前用的最多的是FatFs。
网上大量的方法,我这里只是自己做一遍,不以善小而不为嘛。
FatFs官网:http://elm-chan.org/fsw/ff/00index_e.html
下载源码后发现真的没几个文件:
其中diskio.c是移植的时候需要用的,ff.c是文件系统的主体文件,ffsystem.c在打开了动态内存分配的时候需要移植一些代码,ffunicode.c不用管,ffconf.h是配置文件
现在主要需要对付的是diskio.c,我在vs中用内存模拟了一个flash空间
第一步,重写如下函数:
获取盘的状态,因为是内存模拟的,如果是这个盘的话直接返回正确
磁盘初始化,如果用的spi flash需要做一些初始化的工作,这里是内存,所以直接返回正确
磁盘读取函数,其实就是按照sector计算出偏移,然后取若干个sector的数据,在这里定义了一块内存模拟flash
磁盘读取函数,计算偏移后读取相应数量的数据,对于内存来讲很简单
ioctl函数获取虚拟的磁盘的sector数量和大小,如果是spi flash按照实际的来设置
获取时间函数,如果不用直接返回0也可以
第二步,在ffconf.h中设置FF_USE_MKFS为1,以为最新的这里是0
第三步,在integer.h中需要定义#define _TCHAR_DEFINED,这是vs中需要做的,其他平台不需要,这里这么干是为了使用ff.h定义的typedef char TCHAR;
第四步,写个测试程序试试能不能用:
#include "ff.h"
int _tmain(int argc, _TCHAR* argv[])
{
FATFS fs;
FRESULT res;
BYTE work[FF_MAX_SS];
FIL filp;
BYTE buff[1000];
UINT fnum;
res=f_mount(&fs, "0:", 1);
printf("\r\nmount ret=%d", res);
if (res == FR_NO_FILESYSTEM)
{
printf("\r\nno file system, format");
res = f_mkfs("0:", FM_FAT, 0, work, sizeof(work));
if (res == FR_OK)
{
printf("\r\nformat ok");
res = f_mount(NULL, "0:", 1);
res = f_mount(&fs, "0:", 1);
printf(",mount again ret=%d", res);
}
else
{
printf("\r\nformat fail");
}
}
else if (res != FR_OK)
{
printf("\r\nfile system mount fail");
}
else
{
printf("\r\nfile system mount ok");
}
if (res == FR_OK)
{
res = f_open(&filp, "0:/test.txt", FA_CREATE_ALWAYS | FA_WRITE | FA_READ);
if (res == FR_OK)
{
printf("\r\nf_open ok, now write");
memset(buff, 0x55, sizeof(buff));
res = f_write(&filp, buff, sizeof(buff), &fnum);
if (res == FR_OK)
{
printf("\r\nwrite ok, real write len=%d, read...", fnum);
BYTE temp;
temp = f_eof(&filp);
printf("\r\nreach file end=%d", temp);
printf("\r\nfile pointer back to 0");
f_lseek(&filp, 0);
memset(buff, 0, sizeof(buff));
res = f_read(&filp, buff, sizeof(buff), &fnum);
if (res == FR_OK)
{
printf("\r\nread ok, real read len=%d", fnum);
}
else
{
printf("\r\nread fail, res=%d", res);
}
}
else
{
printf("\r\nwrite fail");
}
printf("\r\nclose file");
f_close(&filp);
}
else
{
printf("\r\nf_open fail");
}
}
else
{
printf("\r\nmount or format ret fail");
}
getchar();
return 0;
}
运行结果是正常的:
源码可以在我的下载中找到