原创 AVR的SD卡接口程序

2008-11-21 18:56 3655 14 12 分类: MCU/ 嵌入式


SD卡接口程序/************************************************************/
/*            SD Code for    M32L              */
/*        By    pasyong         */
/*        2006-4          */
/*        Base ICC6.31A              */
/************************************************************/
#include <iom32v.h>
#include <macros.h>
#include "1011.h"
#define uchar unsigned char
#define uint unsigned int
#define MMC_CS_PIN      BIT(4)     //PORTB.4
#define MMC_PORT        PORTB    


uchar reading="0",a=0,pointer=0;
void sd_port_init()
{
MMC_PORT|=MMC_CS_PIN;
}
uchar BUFFER[512];                    //扇区缓冲区
uint i="0";
void delay_nus(uint n)
{
unsigned char   b;
   for (b = 1; b<n; b++)
    ;
}
//****************************************************************************
//Send a Command to MMC/SD-Card
//Return: the second byte of response register of MMC/SD-Card
//****************************************************************************
uchar SD_Write_Command(uchar cmd,unsigned long arg)
{
    uchar tmp;
    uchar retry="0";
   
    //MMC_PORT|=MMC_CS_PIN;        //SD卡关闭   
    //send 8 Clock Impulse
    Write_Byte_SPI(0xFF);
   
    //set MMC_Chip_Select to low (MMC/SD-Card active)
   MMC_PORT&=~MMC_CS_PIN;        //SD卡使能


    Write_Byte_SPI(cmd|0x40);    //送头命令
    Write_Byte_SPI(arg>>24);
    Write_Byte_SPI(arg>>16);      //send 6 Byte Command to MMC/SD-Card
    Write_Byte_SPI(arg>>8);
    Write_Byte_SPI(arg&0xff);
    Write_Byte_SPI(0x95);        //仅仅对RESET有效的CRC效验码
  
    //get 8 bit response
    //Read_Byte_MMC(); //read the first byte,ignore it.
    do
    {   //Only last 8 bit is used here.Read it out.
       tmp = Read_Byte_SPI();
       retry++;
    }
    while((tmp==0xff)&&(retry<100));   //当没有收到有效的命令的时候
   
    if(reading==0)
    MMC_PORT|=MMC_CS_PIN;             //MMC_CS_PIN=1;
    else MMC_PORT&=~MMC_CS_PIN;       //MMC_CS_PIN=0;   
    return(tmp);
}
//****************************************************************************
//SD卡初始化(SPI-MODE)
//****************************************************************************
uchar SD_Init(void)
{  
    uchar retry,temp;
    uchar i;
    MMC_PORT&=~MMC_CS_PIN;       //SD卡使能
  
   delay_nus(250);   //Wait MMC/SD ready...
    for (i=0;i<0x0f;i++)
    {
       Write_Byte_SPI(0xff); //send 74 clock at least!!!
    }
    //Send Command CMD0 to MMC/SD Card
    retry="0";
   
    do
    { //retry 200 times to send CMD0 command
      temp="SD"_Write_Command(0,0);
      retry++;
      if(retry==100)
      {
       ;//CMD0 Error!
      }
    }
    while(temp!=1);  
   
    //Send Command CMD1 to MMC/SD-Card
    retry="0";
    do
    { //retry 100 times to send CMD1 command
      temp="SD"_Write_Command(1,0);
      retry++;
      if(retry==100)
      {
      ;
      }
    }
    while(temp!=0);
    retry="0";
     SD_Write_Command(16,512);      //设置一次读写BLOCK的长度为512个字节
  
    MMC_PORT|=MMC_CS_PIN;    //MMC_CS_PIN=1;   //set MMC_Chip_Select to high
    return(0); //All commands have been taken.
}
//****************************************************************************
//从SD卡读一个扇区   Return 0 if no Error.
//****************************************************************************
uchar SD_Read_Block(unsigned long address)
{  
    uchar temp="0";uint i="0";
    reading="1";
    temp="SD"_Write_Command(17,address);      //读出RESPONSE     
    while (Read_Byte_SPI()!= 0xfe)
    {;}   //直到读取到了数据的开始头0XFE,才继续
    for(i=0; i<512; i++)
{
BUFFER=Read_Byte_SPI();
}
    Read_Byte_SPI();//CRC - Byte
    Read_Byte_SPI();//CRC - Byte
    reading="0";
    MMC_PORT|=MMC_CS_PIN;         //关闭SD卡
    return(temp);
}

文章评论0条评论)

登录后参与讨论
我要评论
0
14
关闭 站长推荐上一条 /2 下一条