BF533实现CF卡的读写扇区和设备检测等功能
0赞
发表于 5/4/2012 8:30:20 AM
阅读(2465)
#include "dm_bf5xx.h"
#include "dm_types.h"
uint16_t DBR_Buff[256];
uint16_t Drive_Info[256];
extern uint16_t Boot_Sector[256];
/****************************************************************************
* 名称 : Read_Sector_CF
* 功能 : 按物理寻址方式读CF卡,需给定磁头,柱面,扇区,将数据存入Data_Buff
* 入口参数 :Sector,Cylinder,Cmd_Head ,Data_Buff
* 出口参数 :无
****************************************************************************/
void Read_Sector_CF(uint_t Sector, uint_t Cylinder, uint_t Cmd_Head , uint16_t *Data_Buff)
{
int_t i = 0;
Check_CF_Busy();
*SECTOR_REG = Sector; //( Sector_Cnt | Sector_Num ); //Write to ATA Sector Count & Sector No. Registers
Check_CF_RDY_Status();
*CYLINDER_REG = Cylinder; //( Cylinder_Hi | Cylinder_Lo );//Write to ATA Cylinder Low & Cylinder High Registers
Check_CF_RDY_Status();
*DRIVE_HEAD_REG = Cmd_Head; // = ( Read_Sector| LBA | Drive | Head);//Write to ATA Drive/Head & Command Registers
Check_CF_RDY_Status(); //Check CF ATA Status Register RDY bit set
Check_CF_ERR_Status(); //Check CF ATA Status Register ERR bit set
Check_CF_DRQ_Status(); //Check CF ATA Status Register Data Request bit set
Check_CF_Busy();
for ( i=0; i<256; i++ )
Data_Buff[i] = *DATA_REGISTER;
}
/****************************************************************************
* 名称 : DBR_Sector
* 功能 : 判断DBR的位置,有些CF卡没有MBR,考虑到兼容性,用此函数判断出该CF卡是否有MBR
* 入口参数 :无
* 出口参数 :无
****************************************************************************/
void DBR_Sector(void)
{
int_t tem;
int_t Sector = 0x0101;
int_t Cylinder = 0x0000;
int_t Cmd_Head = 0x20A1;
Read_Sector_CF(Sector, Cylinder, Cmd_Head ,Boot_Sector);
if(Boot_Sector[0] != 0x3ceb)
{
Sector = 0x0101;
Cylinder = 0x0000;
Cmd_Head = 0x20A0;
Read_Sector_CF(Sector, Cylinder, Cmd_Head ,Boot_Sector);
}
}
/****************************************************************************
* 名称 : Read_LBA
* 功能 : 该函数功能是给定一个逻辑扇区地址LBA和一个Buff,它将LBA地址所在的扇区的数据读入该Buff中,一次读入一个扇区
* 入口参数 :LBA_Sector,Data_Buff
* 出口参数 :无
****************************************************************************/
void Read_LBA(int_t LBA_Sector ,uint16_t *Data_Buff)
{
uint_t Sector_Num;uint_t Cylinder_Num;uint_t Cmd_Head_Num ;
Sector_Num = LBA_Sector << 8;
Sector_Num |= 0x0001;
Sector_Num &= 0x0000FFFF;
Cylinder_Num = LBA_Sector >> 8;
Cylinder_Num &= 0x0000FFFF;
Cmd_Head_Num = 0x0F000000;
Cmd_Head_Num &= LBA_Sector;
Cmd_Head_Num = Cmd_Head_Num >> 24;
Cmd_Head_Num |= 0x000020E0;
Read_Sector_CF(Sector_Num, Cylinder_Num, Cmd_Head_Num , Data_Buff);
}
/****************************************************************************
* 名称 : Write_Sector_CF
* 功能 : 物理扇区写函数,给定磁头,柱面,扇区,将W_Data_Buff数据写入该扇区
* 入口参数 :Sector,Cylinder,Cmd_Head,W_Data_Buff
* 出口参数 :无
****************************************************************************/
void Write_Sector_CF(int_t Sector, uint_t Cylinder, uint_t Cmd_Head , uint16_t *W_Data_Buff)
{
int_t i = 0;
Check_CF_Busy();
*SECTOR_REG = Sector; //( Sector_Cnt | Sector_Num ); //Write to ATA Sector Count & Sector No. Registers
Check_CF_RDY_Status();
*CYLINDER_REG = Cylinder; //( Cylinder_Hi | Cylinder_Lo );//Write to ATA Cylinder Low & Cylinder High Registers
Check_CF_RDY_Status();
*DRIVE_HEAD_REG = Cmd_Head; // = ( Read_Sector| LBA | Drive | Head ); //Write to ATA Drive/Head & Command Registers
Check_CF_RDY_Status(); //Check CF ATA Status Register RDY bit set
Check_CF_ERR_Status(); //Check CF ATA Status Register ERR bit set
Check_CF_DRQ_Status(); //Check CF ATA Status Register Data Request bit set
Check_CF_Busy;
for ( i=0; i<256; i++ )
*DATA_REGISTER = W_Data_Buff[i] ;
}
/****************************************************************************
* 名称 : Write_LBA
* 功能 : 逻辑写扇区,给定待写的逻辑扇区号,将W_Data_Buff中的数据写入该扇区
* 入口参数 :W_LBA_Sector,W_Data_Buff
* 出口参数 :无
****************************************************************************/
void Write_LBA(int_t W_LBA_Sector ,uint16_t *W_Data_Buff)
{
uint_t Sector_Num;
uint_t Cylinder_Num;
uint_t Cmd_Head_Num ;
Sector_Num = W_LBA_Sector << 8;
Sector_Num |= 0x0001;
Sector_Num &= 0x0000FFFF;
Cylinder_Num = W_LBA_Sector >> 8;
Cylinder_Num &= 0x0000FFFF;
Cmd_Head_Num = 0x0F000000;
Cmd_Head_Num &= W_LBA_Sector;
Cmd_Head_Num = Cmd_Head_Num >> 24;
Cmd_Head_Num |= 0x000030E0;
Write_Sector_CF(Sector_Num, Cylinder_Num, Cmd_Head_Num ,W_Data_Buff);
}
/****************************************************************************
* 名称 : Identify_Drive_Command
* 功能 : 鉴别驱动,用于设备识别,读入的信息主要告诉你这个设备为CF卡等信息?
* 入口参数 :无
* 出口参数 :无
****************************************************************************/
void Identify_Drive_Command(void)
{
int_t i=0;
Check_CF_Busy();
Check_CF_RDY_Status();
*DRIVE_HEAD_REG = 0xECA0; //Write to ATA Drive/Head & Command Registers
Check_CF_RDY_Status(); //Check CF ATA Status Register RDY bit set
Check_CF_DRQ_Status(); //Check CF ATA Status Register Data Request bit set
Check_CF_Busy();
for (i=0;i<256;i++)
Drive_Info[i] = *DATA_REGISTER;
}
