关于petitfatfs的移植问题
来源:互联网 发布:自学编程入门教材 编辑:程序博客网 时间:2024/06/03 23:39
Petit FatFs是FatFs的简版,可以移植到8位单片机上,我此次试验是在PIC16F877A上移植了这种文件系统,用于管理SD卡中的txt文件内容的读写。其中SD卡的驱动程序在另一篇博客中有所介绍。
我在这次试验遇到的问题和想法简述于下,希望对过客有所帮助,也望高手赐教。
1.文件系统中,最为根本的就是底层驱动程序的编写,一般没有必要去过多研读系统本身,而且也很难读懂,我们只想调用接口函数,将自己的驱动函数程序挂在接口函数内。然后调用接口函数实现目标即可。
2.要用文件系统给sd卡里的txt文件写东西,必须先给文件写入需要文件大小的空格,因为在官方的说明中给文件写东西,不能扩大文件的大小。不知道我是不是错了,如果我没错的话,我感觉这是小文件系统的缺陷。它不能创建文件,也不能更改文件的大小。所以,我给sd卡里的txt文件预先写好东西,拿单片机在给文件写入东西的时候,会把原有的东西覆盖。如果我在文件里什么都不写,那么单片机也写不进去任何东西。如果我在文件里输入许多空格,那么单片机就会写入东西,文件指针移动的操作也可以实现。这是经过试验的。
3.在对sd卡的读写需要一定的时序,在没有移植文件系统的时候,我以前的程序可以对sd卡正常操作。但是挂到系统上之后,程序就会卡在某个循环语句处。于是我在程序中用串口发送信息的方式检测程序卡在了那里。
开始我在检测点发送的东西较少,会频繁的卡在一个地方,最后误打误撞,我将发送的内容增加,却调试成功,我也不知道是什么原因,于是在卡点放了一个延迟函数。程序便好用了起来。
一下是接口函数的书写:
/*-----------------------------------------------------------------------*/
/* Low level disk I/O module skeleton for Petit FatFs (C)ChaN, 2009 */
/*-----------------------------------------------------------------------*/
#include <pic.h>/*Platform dependent macros and functions needed to be modified */
#include<string.h>
#include "pff.h"//include "integer.h"
#include "diskio.h"//include "integer.h"
#define CS RC2
#define _XTAL_FREQ 12000000
/*************************************usart*************************************/
void init_pic_usart(void)
{
TRISC7=1;
TRISC6=1;
RCSTA=0x90;//1001 0000,SPEN=1,serial port enabled.CREN=1,
TXSTA=0X24;//0010 0100,TX9=0,select 8 bits transmission.
//TXEN=1,transmit enabled .
//SYNC=0,Asynchronous mode.
//BRGH=1,High speed.
SPBRG=77;
}
void usart_send_byte(CHAR data)
{
TXREG=data;
while(!TRMT);
}
void usart_send_str(const UCHAR *buff,UCHAR EnterFlag)//send of string,and then line feed
{
UINT i;
UINT len=strlen(buff);//count the string length
for(i=0;i<len;i++)
{
usart_send_byte(buff[i]);
}
if(1==EnterFlag)
{
usart_send_byte(0x0a);
usart_send_byte(0x0d);//line feed
}
}
/************************************SPI***********************************************/
void init_pic_spi()
{
TRISC2=0;//CS
TRISC3=0;//SCK
TRISC4=1;//SDI
TRISC5=0;//SDO
SSPSTAT=0X80;
//SMP=1,input data sampled at the end of data output time
//CKE=1;transmit occurs on transition from idle to active clock
SSPCON=0X30;
//SSPM3-SSPM0 0000 SPI master mode ,clock=fosc/64
//CKP=1 idle state for clock high level
//SPEN=1 enable serial port
//WCOL=0 no collision
//falling edge of SCK transmit data
}
void write_command(UCHAR command,DWORD arguement,UCHAR CRC)
{
UCHAR arg[4],i=0;
arguement=arguement<<9;
arg[0]=(UCHAR)(arguement>>24);
arg[1]=(UCHAR)(arguement>>16);
arg[2]=(UCHAR)(arguement>>8);
arg[3]=(UCHAR)(arguement);//four 0x00
SSPBUF=command|0x40;
while(!BF);
for(i=0;i<4;i++)
{
SSPBUF=arg[i];
while(!BF);
}
SSPBUF=CRC;
while(!BF);
}
UCHAR receive_response()
{
UCHAR a=0;
while(a++<100)
{
SSPBUF=0XFF;//if we want to read a data,must send first,we send complete,receive comlete
while(!BF);//receive flag
if(0x01==SSPBUF)
{
break;
}
else if(0x00==SSPBUF)
{
break;
}
else if(0xfe==SSPBUF)
{
break;
}
else if(0xff!=SSPBUF)
{
break;
}
}
return SSPBUF;
}
/*-----------------------------------------------------------------------*/
/* Initialize Disk Drive */
/*-----------------------------------------------------------------------*/
DSTATUS disk_initialize (void)
{
DSTATUS stat;
// Put your code here
stat=RES_ERROR;
int i=0;
do
{
CS=1;//disable sd card
for(i=0;i<15;i++) //more than 74 clock pules,15*8=120,FOR YU JU CUO LE
{
SSPBUF=0XFF;
while(!BF);
}
CS=0;
SSPBUF=0XFF;
while(!BF);//8 clock
write_command(0x00,0,0x95);
}while(receive_response()!=0x01);
CS=1;
SSPBUF=0XFF;//8 clock pules
while(!BF);//untile now ,reset completed
do
{
CS=0;
__delay_us(10);
write_command(0x01,0,0xff);
}while(receive_response()!=0x00);
CS=1;
__delay_us(10);
SSPBUF=0XFF;//8 clock pules
while(!BF);//untile now ,SD card has came into SPI work mode
stat=RES_OK;
return stat;
}
/*-----------------------------------------------------------------------*/
/* Read Partial Sector */
/*-----------------------------------------------------------------------*/
DRESULT disk_readp(
BYTE* dest, /* Pointer to the destination object */
DWORD sector, /* Sector number (LBA) */
WORD sofs, /* Offset in the sector */
WORD count /* Byte count (bit15:destination) */
)
{
DRESULT res;
// Put your code here
res=RES_ERROR;
UINT i=0;
do
{
CS=0;
SSPBUF=0XFF;
while(!BF);//8 clock
write_command(0x11,sector,0xff);//CMD17:the command of read data block,address must be integer multiple of 512
}while(receive_response()!=0x00); __delay_us(100);//usart_send_str("haha,here",1);//must have
当时便卡在了此处,我的测试发送程序是usart_send_str("haha,here",1)时,程序便畅行无阻,于是我在此次加了延时函数__delay_us(100)。
while(receive_response()!=0xfe);
for(i=0;i<sofs;i++)
{
SSPBUF=0XFF;
while(!BF);//skip sofs bytes
}
for(i=0;i<count;i++)//read count byte
{
SSPBUF=0XFF;
while(!BF);//skip sofs bytes
*(dest+i)=SSPBUF;
}
for(i=0;i<512-sofs-count;i++)
{
SSPBUF=0XFF;//skip reminder bytes
while(!BF); //abandon two CRC bytes
}
SSPBUF=0XFF;
while(!BF); //abandon two CRC bytes
SSPBUF=0XFF;
while(!BF);
CS=1;
SSPBUF=0XFF;
while(!BF);//8 clock
res=RES_OK;
return res;
}
/*-----------------------------------------------------------------------*/
/* Write Partial Sector */
/*-----------------------------------------------------------------------*/
DRESULT disk_writep(
const BYTE* buff, /* Pointer to the data to be written, NULL:Initiate/Finalize write operation */
DWORD sc /* Sector number (LBA) or Number of bytes to send */
)
{ /*buff=0,sc=0 finish the write function */
/*buff=0,sc!=0 init write sector */
/*buff!=0,sc=!0 normal write */
DRESULT res;
WORD bc;//typedef unsigned short WORD;
static WORD wc;//init with 0 and keep the value last time
res=RES_ERROR;//init res
if(buff)
{ /* Send data bytes */
bc=(WORD)sc;
while(bc&&wc)
{ /* Send data bytes to the card */
SSPBUF=*buff++;
while(!BF);
wc--;bc--;
}
res=RES_OK;
}
else
{
if(sc)/* Initiate sector write process */
{
do
{
CS=0;
SSPBUF=0XFF;
while(!BF);//8 clock pules
write_command(0x18,sc,0xff);//CMD24
}while(receive_response()!=0x00);
SSPBUF=0XFF;
while(!BF);
SSPBUF=0XFE;
while(!BF);//head data
wc=512; /* Set byte counter */
res=RES_OK;
}
else
{ /* Finalize sector write process */
bc=wc+2;
while(bc--)
{
SSPBUF=0x00; //if the pointer is not on the sector boundary,left bytes should filled with 0
while(!BF);/* Fill left bytes and CRC with zeros */
}
while(0x05==(receive_response()&0x1F));
while(receive_response()!=0xFF);
res = RES_OK;//!= prior to &&,while sdcard is busy ,dataout is low
CS=1;
SSPBUF=0xff;
while(!BF);
}
}
return res;
}
- 关于petitfatfs的移植问题
- 关于程序可移植性的问题
- 关于sam9x5移植遇到的一些问题
- 关于QT移植及触摸屏的问题
- 关于Keil5移植SDIO不成功的问题
- 关于Yaffs2移植问题
- 关于libwebsocket移植问题
- 关于cocos2dx的Android的移植的MK文件问题
- 关于cocos2dx的安卓移植碰到的问题
- 关于《U-Boot 移植手册》里面的一个小问题
- 关于在android系统移植中usb的连接问题
- 关于ucosii移植后的问题及思考
- 关于cocos2dx代码,资源移植到ios上的问题
- 关于内核移植和驱动加载的问题
- 关于linux应用程序向嵌入式设备上移植的问题
- 关于uboot在jz2440上的移植问题
- 关于linux下项目移植到windows上的问题
- [STM32]--关于移植STemwin所遇到的问题记录(1)
- 设计模式之单例模式
- 三种后台登入框注入
- 对摩尔定律的理解
- (转)10个超棒的Android开源项目推荐
- 程序开发人员的思维导图
- 关于petitfatfs的移植问题
- 【转载】详解大端模式和小端模式
- 项目1任务二
- POJ 1936 ALL IN ALL 字符串
- [Euler]Problem 36 - Double-base palindromes
- hdu 4160 Dolls 匈牙利算法求最大匹配
- 杭电acm1003
- 结合硬件的发展史,谈谈你对计算机硬件发展趋势的看法?
- java面试题经典20例