FATFS ff14b版本最简移植

1、前期工作
从FATFS网站上下载相关软件包(http://elm-chan.org/fsw/ff/archives.html)
准备正点原子战舰板SD卡实验例程代码
2、拷贝ff14b到Middlewares文件夹下,并修改文件夹名字为FATFS

3、把FATFS文件夹中的diskio.c和ff.c两个文件加入到新建的Middlewares/FATFS分组下

编译,等看编译结构,修改错误

简单来说,就是diskio.c文件中原来存放的函数在我们程序中不存在。简单粗暴,就是删除这部分代码,后面我们根据自己写的驱动代码再进行添加。
编译,等看编译结构,修改错误

FATFS默认是使能RTC功能的,这里需要用到get_fattime函数,但是该函数没有定义,这里有两个解决办法:① 编写一下这个函数 ② 通过ffconf.h把这个功能关掉
这里演示一下第二个办法:

编译,等看编译结构,修改错误

现在只有warning,因为我们把diskio.c里面的函数内部实现都删除了,也没有返回值,所以提示这个warning。
4、修改ffconf.h文件
从ffconf.h前面往后看配置项,有很多配置项,这里我们明确一下是最简移植,所以简单修改3个配置项即可,FF_USE_STRFUNC、FF_CODE_PAGE和FF_VOLUMES
#define FF_USE_STRFUNC 1

看注释就很清楚,开启这个宏就可以使用字符串辅助函数,如f_gets(),f_putc(),f_printf()。这些函数在进行文件读写操作有用到。
(注:有比较多的配置项都是配置是否可以使用相关函数)
#define FF_CODE_PAGE 936

由于作者是日本人,所以原先这个宏的值是932,而我们要设置成936即为简体中文编码,当不正确设置会导致打开文件失败

#define FF_VOLUMES 1

这个宏是设置有多少个卷,简单来说,就是说你需要挂载多少个设备,在这里,我们只挂载1个SD卡设备,所以设置为1
其他宏可以根据自己需求进行修改,提示一点,假如功能用不了,可以看看宏是否有开启
5、修改diskio.c文件
这里的diskio.c中有5个函数,disk_initialize、disk_status、disk_read、disk_write、disk_ioctl
首先先把物理磁盘号的宏设置好

编写disk_status函数

该函数的功能是获取驱动器状态的,当然大家可以根据返回状态进行编写,这里可以直接返回“RES_OK”
编写disk_initialize函数

该函数的功能用于对硬件进行初始化,注意需要包含相对应的头文件

编写disk_read函数

该函数的功能是用于SD卡中读取数据
编写disk_write函数

该函数的功能用于向SD卡写入数据。
(注:这里涉及到FF_FS_READONLY宏,默认只读功能关闭,写操作相关函数才能使用)

编写disk_ioctl函数

该函数的功能用于控制设备实现指定功能,用于辅助FATFS中的其他API
6、编写测试代码

函数内部比较简单,用到f_mount函数、f_open函数、f_write函数和f_read函数,以及f_tell和f_lseek函数。
简单说一下函数做了什么事情:
① 通过f_mount挂载SD卡设备
② 通过f_open打开文件(这里注意函数的第三个参数,创建一个文件,可读可写),这里的文件是空的
③ 打开文件成功后,通过f_size看看文件大小,通过f_read读取一下数据,假如有数据读取到,那就打印出来原始数据。由于这里属于新建文件,所以读取不到信息的。
④ 通过f_write写入数据“33689745”
⑤ 继续调用f_write在后面继续写入"2222"
⑥ 由于使用f_write会把读写指针往后偏移,所以读取数据前,使用f_lseek进行偏移到头部,然后再通过f_read读取数据并打印
⑦ 操作完成,通过f_close关闭文件
通过串口助手可以看到,打印信息

打开SD卡,查看到有TEST.TXT文件,内容如下:

注意一下:定义FATFS和FIL变量,我们采用的是定义一个指向FATFS和FIL的指针变量,然后通过内存管理进行申请内存。这样会减少内存的开销。

假如我们定义局部变量的话,这样子占用的内存空间太大了。
还有一种方式就是定义成全局变量进行使用。
上面测试代码中用到的文件系统开放API函数介绍
通过f_mount函数对磁盘进行挂载,在这里就是SD卡了。

注:常见错误返回值:FR_NOT_ENABLED和FR_NO_FILESYSTEM。

假如是FR_NOT_ENABLED,这时候你得检查一下是否已经申请到内存
假如是FR_NO_FILESYSTEM,这时候你得检查一下SD卡的文件系统是否被破坏了,或者不是FAT32。
通过f_open函数对文件进行打开。

注:函数的形参mode比较重要,可以理解为对形参path文件的操作权限

FA_READ就是读权限、
FA_WRITE就是写权限,
FA_OPEN_EXISTING就是打开已有的文件,没有该文件会失败
FA_CREATE_NEW就是创建一个新文件,已存在文件会出现提示FR_EXIST错误
FA_CREATE_ALWAYS就是创建一个文件,假如已存在的话,会对其进行覆盖
FA_OPEN_ALWAYS就是打开一个文件,假如不存在的话,就会创建
FA_OPEN_APPEND功能和FA_OPEN_ALWAYS一样,只不过读写指针会在文件末尾
通过f_read函数进行文件数据读取

注:btr是你要求要读多少数据,而br是已经读到多少数据,可以对br进行判断看是不是读完了。
通过f_write函数进行文件数据写入

这里的参数跟f_write差不多。这个函数需要注意的是写完数据后,它的读写指针会在尾部,所以你想对写入内容进行读取,就需要重新把读写指针偏移到开头,用到f_lseek函数。
注:操作完之后,需要f_close,非常作用,不然后果就是啥都没有干
