Fatfs文件系统2015-04

Fatfs文件系统2015-04
Fatfs文件系统2015-04

2015-04-18

FATFS文件管理系统

一、FATFS简介

FATFS 是一个完全免费开源的FAT 文件系统模块,专门为小型的嵌入式系统而设计。它完全用标准 C 语言编写,所以具有良好的硬件平台独立性,可以移植到8051、PIC、AVR、SH、Z80、H8、ARM 等系列单片机上而只需做简单的修改。它支持FATl2、FATl6 和FAT32,支持多个存储媒介;有独立的缓冲区,可以对多个文件进行读/写,并特别对8 位单片机和16 位单片机做了优化。

FATFS 的特点有:

? 代码量少、效率高

? 多种配置选项

? 支持多卷(物理驱动器或分区,最多10 个卷)

? 多个ANSI/OEM 代码页包括DBCS

? 支持长文件名、ANSI/OEM 或Unicode

? 支持RTOS

? 支持多种扇区大小

? 只读、最小化的API 和I/O 缓冲区等

二、FATFS层次结构图

最顶层是应用层,使用者无需理会FATFS 的内部结构和复杂的FAT 协议,只需要调用FATFS 模块提供给用户的一系列应用接口函数,如f_open,f_read,f_write 和f_close 等,就可以像在PC 上读/写文件那样简单。中间层FATFS 模块,实现了FAT 文件读/写协议。FATFS 模块提供的是ff.c 和ff.h。除非有必要,使用者一般不用修改,使用时将头文件直接包含进去即可。需要我们编写移植代码的是FATFS 模块提供的底层接口,它包括存储媒介读/写接口(disk I/O)和供给文件创建修改时间的实时时钟。

三、FATFS源码

1.源码下载

(1)在https://www.360docs.net/doc/2a18067443.html,/fsw/ff/00index_e.html下载FatFs源码R0.10b版本;

(2)打开压缩包,里面有doc和src两个文件夹,doc是对FatFs的一些介绍及

更新说明,src为FatFs的源码;

2.FatFs源码介绍

(1)与硬件平台无关的文件

?ffconf.h FATFS 模块配置文件

?ff.h FATFS 和应用模块公用的包含文件

?ff.c FATFS 模块

?diskio.h FATFS 和disk I/O 模块公用的包含文件

?interger.h 数据类型定义

?option 可选的外部功能(比如支持中文等)

(2) 与硬件平台相关的文件

?diskio.c FATFS 和disk I/O 模块接口层文件

(3) 移植时,重要的选项配置

?_FS_TINY。这个选项在R0.07 版本中开始出现,之前的版本都是以独立的C 文件

出现(FATFS 和Tiny FATFS),有了这个选项之后,两者整合在一起了,使用起来

更方便。我们使用FATFS,所以把这个选项定义为0 即可。

?_FS_READONLY。这个用来配置是不是只读,本章我们需要读写都用,所以这里设

置为0 即可。

?_USE_STRFUNC。这个用来设置是否支持字符串类操作,比如f_putc,f_puts 等,

本章我们需要用到,故设置这里为1。

?_USE_MKFS。这个用来定时是否使能格式化,本章需要用到,所以设置这里为1。

?_USE_FASTSEEK。这个用来使能快速定位,我们设置为1,使能快速定位。

?_USE_LABEL。这个用来设置是否支持磁盘盘符(磁盘名字)读取与设置。我们设

置为1,使能,就可以通过相关函数读取或者设置磁盘的名字了。

?_CODE_PAGE。这个用于设置语言类型,包括很多选项(见FATFS 官网说明),我

们这里设置为936,即简体中文(GBK 码,需要c936.c 文件支持,该文件在

option 文件夹)。

?_USE_LFN。该选项用于设置是否支持长文件名(还需要_CODE_PAGE 支持),取值

范围为0~3。0,表示不支持长文件名,1~3 是支持长文件名,但是存储地方不

一样,我们选择使用3,通过ff_memalloc 函数来动态分配长文件名的存储区域。

?_VOLUMES。用于设置FATFS 支持的逻辑设备数目,我们设置为2,即支持2 个

设备。

?_MAX_SS。扇区缓冲的最大值,一般设置为512。

四、FATFS源码移植步骤

1.数据类型

在integer.h文件中配置数据类型,根据编译器类型配置,如VC中int2字节,在KeilMDK中int占4字节。Integer.h中的数据类型与MDK中相同,所见就不需要进行配置

2.配置FatFs

在ffconf.h中配置上面介绍的重要的选项配置和其他配置,重要的配置按照上面介绍的配置就可以了,其他配置保持默认;

3.函数编写

在diskio中编写底层驱动函数

?disk_initialize - Initialize disk drive

?disk_status - Get disk status

?disk_read - Read sector(s)

?disk_write - Write sector(s)

?disk_ioctl - Control device dependent features

?get_fattime - Get current time

首先需要定义存储器的号码,我们定义SD卡为0 SPI FLASH为1,还需根据不同存储器的类型来定义存储的sector和block,下面介绍必须的六种底层驱动函数

(1)disk_initialize

DSTATUS disk_initialize (

BYTE pdrv /* Physical drive nmuber (0..) */

){

u8 res=0;

switch(pdrv)

{

case SD_CARD: res=SD_Init();//SD 卡初始化

break;

case EX_FLASH: //外部flash

W25QXX_Init();

FLASH_SECTOR_COUNT=2048*12;

break;

default:

res=1;

}

if(res) return STA_NOINIT;

else return 0; //初始化成功

}

对SD卡和SPI FLASH存储进行初始化

DSTATUS disk_status (

BYTE pdrv /* Physical drive nmuber (0..) */

)

{

return 0;

}

返回0即可,用不到

(3)disk_read

DRESULT disk_read (

BYTE pdrv, /* Physical drive nmuber (0..) */

BYTE *buff, /* Data buffer to store read data */

DWORD sector, /* Sector address (LBA) */

UINT count /* Number of sectors to read (1..128) */

){

u8 res=0;

if (!count)return RES_PARERR;//count 不能等于0,否则返回参数错误switch(pdrv)

{

case SD_CARD: //SD 卡

res=SD_ReadDisk(buff,sector,count);

break;

case EX_FLASH: //外部flash

for(;count>0;count--)

{

W25QXX_Read(buff,sector*FLASH_SECTOR_SIZE,FLASH_SECTOR_SIZE);

sector++;

buff+=FLASH_SECTOR_SIZE;

}

res=0;

break;

default:

res=1;

}

if(res==0x00) return RES_OK;

else return RES_ERROR;

}

根据存储器类型,调用存储器相关的读取程序

#if _USE_WRITE

DRESULT disk_write (

BYTE pdrv, /* Physical drive nmuber (0..) */

const BYTE *buff, /* Data to be written */

DWORD sector, /* Sector address (LBA) */

UINT count /* Number of sectors to write (1..128) */

)

{

u8 res=0;

if (!count)return RES_PARERR;//count不能等于0,否则返回参数错误

switch(pdrv)

{

case SD_CARD://SD卡

res=SD_WriteDisk((u8*)buff,sector,count);

while(res)//写出错

{

SD_Init(); //重新初始化SD卡

res=SD_WriteDisk((u8*)buff,sector,count);

//printf("sd wr error:%d\r\n",res);

}

break;

case EX_FLASH://外部flash

for(;count>0;count--)

{

W25QXX_Write((u8*)buff,sector*FLASH_SECTOR_SIZE,FLASH_SECTOR_SIZE);

sector++;

buff+=FLASH_SECTOR_SIZE;

}

res=0;

break;

default:

res=1;

}

//处理返回值,将SPI_SD_driver.c的返回值转成ff.c的返回值

if(res == 0x00)return RES_OK;

else return RES_ERROR;

}

#endif

同disk_read函数相同,调用各存储器写入函数进行读写,API接口

(5)disk_ioctl

//其他表参数的获得

//drv:磁盘编号0~9

//ctrl:控制代码

//*buff:发送/接收缓冲区指针

#if _USE_IOCTL

DRESULT disk_ioctl (

BYTE pdrv, /* Physical drive nmuber (0..) */

BYTE cmd, /* Control code */

void *buff /* Buffer to send/receive control data */

)

{

DRESULT res;

if(pdrv==SD_CARD)//SD卡

{

switch(cmd)

{

case CTRL_SYNC:

res = RES_OK;

break;

case GET_SECTOR_SIZE:

*(DWORD*)buff = 512;

res = RES_OK;

break;

case GET_BLOCK_SIZE:

*(WORD*)buff = SDCardInfo.CardBlockSize;

res = RES_OK;

break;

case GET_SECTOR_COUNT:

*(DWORD*)buff = SDCardInfo.CardCapacity/512;

res = RES_OK;

break;

default:

res = RES_PARERR;

break;

}

}else if(pdrv==EX_FLASH) //外部FLASH

{

switch(cmd)

{

case CTRL_SYNC:

res = RES_OK;

break;

case GET_SECTOR_SIZE:

*(WORD*)buff = FLASH_SECTOR_SIZE;

res = RES_OK;

break;

case GET_BLOCK_SIZE:

*(WORD*)buff = FLASH_BLOCK_SIZE;

res = RES_OK;

break;

case GET_SECTOR_COUNT:

*(DWORD*)buff = FLASH_SECTOR_COUNT;

res = RES_OK;

break;

default:

res = RES_PARERR;

break;

}

}else res=RES_ERROR;//其他的不支持

return res;

}

#endif

获得存储器信息,存储容量,sector block等

(6)get_fattime函数

没有用到,返回0即可

(7)memalloc 和memfree函数等在长文件名功能时会应用

五、FATFS主要API函数及类型结构体和全局变量的介绍

1.结构体

(1)FATFS结构体

FATFS 结构(文件系统对象)用来保存独立逻辑驱动器动态工作区域。这个结构由应用程序给定,使用f_mount 函数注册/注销FATFS 模块。在执行f_mount 或媒体发生变化后,访问第一个文件时FATFS 被初始化。其他应用程序不能改变结构的任何成员变量。

typedef struct {

BYTE fs_type; /* FAT sub-type (0:Not mounted) 0表示为挂载*/

BYTE drv; /* Physical drive number */ 物理地址SD:0 FLASH1

BYTE csize; /* Sectors per cluster (1,2,4...128) */一个簇有多少扇区

BYTE n_fats; /* Number of FAT copies (1 or 2) */文件分配表数目

BYTE wflag; /* win[] flag (b0:dirty) */标记文件是否改写过

BYTE fsi_flag; /* FSINFO flags (b7:disabled, b0:dirty) */标记文件系统信

息是否改动过WORD id; /* File system mount ID */文件系统挂载的ID

WORD n_rootdir; /* Number of root directory entries (FAT12/16) */根目录

区入口,用于FAT12/16,#if _MAX_SS != _MIN_SS 如果在ffconf中定义的不相等,定义的是一个

范围,在这里配置设置存储器sector大小

WORD ssize; /* Bytes per sector (512, 1024, 2048 or 4096) */

#endif

#if _FS_REENTRANT 如果可重入,定义同步对象

_SYNC_t s obj; /* Identifier of sync object */

#endif

#if !_FS_READONLY 如果为可读写

DWORD last_clust; /* Last allocated cluster */上一个被分配的簇

DWORD free_clust; /* Number of free clusters */空闲簇

#endif

#if _FS_RPATH 允许相对目录使使用,存储当前目录起始簇

DWORD cdir; /* Current directory start cluster (0:root) */

#endif

DWORD n_fatent; /* Number of FAT entries, = number of clusters + 2 */ FAT条目数量,等于簇+2 DWORD fsize; /* Sectors per FAT */每个FAT扇区数量

DWORD volbase; /* Volume start sector */卷起始扇区???

DWORD fatbase; /* FAT start sector */FAT起始扇区

DWORD dirbase; /* Root directory start sector (FAT32:Cluster#) */

根目录起始扇区

DWORD database; /* Data start sector */数据起始扇区

DWORD winsect; /* Current sector appearing in the win[] */当前缓冲区

存储的扇区号BYTE win[_MAX_SS]; /* Disk access window for Directory, FAT (and file data at tiny cfg) */单个扇区缓存

} FATFS;

(2)FIL结构体

FIL 结构(文件对象)用来保存打开文件的状态。它由f_open 函数创建,由f_close 函数废弃。除cltbl 外,其成员不能被其他应用程序改变。注意:在non-tiny 配置情况下,在结构体中定义了一个扇区缓冲区,因此FIL 结构不能够被定义为自动变量。

typedef struct {

FATFS* fs; /* Pointer to the related file system object (**do not change order**) */ 指向相关文件系统的指针

WORD id; /* Owner file system mount ID (**do not change order**) */所在文件系统的挂在编号,SD:0 FLASH:1

BYTE flag; /* Status flags */ 状态标志

BYTE err; /* Abort flag (error code) */错误标志

DWORD fptr; /* File read/write pointer (Zeroed on file open) */

文件读写指针,打开文件时清零

DWORD fsize; /* File size */ 文件大小

DWORD sclust; /* File start cluster (0:no cluster chain, always 0 when fsize is 0) */ 文件起始簇

DWORD clust; /* Current cluster of fpter (not valid when fprt is 0) */ fpter指向的文件所在的当前簇DWORD dsect; /* Sector number appearing in buf[] (0:invalid) */ #if !_FS_READONLY 当前数据扇区

DWORD dir_sect; /* Sector number containing the directory entry */

含有目录的扇区数量

BYTE* dir_ptr; /* Pointer to the directory entry in the win[] */

目录入口指针,(目录应该缓存在win[]中,猜测)#endif

#if _USE_FASTSEEK 指向簇链接映射表的指针

DWORD* cltbl; /* Pointer to the cluster link map table (Nulled on file open) */

#endif

#if _FS_LOCK

UINT lockid; /* File lock ID origin from 1 (index of file semaphore table Files[]) */

#endif

#if !_FS_TINY 数据读写缓冲

BYTE buf[_MAX_SS]; /* File private data read/write window */

#endif

} FIL;

(3)DIR 目录结构体

DIR 结构体被f_opendir,f_readdir 函数用来读取工作区目录。其他应用程序不能改变其成员变量。

typedef struct {

FATFS* fs; /* Pointer to the owner file system object (**do not change order**) */ 文件系统指针

WORD id; /* Owner file system mount ID (**do not change order**) */ 文件系统挂在编号SD:0 FALSH:1 WORD index; /* Current read/write index number */

当前读写目录索引号

DWORD sclust; /* Table start cluster (0:Root dir) */

根目录表起始簇

DWORD clust; /* Current cluster */

当前簇,当前扇区

DWORD sect; /* Current sector */

当前短文件入口指针

BYTE* dir; /* Pointer to the current SFN entry in the win[] */

BYTE* fn; /* Pointer to the SFN (in/out)

{file[8],ext[3],status[1]} */文件指针SFN short file name

#if _FS_LOCK

UINT lockid; /* File lock ID (index of file semaphore table Files[]) */

#endif

#if _USE_LFN 指向长文件名的指针缓冲

WCHAR* lfn; /* Pointer to the LFN working buffer */

WORD lfn_idx; /* Last matched LFN index number (0xFFFF:No LFN) */ #endif 最后匹配的长文件名索引号

} DIR;

(4)FILINFO 文件Information结构体,存储文件的信息

typedef struct {

DWORD fsize; /* File size */ 文件大小

WORD fdate; /* Last modified date */最后更改日期

WORD ftime; /* Last modified time */最后更改时间

BYTE fattrib; /* Attribute */属性

TCHAR fname[13]; /* Short file name (8.3 format) */短文件名

#if _USE_LFN 指向长文件名的指针

TCHAR* lfname; /* Pointer to the LFN buffer */

UINT lfsize; /* Size of LFN buffer in TCHAR */

长文件名缓冲区大小

#endif

} FILINFO;

(5) FRESULT 配置状态结构体

typedef enum {

FR_OK = 0, /* (0) Succeeded */

FR_DISK_ERR, /* (1) A hard error occurred in the low level disk I/O layer */

FR_INT_ERR, /* (2) Assertion failed */

FR_NOT_READY, /* (3) The physical drive cannot work */

FR_NO_FILE, /* (4) Could not find the file */

FR_NO_PATH, /* (5) Could not find the path */

FR_INVALID_NAME, /* (6) The path name format is invalid */

FR_DENIED, /* (7) Access denied due to prohibited access or directory full */

FR_EXIST, /* (8) Access denied due to prohibited access */ FR_INVALID_OBJECT, /* (9) The file/directory object is invalid */

FR_WRITE_PROTECTED, /* (10) The physical drive is write protected */ FR_INVALID_DRIVE, /* (11) The logical drive number is invalid */

FR_NOT_ENABLED, /* (12) The volume has no work area */

FR_NO_FILESYSTEM, /* (13) There is no valid FAT volume */

FR_MKFS_ABORTED, /* (14) The f_mkfs() aborted due to any parameter error */

FR_TIMEOUT, /* (15) Could not get a grant to access the volume within defined period */

FR_LOCKED, /* (16) The operation is rejected according to the file sharing policy */

FR_NOT_ENOUGH_CORE, /* (17) LFN working buffer could not be allocated */

FR_TOO_MANY_OPEN_FILES, /* (18) Number of open files > _FS_SHARE */ FR_INVALID_PARAMETER /* (19) Given parameter is invalid */

} FRESULT;

2.FATFS文件系统API函数介绍

(1) f_mount

f_mount 函数,主要用来在FatFS 模块中注册/注销工作区。

FRESULT f_mount(

BYTE Drive, /*逻辑驱动器号*/

FATFS* FileSystemObject /*工作区域指针*/

);

参数说明

Drive 注册/注销工作区域的逻辑驱动器号(0~9)

FileSystemObject 被注册的工作区域(文件系统目标)指针。

函数返回值

FR_OK (0) 函数执行成功

FR_INVALID_DRIVE 指定的驱动器号非法

函数描述

f_mount 函数在FatFS 模块中注册/注销一个工作区。在使用其他文件函数前工作区必须先使用这个函数给定每个卷。指定一个NULL 到FileSystemObject,注销一个工作区,然后工作区将被废弃。不管驱动器处于何种状态,此函数总是返回成功。在此函数中不发生媒体访问。它只初始化给定的工作区域并且注册其地址到内部表。在f_mount 函数执行或者媒体改变后,在第一次文件访问时执行卷安装过程。

(2) f_open()函数

创建一个将要访问的文件对象(参数可选打开文件)

FRESULT f_open (

FIL* FileObject, /* 空目标文件结构体指针*/

const TCHAR* FileName, /* 文件名指针*/

BYTE ModeFlags /* 文件打开模式标志*/

);

参数说明

FileObject 要创建的目标文件结构体指针。

FileName 指定创建或打开以空终止的字符串文件名指针

ModeFlags 指定访问或打开文件的模式类型。可以是以下标志的

组合。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_FILE,

FR_NO_PATH,FR_INVALID_NAME,FR_DENIED,FR_EXIST,FR_WRITE_PR

OTECTED,FR_INVALID_DRIVE,FR_NOT_ENABLED,FR_NO_FILESYSTEM,

FR_TIMEOUT,FR_LOCKED,FR_NOT_ENOUGH_CORE,FR_TOO_MANY_

OPEN_FILES

函数描述

在f_open 函数执行成功后,文件对象开始有效。文件对象用于随后指定

文件的读写函数。使用f_close 函数来关闭打开的文件对象。如果更改的

文件未被关闭,文件数据可能崩溃。在使用任何文件函数前,必须使用

f_mount 函数在逻辑驱动器上注册一个工作区(文件系统对象)。除f_fdisk

函数外,所有的API 函数需在完成此过程后工作。注意,当_FS_READONLY

== 1 时,模式标志FA_WRITE,FA_CREATE_ALWAYS,

FA_CREATE_NEW 和FA_OPEN_ALWAYS 不可用。

(3) f_close()函数

f_close 函数,此函数的功能是关闭一个打开的文件。

FRESULT f_close (

FIL* FileObject, /* 文件对象结构体指针*/

);

参数说明

FileObject 将要关闭的已打开文件指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

f_close 函数关闭一个打开的文件对象。如果有任何数据写入到了文件,文

件的缓冲区信息被写回到磁盘。在f_close 函数执行成功后,文件对象不

再有效,并被丢弃。

(4) f_read()函数

FRESULT f_read (

FIL* FileObject, /*文件对象结构体指针*/

void* Buffer, /* 读取数据缓冲区指针*/

UINT ByteToRead, /* 读字节数*/

UINT* ByteRead /*读字节数变量指针*/

);

参数说明

FileObject 打开的文件对象指针

Buffer 存储读取数据缓冲区指针

ByteToRead 在UINT 范围内,读取的字节数

ByteRead 返回读取字节数的无符号整型变量指针。这个值在函数调用后

有效,与函数执行结果无关。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

文件对象的文件指针随着读取字节数的增加而增加。在函数执行成功后,

*ByteRead应该是否检测到了文件结尾。在*ByteRead < ByteToRead 情况下,意味着在读操作期间,读写指针到达了文件尾。

(5) f_write()函数

FRESULT f_write (

FIL* FileObject, /*文件对象结构体指针*/

const void* Buffer, /*写入数据缓冲区指针*/

UINT ByteToWrite, /* 写字节数*/

UINT* ByteWritten /*写字节数变量指针*/

);

参数说明

FileObject 打开的文件对象指针

Buffer 存储写入数据缓冲区指针

ByteToWrite 在UINT 范围内,写入的字节数

ByteWrite 返回写入字节数的无符号整型变量指针。这个值在函数调用后

有效,与函数执行结果无关。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

文件对象的文件指针随着写入字节数的增加而增加。在函数执行成功后,*ByteWrite 应该是否检测到了文件结尾。当*ByteWrite < ByteToWrite 时,意味着在写操作期间卷满了。当卷满或接近满时,函数可能会花费一些时间。

当_FS_READONLY == 0 时此函数可用。

(6) f_lseek函数

f_lseek 函数:移动指针

FRESULT f_lseek (

FIL* FileObject, /*文件对象结构体指针*/

DWORD Offset /* 文件偏移量(单位:字节)*/

);

参数说明

FileObject 打开的文件对象指针

Offset 相对文件开头的字节数

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

f_lseek 函数功能是移动一个打开文件的文件读写指针。偏移量可以被设定为唯一源自文件顶部。当一个超过文件大小的偏移量在写模式下被设置时,文件大小增加到偏移量大小但在扩展区域中的数据是不确定的。这适合快速创建一个大文件,快速的写文件。在f_lseek 函数成功执行后,应该检查文件对象结构体成员变量fptr,以确定读写指针是否被正确地移动。在fptr 不是预期值的情况下,可能发生以下两种情况。. 文件结束。指定的偏移量被限制到文件大小,因为该文件已在只读模式打开。. 磁盘满。卷上没有足够的空余空间来扩展文件大小。

当_USE_FASTSEEK 置1 时使能快速搜索模式,并且文件对象结构体中成员cltbl不为NULL。此功能通过访问存储在用户定义表中的簇链接映射表

(CLMT)实现了无文件分区表(FAT)快速后退/长搜索操作。它也适用于f_read/ f_write 函数。在此模式下,文件大小不能被f_write/f_lseek 函数增加。在使用快速搜索功能前,CLMT 必须事先创建在用户定义的DWORD 数组中。创建CLMT,设置文件对象结构成员cltbl 指向DWORD 数组指针,在数组第一个条目中设置以条目为单位的数组大小,并以参数Offset = CREATE_LINKMAP 调用f_lseek函数。在函数成功执行后CLMT 被创建,随后的

f_read/f_write/f_lseek 函数访问文件无需文件分区表。如果函数执行失败返回FR_NOT_ENOUGH_CORE,表明给定的数组大小不足以容下该文件,并且将需要的条目数返回到数组的第一个条目中。需要的数组大小是(number of fragments + 1) * 2 条。例如,当文件分为5 个片段时,CLMT 需要12 个条目。此函数当_FS_MINIMIZE <= 2 时可用。

(7) f_truncate 函数

FRESULT f_truncate (

FIL* FileObject /*文件对象结构体指针*/

);

参数说明

FileObject 被截断的文件对象指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

f_truncate 函数截短文件大小到当前文件读写点处。如果文件读写点已经到达

文件结尾对此函数没有影响。

当_FS_READONLY == 0 and _FS_MINIMIZE == 0 时,此函数可用。

(8) f_sync 函数

FRESULT f_sync (

FIL* FileObject /*文件对象结构体指针t */

);

参数说明

FileObject 被清除的文件对象指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT

函数描述

f_sync 函数执行了与f_close 函数相同的过程,但其运行后保持文件打开状态,仍可以继续对文件进行读、写、搜索等操作。这样比较适合长时间写模式打开文件的应用,例如数据日志记录应用。在执行f_sync 函数期间或者在f_write 函数执行后立即运行f_sync 函数可以把由于突然断电或者磁盘的意外移除造成数据丢失的风险降到最低。然而,由于在f_close 函数执行中已经执行了f_sync 相同的功能,所以在f_close 函数之前执行f_sync 函数没有任何优点。换言之,这两个函数之间的区别是文件对象是否失效。当_FS_READONLY == 0 时此函数可用。

(9) f_opendir 函数:打开目录、创建目录

FRESULT f_opendir (

DIR* DirObject, /* 目录对象结构体指针*/

const TCHAR* DirName /* 目录名指针*/

);

参数说明

DirObject 目录对象结构体指针

DirName 以空终止的字符串表示的要打开的目录名指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_PATH,

FR_INVALID_NAME, FR_INVALID_DRIVE, FR_NOT_ENABLED, FR_NO_FILESYSTEM,

FR_TIMEOUT, FR_NOT_ENOUGH_CORE

函数描述

此函数打开一个已经存在目录并且为随后的调用创建一个目录对象。目录对象结构体可以随时无任何手续被丢弃。当_FS_MINIMIZE <= 1 时,此函数可用

(10) f_readdir 函数

FRESULT f_readdir (

DIR* DirObject, /*目录对象结构体指针*/ (已打开)

FILINFO* FileInfo /*文件信息结构体指针*/(已存储)

);

参数说明

DirObject 打开的目录对象结构体指针

FileInfo 存储在读条目中的文件信息结构指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_INVALID_OBJECT,

FR_TIMEOUT, FR_NOT_ENOUGH_CORE

函数描述

f_readdir 函数按顺序读取目录条目。反复调用f_readdir 函数可以读取目录的所有条目。当已读完所有的目录条目并且没有其他条目可读时,函数返回一个空字符串到成员变量f_name[]中,并且不返回错误提示。当FileInfo 指向一个空指针,读取的目录对象将被倒回。当LFN 被打开时,文件信息结构体中的lfname 和lfsize 必须在使用f_readdir函数前初始化为有效值。lfname 是一个返回长文件名的字符串缓冲区指针。lfsize表示以TCHAR 为单位的字符串缓冲区的大小。如果读缓冲区或LFN 工作缓冲区容量不够存储LFN 或者对象没有LFN,将返回一个空字符串到LFN 读缓冲区。在没有对Unicode API 配置的情况下,如果LFN 包含任何不能转换成OEM 码的字符,将返回一个空字符串。当lfname 是NULL 时,LFN 没有任何返回。当对象没有LFN 时,一些小写字母被包含到SFN中。当相关的路径特征被使能(_FS_RPATH == 1),”.”和”..”不被过滤并且将出现在所读条目中。当_FS_MINIMIZE <= 1 时,此函数可用

(11) f_getfree 函数:获取驱动器(如,SD卡)的空白鏃数量

FRESULT f_getfree (

const TCHAR* Path, /* 逻辑驱动器号*/

DWORD* Clusters, /* 存储空白簇变量指针*/

FATFS** FileSystemObject /* 指向文件系统对象指针的指针*/

);

参数说明

Path 以空字符终止的字符串表示的逻辑驱动器指针

Clusters 存储空闲簇数量的DWORD 类型变量指针

FileSystemObject 存储相应文件系统对象指针的指针

函数返回值

FR_OK,FR_DISK_ERR,FR_INT_ERR,FR_NOT_READY,FR_INVALID_OBJECT,FR_NOT_ ENABLED,FR_NO_FILESYSTEM, FR_TIMEOUT

函数描述

f_getfree 函数获取驱动器的空白簇数量。FileSystemObject->csize 反映了每簇的扇区数量,因此以扇区为单位的空闲空间可以用这个成员来计算。当FSInfo 结构体与FAT32 卷不同步,函数返回的空闲簇数量可能不正确。当_FS_READONLY == 0 and _FS_MINIMIZE == 0 时,此函数可用。

(12) f_stat 函数

FRESULT f_stat (

const TCHAR* FileName,/* 文件或目录指针*/

FILINFO* FileInfo /* FILINFO 结构指针*/

);

参数说明

FileName 要获取信息的以空字符终止的字符串表示的文件或文件目录指针FileInfo 存储信息的空FILINFO 结构体指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_FILE, FR_NO_PATH,

FR_INVALID_NAME, FR_INVALID_DRIVE, FR_NOT_ENABLED, FR_NO_FILESYSTEM,

FR_TIMEOUT, FR_NOT_ENOUGH_CORE

函数描述

f_stat 函数用来获取文件或目录信息。对于更详细的信息,请参考FILINFO 结

构体和f_readdir 函数。这个函数不支持最小化水平的> = 1。

(13) f_mkdir 函数

FRESULT f_mkdir (

const TCHAR* DirName /* 目录名指针*/

);

参数说明

DirName 以空字符结束的字符串表示的要创建的目录名指针

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_PATH,

FR_INVALID_NAME,

FR_DENIED, FR_EXIST, FR_WRITE_PROTECTED, FR_INVALID_DRIVE, FR_NOT_ENABLED, FR_NO_FILESYSTEM, FR_TIMEOUT, FR_NOT_ENOUGH_CORE

函数描述

F_mkdir 函数用来创建一个文件夹或目录。

(14) f_unlink 函数

FRESULT f_unlink (

const TCHAR* FileName /*文件名指针*/

);

参数说明

FileName 以空字符终止的字符串表示的被移除对象名指针。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_FILE, FR_NO_PATH,

FR_INVALID_NAME, FR_DENIED, FR_EXIST, FR_WRITE_PROTECTED,

FR_INVALID_DRIVE,FR_NOT_ENABLED, FR_NO_FILESYSTEM, FR_TIMEOUT,

FR_LOCKED,FR_NOT_ENOUGH_CORE

函数描述

如果移除对象的条件满足下列条款,函数将运行失败并返回错误。

. 对象必须没有只读属性(AM_RDO)否则函数将被拒绝并返回FR_DENIED.

. 文件夹必须是空的并且不是当前文件夹否则函数将被拒绝并返回FR_DENIED. . 文件必须不是正被打开的文件否则FAT 卷可能崩溃。当文件共享控制被打开,函数可能会被拒绝并返回FR_LOCKED.当_FS_READONLY == 0 and _FS_MINIMIZE == 0 时,此函数可用。

(15) f_chmod 函数:改变文件或文件夹的属性

FRESULT f_chmod (

const TCHAR* FileName, /* 文件或文件夹指针*/

BYTE Attribute, /* 属性标识*/

BYTE AttributeMask /* 属性掩码*/

);

参数说明

FileName 以空字符串终止的字符串表示的文件或文件夹指针。

Attribute 设置的属性下列标志的一个或多个组合。设置或者清除指定的属性。

属性描述

AM_RDO 只读

AM_ARC 档案

AM_SYS 系统

AM_HID 隐藏

AttributeMask 属性掩码指定哪个属性被改变。指定的属性被设置或清除。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_FILE, FR_NO_PATH,

FR_INVALID_NAME, FR_WRITE_PROTECTED, FR_INVALID_DRIVE, FR_NOT_ENABLED, FR_NO_FILESYSTEM, FR_TIMEOUT, FR_NOT_ENOUGH_CORE

函数描述

f_chmod 函数用来改变文件或文件夹的属性。

当_FS_READONLY == 0 and _FS_MINIMIZE == 0 时,此函数可用。

(16) f_utime 函数

FRESULT f_utime (

const TCHAR* FileName, /* 文件或文件夹路径指针*/

const FILINFO* TimeDate /* 设置的时间和日期*/

);

参数说明

FileName 以空字符串终止的字符串表示的文件或文件夹指针。

TimeDate 已有时间戳的文件信息结构体被设置成fdate 和ftime 指针。不用关心其他成员。

函数返回值

FR_OK, FR_DISK_ERR, FR_INT_ERR, FR_NOT_READY, FR_NO_FILE, FR_NO_PATH,

FR_INVALID_NAME, FR_WRITE_PROTECTED, FR_INVALID_DRIVE, FR_NOT_ENABLED, FR_NO_FILESYSTEM, FR_TIMEOUT, FR_NOT_ENOUGH_CORE

原理图元件库的设计步骤(精)

原理图元件库的设计步骤 一. 了解欲绘制的原理图元件的结构 1. 该单片机实际包含40只引脚,图中只出现了38只, 有两只引脚被隐藏,即电源VCC(Pin40和GND(Pin20。 2. 电气符号包含了引脚名和引脚编号两种基本信息。 3. 部分引脚包含引脚电气类型信息(第12脚、第13脚、第32至第39脚。 4. 除了第18脚和第19脚垂直放置,其余水平放置。由于VCC及GND隐藏,所以放置方式可以任意。 5. 一些引脚的名称带有上划线及斜线,应正确标识。

二. 新建集成元件库及电气符号库 1. 在D盘新建一个文件夹D:/student 2. 建立一个工程文件,选择File/New/Project/Integrated Library,如:Dong自制元件库.LibPkg 3. 新建一个电气符号库,选择File/New/Library/Schematic Library,如:Dong自制元件库.SchLib 4. 追加原理图元件 在左侧的SCH Library标签中,点击库元件列表框(第一个窗口下的Add(追加按钮,弹出New Component Name对话框,追加一个原理图元件,输入8051并确认,8051随即被添加到元件列表框中。 三. 绘制原理图元件 1. 绘制矩形元件体 矩形框的左上角定位在原点,则矩形框的右下脚应位于(130,-250。 注意:图纸设置中各Grids都设为10mil。 2. 放置引脚 (1P0.0~P0.7的放置及属性设置 单击实用工具面板的引脚放置工具图标,并按Tab键,系统弹出【引脚属性】对话框: 【Display Name显示名称】文本框中输入“P0.0”; 【Designator标识符】文本框中输入“39”;

LINUX文件系统制作详细

Linux文件系统制作流程 关键词:ARM Linux yaffs文件系统移植 Linux文件系统简介 Linux支持多种文件系统,包括ext2、ext3、vfat、ntfs、iso9660、jffs、romfs和nfs等,为了对各类文件系统进行统一管理,Linux引入了虚拟文件系统VFS(Virtual File System),为各类文件系统提供一个统一的操作界面和应用编程接口。 Linux下的文件系统结构如下: Linux启动时,第一个必须挂载的是根文件系统;若系统不能从指定设备上挂载根文件系统,则系统会出错而退出启动。之后可以自动或手动挂载其他的文件系统。因此,一个系统中可以同时存在不同的文件系统。 不同的文件系统类型有不同的特点,因而根据存储设备的硬件特性、系统需求等有不同的应用场合。在嵌入式Linux应用中,主要的存储设备为RAM(DRAM,

SDRAM)和ROM(常采用FLASH存储器),常用的基于存储设备的文件系统类型包括:jffs2,yaffs,cramfs,romfs,ramdisk,ramfs/tmpfs等。 >基于FLASH的文件系统 Flash(闪存)作为嵌入式系统的主要存储媒介,有其自身的特性。Flash的写入操作只能把对应位置的1修改为0,而不能把0修改为1(擦除Flash就是把对应存储块的内容恢复为1),因此,一般情况下,向Flash写入内容时,需要先擦除对应的存储区间,这种擦除是以块(block)为单位进行的。 闪存主要有NOR和NAND两种技术(简单比较见附录)。Flash存储器的擦写次数是有限的,NAND闪存还有特殊的硬件接口和读写时序。因此,必须针对Flash 的硬件特性设计符合应用要求的文件系统;传统的文件系统如ext2等,用作Flash的文件系统会有诸多弊端。 在嵌入式Linux下,MTD(Memory Technology Device,存储技术设备)为底层硬件(闪存)和上层(文件系统)之间提供一个统一的抽象接口,即Flash的文件系统都是基于MTD驱动层的(参见上面的Linux下的文件系统结构图)。使用MTD 驱动程序的主要优点在于,它是专门针对各种非易失性存储器(以闪存为主)而设计的,因而它对Flash有更好的支持、管理和基于扇区的擦除、读/写操作接口。 顺便一提,一块Flash芯片可以被划分为多个分区,各分区可以采用不同的文件系统;两块Flash芯片也可以合并为一个分区使用,采用一个文件系统。即文件系统是针对于存储器分区而言的,而非存储芯片。 1.jffs2 JFFS文件系统最早是由瑞典Axis Communications公司基于Linux2.0的内核为嵌入式系统开发的文件系统。JFFS2是RedHat公司基于JFFS开发的闪存文件系统,最初是针对RedHat公司的嵌入式产品eCos开发的嵌入式文件系统,所以JFFS2也可以用在Linux,uCLinux中。 Jffs2:日志闪存文件系统版本2(Journalling Flash FileSystem v2) 主要用于NOR型闪存,基于MTD驱动层,特点是:可读写的、支持数据压缩的、基于哈希表的日志型文件系统,并提供了崩溃/掉电安全保护,提供“写平衡”支持等。缺点主要是当文件系统已满或接近满时,因为垃圾收集的关系而使jffs2的运行速度大大放慢。 目前jffs3正在开发中。关于jffs系列文件系统的使用详细文档,可参考MTD补丁包中mtd-jffs-HOWTO.txt。 jffsx不适合用于NAND闪存主要是因为NAND闪存的容量一般较大,这样导致jffs为维护日志节点所占用的内存空间迅速增大,另外,jffsx文件系统在

Prote原理图常用元件库及常用元件

Protel DXP 2004 原理图常用元件库及学用元件 提示:搜索元件时,特殊符号用“ *”号代替,在元件名称前与后分别加“ *”,可提高搜索可靠性。 元件库常用元件

Cap C? CB? 蜂鸣器 Buzzer 电容(无极性) 穿心电容器 Cap Feed 电容(有极性) Cap Pol2 MK? 麦克风 Mic 1 可调电容 Cap Var 电路熔断器 Circuit Breaker Circuit Breaker Cap Feed lOOpF Cap Pol2 lOOpF C? Cap Var lOOpF LS? R Buzzer C? Cap lOOpF

肖特基二极管 D Schottky 变容二极管 D Varactor D? * D Schottky D? -MH D Varactor 齐纳二极管 D Zener D? D Zener 隧道二极管 D Tu nn ell D? D Tunnell 保险管Fuse 1 F? 1 1 11 11 Fuse 1 铁芯电感In ductor Iron L? Inductor lion lOniH 可调电感In ductor Adj L? Inductor Adj IO111H

扬声器Speaker LS? Speaker 增强型N沟道MOS管M0SFET-2GN Q? M0SFET-2GN 增强型P沟道MOS管MOSFET-2GP Q? M0SFET^2GP 增强型N沟道MOS管(衬底有引出线)MOSFET-N3 i Lil M0SFET-N3 耗尽型N沟道MOS管 (衬底有引出线) MOSFET-N4 Q? 增强型P沟道MOS管(衬底有引出线)MOSFET-P3 Q? M0SFET-P3 NPN型光电二极 管 Photo PNP

实验四Linux内核移植实验

合肥学院 嵌入式系统设计实验报告 (2013- 2014第二学期) 专业: 实验项目:实验四 Linux内核移植实验 实验时间: 2014 年 5 月 12 实验成员: _____ 指导老师:干开峰 电子信息与电气工程系 2014年4月制

一、实验目的 1、熟悉嵌入式Linux的内核相关代码分布情况。 2、掌握Linux内核移植过程。 3、学会编译和测试Linux内核。 二、实验内容 本实验了解Linux2.6.32代码结构,基于S3C2440处理器,完成Linux2.6.32内核移植,并完成编译和在目标开发板上测试通过。 三、实验步骤 1、使用光盘自带源码默认配置Linux内核 ⑴在光盘linux文件夹中找到linux-2.6.32.2-mini2440.tar.gz源码文件。 输入命令:#tar –jxvf linux-2.6.32.2-mini2440-20110413.tar对其进行解压。 ⑵执行以下命令来使用缺省配置文件config_x35 输入命令#cp config_mini2440_x35 .config;(注意:x35后面有个空格,然后有个“.”开头的 config ) 然后执行“make menuconfig”命令,但是会出现出现缺少ncurses libraries的错误,如下图所示: 解决办法:输入sudo apt-get install libncurses5-dev 命令进行在线安装ncurses libraries服务。

安装好之后在make menuconfig一下就会出现如下图所示。 ⑶配置内核界面,不用做任何更改,在主菜单里选择退出,并选“Yes”保存设置返回到刚命令行界面,生成相应配置的头文件。 编译内核: #make clean #make zImage 在执行#make zImage命令时会出现如下错误: 错误:arch/arm/mach-s3c2440/mach-mini2440.c:156: error: unknown field 'sets' specified in initializer 通过网上查找资料 于是在自己的mach-mini2440.c中加入 #include

文件系统移植

嵌入式linux内核上文件系统的移植 实验目的:在已经能运行的内核上架构文件系统 其实,虽然 root_qtopia 这个文件系统的GUI 是基于Qtopia 的,但其初始化启动过程 却是由大部分由busybox 完成,Qtopia(qpe)只是在启动的最后阶段被开启。由于默认的内核命令行上有 init=/linuxrc, 因此,在文件系统被挂载后,运行的第一个程 序是根目录下的linuxrc。这是一个指向/bin/busybox 的链接,也就是说,系统起来后运行的 第一个程序也就是busybox 本身。 这种情况下,busybox 首先将试图解析/etc/inittab 来获取进一步的初始化配置信息(参 考busybox 源代码init/init.c 中的parse_inittab()函数)。而事实上,root_qtopia 中并没有/et c/inittab 这个配置文件,根据busybox 的逻辑,它将生成默认的配置 实验过程: 一、获取yaffs2源代码 现在大部分开发板都可以支持 yaffs2 文件系统,它是专门针对嵌入式设备,特别是使用nand flash 作为存储器的嵌入式设备而创建的一种 文件系统,早先的yaffs 仅支持小页(512byte/page)的nand flash,现 在的开发板大都配备了更大容量的nand flash,它们一般是大页模式 (2K/page),使用yaffs2 就可以支持大页的nand flash,下面是yaffs2 的移植详细步骤。 在https://www.360docs.net/doc/2a18067443.html,/node/346 可以下载到最新的yaffs2 源代码,需要使用git工具( 安装方法见本手册第一章),在命令行输入:#git clone git://https://www.360docs.net/doc/2a18067443.html,/yaffs2 稍等片刻,就可以下载到最新的yaffs2 的源代码目录,本光盘中也有单独的yaffs2 源代码包( 文件名为:yaffs2-src-20100329.tar.gz)

FAT文件系统原理详细介绍

FAT文件系统原理详细介绍 2012-03-29 23:09 434人阅读评论(0) 收藏举报 FAT文件起源于70年代末80年代初,用于微软的MS-DOS操作系统。它开始被设计成一个简单的文件系统用于小于500K的软件盘。后来被功能被大大增强用于支持越来越大的媒质。现在的文件系统有FAT12,FAT16和FAT32三种子类。 FAT12是最早的一版,主要用于软盘,它对簇的编址采用12bit宽度的数,所以称为FAT12。12bit的地址可以寻址4096个簇,事实上在FAT12中只能寻址4078个簇(在Linux 下可寻址4084个簇),有一些簇号是不能用的,在后面会给出具体的说明。磁盘的扇区是用16bit的数进行计算的,所以磁盘的容量就被局限在32M空间之内。 在FAT16中,采用了16bit宽的簇地址,32bit宽扇区地址。虽然32bit的扇区地址可以寻址2^32*512,约2个TB的容量,但于由规定每簇最大的容量不超过1024*32,所以FAT16文件系统的容量也就限制到了2^16*1024*32,大约2.1GB的空量,并且实际还达不到这个值。 FAT32文件系统使用了32bit宽的簇地址,所以称为FAT32。但在微软件的文件系统中只使用了低28位,最大容量为2^28*1024*32,约8.7TB的空量。有的人认为32bit全用,最大容量为2^32*1024*32,这种说法是不正确的。 虽然FAT32具有容纳近乎8.7TB的容量,但实际应用中通常不使用超过32GB的FAT32分区。WIN2000及之上的OS已经不直接支持对超过32GB的分区格式化成FAT32,但WIN98依然可以格式化大到127GB的FAT32分区,但不推荐这样做。 下面是一个FAT分区的构成概况 需要说明的是: 1.引导扇区和其他保留扇区一起称为保留扇区,而其他保留扇区是可选的,当没有时候,引导扇区后紧跟的就是FAT表1 2.根目录区是仅FAT12/16才有,FAT32的目录项位于数据区。由于FAT12/16的根目录区是一个固定的区域,所以它的根目录的项数是有限制的,意即不能在根录建立超过这个定数的目录项数。 (一)引导扇区与BPB BPB(BIOS Parametre Block)是FAT文件系统中第一个重要的数据结构,它位于该FAT分区的第一个扇区,同时也属于FAT文件系统基本区域的保留区, 在下面的描述中。凡名称以BPB_开头的都是BPB的一部分,凡名称与BS_开头的项

Altium Designer10原理图常用库文件

原理图常用库文件: Miscellaneous Devices.IntLib Miscellaneous Connectors.IntLib PCB元件常用库: Miscellaneous Devices PCB Miscellaneous Connector PCB.PcbLib 部分分立元件库元件名称及中英对照 AND 与门 ANTENNA 天线 BA TTERY 直流电源 BELL 铃,钟 BVC 同轴电缆接插件 BRIDEG 1 整流桥(二极管) BRIDEG 2 整流桥(集成块) BUFFER 缓冲器 BUZZER 蜂鸣器 CAP 电容 CAPACITOR 电容 CAPACITOR POL 有极性电容 CAPV AR 可调电容 CIRCUIT BREAKER 熔断丝 COAX 同轴电缆 CON 插口 CRYSTAL 晶体整荡器 DB 并行插口 DIODE 二极管 DIODE SCHOTTKY 稳压二极管 DIODE VARACTOR 变容二极管 DPY_3-SEG 3段LED DPY_7-SEG 7段LED DPY_7-SEG_DP 7段LED(带小数点) ELECTRO 电解电容 FUSE 熔断器 INDUCTOR 电感 INDUCTOR IRON 带铁芯电感INDUCTOR3 可调电感 JFET N N沟道场效应管 JFET P P沟道场效应管原理图常用库文件:Miscellaneous Devices.IntLib Miscellaneous Connectors.IntLib PCB元件常用库: Miscellaneous Devices PCB Miscellaneous Connector PCB.PcbLib

根文件系统移植

实验五根文件系统移植 实验目的: 通过本次实验,使大家学会根文件系统移植的具体步骤,并对根文件系统有更近一步的感官认识。让同学理解由于根文件系统是内核启动时挂在的第一个文件系统,那么根文件系统就要包括Linux启动时所必须的目录和关键性的文件,任何包括这些Linux 系统启动所必须的文件都可以成为根文件系统。 实验硬件条件: 1、实验PC机一台,TINY6410开发板一台 2、电源线,串口线,数据线。 实验软件条件: 1、VMware Workstation, 2、Ubuntu10.04 3、mktools-20110720.tar.gz 4、busybox-1.13.3-mini2440.tgz, 5、SecureCRT以及dnw烧写工具 实验步骤: 一、实验步骤 1.进入rootfs目录,查看压缩文件,具体操作指令如下:

2.发现有两个压缩文件夹,分别进行解压: 3.tar xvzf busybox-1.13.3-mini2440.tgz, 4.tar xvzf mktools-20110720.tar.gz,解压完成后, 5.查看文件夹#ls

二、实验步骤 1.修改架构,编译器#cd busybox-1.13.3/ 2.进入后查看#ls 3.#gedit Makefile 4.修改 164行 CROSS_COMPILE ?=arm-linux- 5.修改190行 ARCH ?= arm 6.保存后,退出!

三、实验步骤 1.修改配置 #make menuconfig 2.若出现如下提示

3.需调整到最大化。

4.把Busybox Settings -----→>Build Option ------→> Build BusyBox as astatic binary (no shared libs) 选择上,其他的默认即可。 然后一直退出,保存即可 5.接着执行 make接着执行 make install 6.最终生成的文件在_install 中 #cd _install

FATFS深入理解

一、通过格式化命令-看磁盘文件系统的建立过程 1、添加format命令,单步调试 所有的底层驱动函数都已经准备好。添加格式化命令format后,编译下载。 Format命令的执行主要是调用f_mkfs()函数,下面进行单步调试。 以下主要列出函数的主要执行步骤: res=f_mkfs( 0, 1, 4096 ); //1表示不需要引导扇区。4096是8个扇区。 进入f_mkfs()函数,这里只列出主要执行步骤: if (disk_ioctl(drv, GET_SECTOR_COUNT, &n_part) != RES_OK || n_part < MIN_SECTOR) return FR_MKFS_ABORTED;这个函数调用后,n_part=0x000F,3400 = 996 352,这是SD的总块数。allocsize /= SS(fs); 等于8/*Number of sectors per cluster */ n_clst = n_part / allocsize; //等于0x1E680 = 124 544 簇。 if (n_clst >= 0xFFF5) fmt = FS_FAT32; 所以文件系统确定为FAT32类型。 n_fat = ((n_clst * 4) + 8 + SS(fs) - 1) / SS(fs); 等于0x3CE = 974,表示FAT要占据974个扇区。 n_rsv = 33 - partition; 保留扇区32个。 n_dir = 0; b_fat = b_part + n_rsv; /* FATs start sector 32扇区*/ b_dir = b_fat + n_fat * N_FATS; /* Directory start sector 0x3EE =1006,由于FAT表个数设为1个,所以目录区=FAT起始+FAT占用扇区数*/ b_data = b_dir + n_dir; /* Data start sector */ 以上三项确定FAT区域、根目录区、数据区的起始扇区。 disk_ioctl(drv, GET_BLOCK_SIZE, &n) != RES_OK,这个函数调用没有正确返回可擦出扇区的总数。接下来程序会出错,因此退出,修改disk_ioctl()函数后,再次分析。把这个函数返回值直接改为32。并且把FAT表的个数定义为2. N_FATS改为2后,根目录区、数据区的起始扇区的起始扇区变为0x7BC=1980扇区。继续往下执行。 n = (b_data + n - 1) & ~(n - 1); n_fat += (n - b_data) / N_FATS;这两句话对fat所占扇区数进行了修正,保证擦除时,以32个扇区为一个单位。 n_clst = (n_part - n_rsv - n_fat * N_FATS - n_dir) / allocsize; =0x1E588。 tbl = fs->win; /* Clear buffer */ mem_set(tbl, 0, SS(fs)); 清零文件系统缓冲区。 mem_set(tbl, 0, SS(fs)); ST_DWORD(tbl+BS_jmpBoot, 0x90FEEB); /* Boot code (jmp $, nop) */ ST_WORD(tbl+BPB_BytsPerSec, SS(fs)); /* Sector size */ tbl[BPB_SecPerClus] = (BYTE)allocsize; /* Sectors per cluster */ ST_WORD(tbl+BPB_RsvdSecCnt, n_rsv); /* Reserved sectors */ 上面的工作主要是填充引导扇区缓冲区,也就是常说的DBR扇区缓冲,等所有的参数写好,就可以写回磁盘。 ST_WORD(tbl+BS_55AA, 0xAA55); /* Signature */ if (disk_write(drv, tbl, b_part+0, 1) != RES_OK) return FR_DISK_ERR; //这就是在写有效引导标志sec[510]=0x55, sec[511]=0xAA。 if (fmt == FS_FAT32) disk_write(drv, tbl, b_part+6, 1); //FAT32在第六扇区有个备份引导扇区。 for (m = 0; m < N_FATS; m++) { mem_set(tbl, 0, SS(fs)); /* 1st sector of the FAT */ if (fmt != FS_FAT32) { n = (fmt == FS_FAT12) ? 0x00FFFF00 : 0xFFFFFF00; n |= partition; ST_DWORD(tbl, n); /* Reserve cluster #0-1 (FAT12/16) */ } else { ST_DWORD(tbl+0, 0xFFFFFFF8); /* Reserve cluster #0-1 (FAT32) */

FATFS文件系统移植和应用

FATFS文件系统的移植 作者:LJ 时间:2010年11月12日 随着信息技术的发展,目前常用文件系统主要有微软的FAT12、FAT16、FAT32、NTES文件系统,以及Linux系统的EXT2、EXT3等。由于Windows操作系统的广泛应用,当前很多嵌入式产品中用的最多的还是FAT文件系统。所以,选择一款容易移植和使用,并且占用资源少而功能全面的文件系统就显得非常重要了。 FATFS文件系统是一个完全免费且开源的FAT文件系统模块,由小日本工程师编写,它支持FAT12、FAT16和FAT32文件系统,专门为小型的嵌入式系统而设计。模块用标准的C语言编写,可以很容易地移植到各种硬件平台。 在“驱动程序”文件夹中有一个“FatFs R0.07c”文件夹,这是官方提供的FATFS文件系统的源码和文档,版本为R0.07c。打开“doc”文件夹下的“00index_e.html”英文网页文档,里面有FATFS文件系统的全部API函数说明,相对应的应用实例和如何编写硬件接口程序的说明。如果您的英文不怎么好,建议您先装一个有道词典,使用屏幕取词功能,能帮助我们阅读和理解。“00index_j.html”则是日文版的网页,毕竟是小日本写的。“src”文件夹存放有FATFS文件系统源码,下面是该文件夹下各个文件或文件夹存放的内容说明:“ff.h”文件:FATFS文件系统的配置和API函数声明; “ff.c”文件:FATFS源码;

“diskio.h”文件:FATFS与存储设备接口函数的声明; “diskio.c”文件:FATFS与存储设备接口函数; “integer.h”文件:FATFS用到的所有变量类型的定义; “option”文件夹:存放一些外接函数,下一实例有实际的讲解; “00readme.txt”文件:FATFS版本及相关信息说明; 编译工程,没有通过,根据编译信息提示在“diskio.c”文件中在几个函数没有定义。这很正常,因为我们还没有编写文件系统与存储设备的接口函数。下面来分析“diskio.c”文件中各个函数的功能:“DSTATUS disk_initialize ( BYTE drv )”是存储媒介的初始化函数,由于我们使用的是SD卡,所以实际上是对SD卡的初始化; “DSTATUS disk_status ( BYTE drv )”状态检测函数,检测是否支持当前的存储设备,支持返回0; “DRESULT disk_read (BYTE drv, BYTE *buff, DWORD sector, BYTE count)”是读扇区函数,drv是要读扇区的存储媒介号,*buff 存储读取的数据,sector是读数据的开始扇区,count是要读的扇区数。在SD卡的驱动程序中,分别提供了读一个扇区和读多个扇区的函数。当count == 1时,用读一个扇区函数;当 count > 1时,用读多个扇区的函数,这样提高了文件系统读效率。操作成功返回0。 “DRESULT disk_write(BYTE drv, BYTE *buff, DWORD sector, BYTE count)”写扇区函数,drv是要写扇区的存储媒介号,*buff存储写入的数据,sector是写开始扇区,count是要写的扇区数。同样在SD卡的驱动程序中,分别提供了写一个扇区和写多个扇区的函数。

FATFS文件系统剖析1

FATFS文件系统剖析1: FAT16: 数据按照其不同的特点和作用大致可分为5部分:MBR区、DBR区、FAT区、DIR区和DATA区,相比fat12多了DBR区 Main boot record: MBR(0--1bdh)磁盘参数存放 DPT(1beh--1fdh)磁盘分区表 55,aa 分区结束标志 DBR(Dos Boot Record)是操作系统引导记录区的意思 FAT区(有两个,一个备份):对于fat16,每一个fat项16位,所以可寻址的簇项数为65535(2的16次方)。而其每簇大小不超过32k,所以其每个分区最大容量为2G。fat32,每一个fat项32位,可寻址簇数目为2的32次方。 DIR区(根目录区):紧接着第二FAT表(即备份的FAT表)之后,记录着根目录下每个文件(目录)的起始单元,文件的属性等。定位文件位置时,操作系统根据DIR中的起始单元,结合FAT表就可以知道文件在硬盘中的具体位置和大小了。 DATA区:实际文件内容存放区。 FAT32: 暂时放在这里,不讨论! Fatfs:嵌入式fat文件系统,支持fat16,fat32。 包含有ff.h,diskio.h,integer.h,ffconf.h 四个头文件以及ff.c 文件系统实现。当然要实现具体的应用移植,自己要根据diskio.h实现其diskio。c 底层驱动。 diskio.h : 底层驱动头文件 ff.h : 文件系统实现头文件,定义有文件系统所需的数据结构 ff.c : 文件系统的具体实现

如下开始逐个文件加以分析: integer.h :仅实现数据类型重定义,增加系统的可移植性。 ffconf.h : 文件系统配置---逐个配置,先配置实现一个最小的fat文件系统,下面来分析各配置选项: #define _FFCONF 8255 //版本号 #define _FS_TINY 0 /* 0:Normal or 1:Tiny */ //在这里与先前版本有些许变化,是通过配置头配置两种不同大小的文件系统,这里配置为0。 #define _FS_READONLY 1//定义文件系统只读,也就不能写修改,在此定义为1,这样文件系统会大大缩小,简化学习理解过程。 #define _FS_MINIMIZE 3 /* 0 to 3 */ 这个选项是用于过滤掉一些文件系统功能,为0时是全功能,3是功能实现最小 #define _USE_STRFUNC 0 /* 0:Disable or 1/2:Enable */ 是否使用字符串文件接口,为0,不使用 #define _USE_MKFS 0 /* 0:Disable or 1:Enable */ 制作文件系统,这个功能实现是还要_FS_READONLY=0 #define _USE_FORWARD 0 /* 0:Disable or 1:Enable */ f_forward function 实现还需_FS_TINY =1 #define _USE_FASTSEEK 0 /* 0:Disable or 1:Enable */ 快速查找功 能 #define _CODE_PAGE 936 // 936 - Simplified Chinese GBK (DBCS, OEM, Windows) #define _USE_LFN 0/* 0 to 3 */ 0:不使用长文件名 #define _MAX_LFN 255/* Maximum LFN length to handle (12 to 255) */ #define _LFN_UNICODE 0 /* 0:ANSI/OEM or 1:Unicode */

petit_fatfs文件系统移植

FatFS文件系统的优点我就不赘述了,我需要的功能不多,所以我移植是FatFS的精简版petit fatfs,现将我的一直步骤写下来供大家参考。工程暂不能分享,见谅。 1、移植的文件系统为petit fatfs R0.02。 下载地址:https://www.360docs.net/doc/2a18067443.html,/fsw/ff/pff2.zip 2、本人选用的单片机是STC12C5A56S2(容量够大)。 3、选用的SD卡为macro SD,容量512M,格式化为fat32文件系统,分配大小为512字节。 Petit fatfs文件系统的修改步骤及说明如下: 一、integer.h,pff.c,diskio.h这三个文件不需要修改。 二、pff.h的修改: 1、使能FAT32文件系统的支持#define_FS_FAT321 2、选择简体中文编码格式#define_CODE_PAGE936 三、diskio.c的修改: 1、添加必要头文件:reg51.h,sd.h,spi.h。 2、填写设备初始化函数DSTATUS disk_initialize(void) 这个函数我是参考别人写的: DSTATUS disk_initialize(void) { DSTATUS stat; //Put your code here stat=STA_NOINIT; if(!SD_Init()) { stat&=~STA_NOINIT; } return stat; } 3、填写读函数:DRESULT disk_readp(BYTE*dest,DWORD sector,WORD sofs,WORD count) 这个函数写法各异,就不具体说了, BYTE*dest这个就是指你要讲读出来的数据存在哪里的指针变量。 DWORD sector是要读扇区的地址,看一下SD卡的读写命令你就知道了。 WORD sofs是偏移量,简单就是说,要读的数据相对于扇区开始的字节数,这个读出来,直接忽略掉。 WORD count是要读的字节个数,读完偏移量的字节数,就是要读这个,将读出来的数据存在干才说的那个BYTE*dest。 最后还有一个剩余字节数即(512-sofs-count),这个也不是需要的数据,读出来忽略掉就行了。 4、我做的东西不需要向SD写入,所以disk_writep就没有动。 具体操作,以及在主函数中的调用可参考https://www.360docs.net/doc/2a18067443.html,/tlptotop/blog/item/21c30b2ae0c9a4f5e7cd40de.html

详细了解并学习FatFS文件系统的基本原理

详细了解并学习FatFS文件系统的基本原理 最近做的spi flash,本打算弄个文件系统,由于之前用过了JFFS、YAFFS和TrueFFS,代码量都相当的大,这次想找款代码量不那么吓人的,学习一下,听说配置会相对复杂一些。选来选去,最终选定了FatFS,代码量足够的小,最新的R0.09版本只有1个.c文件(当然,还有一个底层的要自己写,option文件夹里的无视),老点版本就更小了。而且更新很频繁,用户量也够大,就选定它了。尽管最后由于硬件和项目原因未能实际的移植它到vxWorks,但学过的还是要记录下。 在这里http://elm-chan/fsw/ff/00index_el下载源码,只有800多K,小的可怜,还可以下载示例程序,有A VR、Win32、lpc等多平台已实现的方案。打开看src文件夹,一个opTIon 文件夹、00readme.txt、diskio.h、ff.c、ff.h、ffconf.h和interger.h。移植时需要修改的文件主要包括ffconf.h和interger.h,后者是在它的定义与目标平台上的有冲突,或者用的不习惯时修改的。 在做具体修改之前,先大概阅读下FatFS的源代码,可以先读integer.h,了解所用的数据类型,然后是ff.h,了解文件系统所用的数据结构和各种函数声明,再就是diskio.h,了解与介质相关的数据结构和操作函数。ff.c这个文件相对较大,可以在最后将所实现的函数大致扫描一遍,之后根据用户应用层程序调用函数的次序仔细阅读相关代码。各个文件都可以直接用记事本打开查阅,非常方便。ff.h中的几个结构体十分重要,列举如下,首先是最基础的文件系统结构体: view plaincopy to clipboardprint? /* File system object structure (FATFS) */ typedef struct { BYTE fs_type; /* FAT子类型,一般在mount时用,置0表示未挂载*/ BYTE drv; /* 物理驱动号,一般为0*/ BYTE csize; /* 每个簇的扇区数目(1,2,4...128) */ BYTE n_fats; /* 文件分配表的数目(1,2) */

在STM32中移植FATFS文件系统

STM32的FATFS文件系统移植笔记 一、序言 经常在网上、群里看到很多人问关于STM32的FATFS文件系统移植的问题,刚好自己最近也在调试这个程序,为了让大家少走弯路,我把我的调试过程和方法也贡献给大家。 二、FATFS简介 FatFs Module是一种完全免费开源的FAT文件系统模块,专门为小型的嵌入式系统而设计。它完全用标准C语言编写,所以具有良好的硬件平台独立性,可以移植到8051、PIC、AVR、SH、Z80、H8、ARM等系列单片机上而只需做简单的修改。它支持FATl2、FATl6和FAT32,支持多个存储媒介;有独立的缓冲区,可以对多个文件进行读/写,并特别对8位单片机和16位单片机做了优化。 三、移植准备 1、FATFS源代码的获取,可以到官网下载:https://www.360docs.net/doc/2a18067443.html,/fsw/ff/00index_e.html最新版本是R0.09版本,我们就移植这个版本的。 2、解压文件会得到两个文件夹,一个是doc文件夹,这里是FATFS的一些使用文档和说明,以后在文件编程的时候可以查看该文档。另一个是src文件夹,里面就是我们所要的源文件。 3、建立一个STM32的工程,为方便调试,我们应重载printf()底层函数实现串口打印输出。可以参考已经建立好的printf()打印输出工程:.viewtool./bbs/foru ... d=77&extra=page%3D1 四、开始移植 1、在已经建立好的工程目录User文件夹下新建两个文件夹,FATFS_V0.09和 SPI_SD_Card,FATFS_V0.09用于存放FATFS源文件,SPI_SD_Card用于存放SPI的驱动文件。 2、如图1将ff.c添加到工程文件夹中,并新建diskio.c文件,在diskio.c文件中实现五个函数: 1.DSTATUS disk_initialize (BYTE);//SD卡的初始化 2. DSTATUS disk_status (BYTE);//获取SD卡的状态,这里可以不用管 3. DRESULT disk_read (BYTE, BYTE*, DWORD, BYTE);//从SD卡读取数据 4. DRESULT disk_write (BYTE, const BYTE*, DWORD, BYTE);//将数据写入 SD卡,若该文件系统为只读文件系统则不用实现该函数 5. DRESULT disk_ioctl (BYTE, BYTE, void*);//获取SD卡文件系统相关信息 6. 复制代码

FAT文件系统原理

FAT文件系统原理 一、硬盘的物理结构: 硬盘存储数据是根据电、磁转换原理实现的。硬盘由一个或几个表面镀有磁性物质的金属或玻璃等物质盘片以及盘片两面所安装的磁头和相应的控制电路组成(图1),其中盘片和磁头密封在无尘的金属壳中。 硬盘工作时,盘片以设计转速高速旋转,设置在盘片表面的磁头则在电路控制下径向移动到指定位置然后将数据存储或读取出来。当系统向硬盘写入数据时,磁头中“写数据”电流产生磁场使盘片表面磁性物质状态发生改变,并在写电流磁场消失后仍能保持,这样数据就存储下来了;当系统从硬盘中读数据时,磁头经过盘片指定区域,盘片表面磁场使磁头产生感应电流或线圈阻抗产生变化,经相关电路处理后还原成数据。因此只要能将盘片表面处理得更平滑、磁头设计得更精密以及尽量提高盘片旋转速度,就能造出容量更大、读写数据速度更快的硬盘。这是因为盘片表面处理越平、转速越快就能越使磁头离盘片表面越近,提高读、写灵敏度和速度;磁头设计越小越精密就

能使磁头在盘片上占用空间越小,使磁头在一张盘片上建立更多的磁道以存储更多的数据。 二、硬盘的逻辑结构。 硬盘由很多盘片(platter)组成,每个盘片的每个面都有一个读写磁头。如果有N个盘片。就有2N个面,对应2N个磁头(Heads),从0、1、2开始编号。每个盘片被划分成若干个同心圆磁道(逻辑上的,是不可见的。)每个盘片的划分规则通常是一样的。这样每个盘片的半径均为固定值R的同心圆再逻辑上形成了一个以电机主轴为轴的柱面(Cylinders),从外至里编号为0、1、2……每个盘片上的每个磁道又被划分为几十个扇区(Sector),通常的容量是512byte,并按照一定规则编号为1、2、3……形成Cylinders×Heads×Sector个扇区。这三个参数即是硬盘的物理参数。我们下面的很多实践需要深刻理解这三个参数的意义。 三、磁盘引导原理。 3.1MBR(MasterBootRecord)扇区:

原理图元件库

1.在查找元件时,为了增加找到原理图元件的机会,在输入的元件名称中,最 好使用通配符 * 。 2.在字符串查找过程中,系统要寻找所有第一个字母为A的字符串的元件,应 该输入 A* 。 3.在查找元件时,可执行菜单命令工具/查找元件或点击元件库文件面 板上的【查找】按钮。 4.新建原理图元件必须在原理图库文件编辑器中进行。 5.制作一个原理图元器件首先要创建元件库。 6.在原理图库文件编辑环境下,“SCH Library”面板的功能是浏览元件库的 元件。 7.在自己建的原理图元件库文件中,要绘制一个新的元件符号,应执行 Tools/New Component(工具/新元件)菜单命令或单击“SCH Library” 面板上的 Add(追加)按钮。 8.启动元件库编辑器有两种方法,一种方法是打开已有元件库,另一种方 法是创建一个新的元件库。 9.原理图元件库编辑器工作区的中心有一个十字坐标轴,将工作区划分为4 个象限,一般在第四象限绘制原理图元件。 10.原理图元件库编辑器工作区的中心位置坐标为(0,0)。 11.通过原理图元件库编辑器的制作工具来绘制和修改一个元件图 形。 12.在原理图元件编辑环境中,“SCH Library”面板上包括“元件”区、“别 名”区、“引脚”区和“模型”区。 13.“Libraries(库文件)”面板上提供了元件库(Libraries)、查找

(Search

)和放置(Place) 三个工具按钮。 14.原理图元件库编辑管理器中除了主工具栏,还提供了绘制图形工具栏 和 IEEE 工具栏。 15.元件库编辑器里可以产生元件报表、元件库报表和元件规则检查 表。 16.在绘制直线时,可利用空格键切换直线的转角。 17.在绘制椭圆弧时第一次单击鼠标左键确定的是椭圆弧的圆心位置。 18.原理图元件由两部分组成:外形和引脚。 19.制作元器件时,为了画图形实体的外形,捕获网格的值可以按照需要 改动,但是在放置引脚之前,一定要改回 10 。 20.元件名称是为外形和引脚功能相同的元件取的一个通用名称。 21.当元器件绘制完成后,在原理图元件库编辑管理器中单击“元件”区的 “编辑”按钮可设置元件属性。 22.制作元器件符号时,要更改第一个元件名称必须选工具菜单中的重 新命名元件进行修改;要增加一个制作元件直接按【追加】按钮再修改名称。 23.在放置VCC和GND引脚时,在【电气特性】选项中应选择“Power”。 24.若放置与非门74LS00如图01所示功能单元,则在属性对话框中, Designator输入 U1 ;Part为 4 。 图01

嵌入式linux下的文件系统

嵌入式linux下常见的文件系统RomFS:只读文件系统,可以放在ROM空间,也 可以在系统的RAM中,嵌入式linux中常用来作 根文件系统 ?RamFS:利用VFS自身结构而形成的内存文件系 统,使用系统的RAM空间 ?JFFS/JFFS2:为Flash设计的日志文件系统?Yaffs:专门为Nand Flash设计 ?proc:为内核和内核模块将信息发送给进程提 供一种机制,可以查看系统模块装载的信息?devFS:设备文件系统 Linux上的Ext2fs ?支持4 TB 存储、文件名称最长1012 字符 ?可选择逻辑块 ?快速符号链接 ?Ext2不适合flash设备 ?是为象IDE 设备那样的块设备设计的,逻辑块大小必 须是512 byte、1 KB、2KB等 ?没有提供对基于扇区的擦除/写操作的良好管理 ?如果在一个扇区中擦除单个字节,必须将整个扇区复制到RAM,然后擦除,再重写入

?在出现电源故障时,Ext2fs 是不能防止崩溃的 ?文件系统不支持损耗平衡,缩短了flash的寿命 jffs/jffs2文件系统的优缺点 ?日志文件系统 ?提供了更好的崩溃、掉电安全保护 ?jffs2支持对flash的均匀磨损 ?在扇区级别上执行闪存擦除/写/读操作要 比Ext2文件系统好 ?文件系统接近满时,JFFS2 会大大放慢运行 速度——垃圾收集 Nand上yaffs文件系统的优势 ?专门为Nand flash设计的日志文件系统 ?jffs/jffs2不适合大容量的Nand flash ?jffs的日志通过jffs_node建立在RAM中,占用RAM空间:对于128MB的Nand大概需要4MB的空间来维护节点 ?启动的时候需要扫描日志节点,不适合大容量 的Nand flash ?FAT系统没有日志 编译yaffs文件系统 ?mtd的最新补丁升级? ?接口更新,适合与yaffs

相关文档
最新文档