📄 sd.lst
字号:
C51 COMPILER V8.09 SD 05/19/2011 23:29:39 PAGE 1
C51 COMPILER V8.09, COMPILATION OF MODULE SD
OBJECT MODULE PLACED IN sd.OBJ
COMPILER INVOKED BY: C:\Keil\C51\BIN\C51.EXE sd.c LARGE BROWSE DEBUG OBJECTEXTEND
line level source
1 #include "sd.h"
2 #include "Delay.h"
3
4 /*******************************************************
5
6 +-------------------------------------+
7 | 振南电子 高级资源驱动 SD卡 部分 |
8 +-------------------------------------+
9
10 此源码版权属 振南 全权享有,如欲引用,敬请署名并告知
11 严禁随意用于商业目的,违者必究,后果自负
12 振南电子
13 ->产品网站 http://www.znmcu.cn/
14 ->产品网店 http://shop.znmcu.cn/
15 ->产品咨询 QQ :987582714
16 MSN:yzn07@126.com
17 WW :yzn07
18 ********************************************************/
19
20 //变量定义
21 //--------------------------------------------------------------
22 bit is_init; //在初始化的时候设置此变量为1,同步数据传输(SPI)会放慢
23 //---------------------------------------------------------------
24
25 unsigned char bdata _dat;
26 sbit _dat7=_dat^7;
27 sbit _dat6=_dat^6;
28 sbit _dat5=_dat^5;
29 sbit _dat4=_dat^4;
30 sbit _dat3=_dat^3;
31 sbit _dat2=_dat^2;
32 sbit _dat1=_dat^1;
33 sbit _dat0=_dat^0;
34
35 /******************************************************************
36 - 功能描述:IO模拟SPI,发送一个字节
37 - 隶属模块:SD卡模块
38 - 函数属性:内部
39 - 参数说明:x是要发送的字节
40 - 返回说明:无返回
41 - 注:其中is_init为1时,写的速度放慢,初始化SD卡SPI速度不能太高
42 ******************************************************************/
43
44 void SD_spi_write(unsigned char x)
45 {
46 1 _dat=x;
47 1
48 1 SD_SI=_dat7;
49 1 SD_SCL=0;
50 1 if(is_init) delay(DELAY_TIME);
51 1 SD_SCL=1;
52 1 if(is_init) delay(DELAY_TIME);
53 1
54 1 SD_SI=_dat6;
55 1 SD_SCL=0;
C51 COMPILER V8.09 SD 05/19/2011 23:29:39 PAGE 2
56 1 if(is_init) delay(DELAY_TIME);
57 1 SD_SCL=1;
58 1 if(is_init) delay(DELAY_TIME);
59 1
60 1 SD_SI=_dat5;
61 1 SD_SCL=0;
62 1 if(is_init) delay(DELAY_TIME);
63 1 SD_SCL=1;
64 1 if(is_init) delay(DELAY_TIME);
65 1
66 1 SD_SI=_dat4;
67 1 SD_SCL=0;
68 1 if(is_init) delay(DELAY_TIME);
69 1 SD_SCL=1;
70 1 if(is_init) delay(DELAY_TIME);
71 1
72 1 SD_SI=_dat3;
73 1 SD_SCL=0;
74 1 if(is_init) delay(DELAY_TIME);
75 1 SD_SCL=1;
76 1 if(is_init) delay(DELAY_TIME);
77 1
78 1 SD_SI=_dat2;
79 1 SD_SCL=0;
80 1 if(is_init) delay(DELAY_TIME);
81 1 SD_SCL=1;
82 1 if(is_init) delay(DELAY_TIME);
83 1
84 1 SD_SI=_dat1;
85 1 SD_SCL=0;
86 1 if(is_init) delay(DELAY_TIME);
87 1 SD_SCL=1;
88 1 if(is_init) delay(DELAY_TIME);
89 1
90 1 SD_SI=_dat0;
91 1 SD_SCL=0;
92 1 if(is_init) delay(DELAY_TIME);
93 1 SD_SCL=1;
94 1 if(is_init) delay(DELAY_TIME);
95 1 }
96
97 /******************************************************************
98 - 功能描述:IO模拟SPI,读取一个字节
99 - 隶属模块:SD卡模块
100 - 函数属性:内部
101 - 参数说明:无
102 - 返回说明:返回读到的字节
103 ******************************************************************/
104
105 unsigned char SD_spi_read() //SPI读一个字节
106 {
107 1 SD_SO=1;
108 1
109 1 SD_SCL=1;
110 1 if(is_init) delay(DELAY_TIME);
111 1 SD_SCL=0;
112 1 if(is_init) delay(DELAY_TIME);
113 1 _dat7=SD_SO;
114 1
115 1 SD_SCL=1;
116 1 if(is_init) delay(DELAY_TIME);
117 1 SD_SCL=0;
C51 COMPILER V8.09 SD 05/19/2011 23:29:39 PAGE 3
118 1 if(is_init) delay(DELAY_TIME);
119 1 _dat6=SD_SO;
120 1
121 1 SD_SCL=1;
122 1 if(is_init) delay(DELAY_TIME);
123 1 SD_SCL=0;
124 1 if(is_init) delay(DELAY_TIME);
125 1 _dat5=SD_SO;
126 1
127 1 SD_SCL=1;
128 1 if(is_init) delay(DELAY_TIME);
129 1 SD_SCL=0;
130 1 if(is_init) delay(DELAY_TIME);
131 1 _dat4=SD_SO;
132 1
133 1 SD_SCL=1;
134 1 if(is_init) delay(DELAY_TIME);
135 1 SD_SCL=0;
136 1 if(is_init) delay(DELAY_TIME);
137 1 _dat3=SD_SO;
138 1
139 1 SD_SCL=1;
140 1 if(is_init) delay(DELAY_TIME);
141 1 SD_SCL=0;
142 1 if(is_init) delay(DELAY_TIME);
143 1 _dat2=SD_SO;
144 1
145 1 SD_SCL=1;
146 1 if(is_init) delay(DELAY_TIME);
147 1 SD_SCL=0;
148 1 if(is_init) delay(DELAY_TIME);
149 1 _dat1=SD_SO;
150 1
151 1 SD_SCL=1;
152 1 if(is_init) delay(DELAY_TIME);
153 1 SD_SCL=0;
154 1 if(is_init) delay(DELAY_TIME);
155 1 _dat0=SD_SO;
156 1
157 1 return (_dat);
158 1 }
159
160 /******************************************************************
161 - 功能描述:向SD卡写命令
162 - 隶属模块:SD卡模块
163 - 函数属性:内部
164 - 参数说明:SD卡的命令是6个字节,pcmd是指向命令字节序列的指针
165 - 返回说明:命令写入后,SD卡的回应值,调用不成功,将返回0xff
166 ******************************************************************/
167
168 unsigned char SD_Write_Cmd(unsigned char *pcmd) //向SD卡写命令,pcmd是命令字节序列的首地址
169 {
170 1 unsigned char temp,time=0;
171 1
172 1 SD_CS=1;
173 1 SD_spi_write(0xff); //提高兼容性,如果没有这里,有些SD卡可能不支持
174 1 SD_CS=0;
175 1
176 1 SD_spi_write(pcmd[0]);
177 1 SD_spi_write(pcmd[1]);
178 1 SD_spi_write(pcmd[2]);
179 1 SD_spi_write(pcmd[3]);
C51 COMPILER V8.09 SD 05/19/2011 23:29:39 PAGE 4
180 1 SD_spi_write(pcmd[4]);
181 1 SD_spi_write(pcmd[5]);
182 1
183 1 do
184 1 {
185 2 temp = SD_spi_read();//一直读,直到读到的不是0xff或超时
186 2 time++;
187 2 }while((temp==0xff)&&(time<TRY_TIME));
188 1
189 1 return(temp);
190 1 }
191
192 /******************************************************************
193 - 功能描述:复位SD卡,用到CMD0,使用SD卡切换到SPI模式
194 - 隶属模块:SD卡模块
195 - 函数属性:外部,供用户调用
196 - 参数说明:无
197 - 返回说明:调用成功,返回0x00,否则返回INIT_CMD0_ERROR (sd.h中有定义)
198 ******************************************************************/
199
200 unsigned char SD_Reset()//SD卡复位,进入SPI模式,使用CMD0(命令0)
201 {
202 1 unsigned char time,temp,i;
203 1 unsigned char pcmd[] = {0x40,0x00,0x00,0x00,0x00,0x95}; //命令0的字节序列
204 1
205 1 is_init=1; //将is_init置为1
206 1
207 1 SD_CS=1; //关闭片选
208 1 for(i=0;i<0x0f;i++) //初始时,首先要发送最少74个时钟信号,这是必须的!!!
209 1 {
210 2 SD_spi_write(0xff); //120个时钟
211 2 }
212 1
213 1 SD_CS=0; //打开片选
214 1
215 1 time=0;
216 1 do
217 1 {
218 2 temp=SD_Write_Cmd(pcmd);//写入CMD0
219 2 time++;
220 2 if(time==TRY_TIME)
221 2 {
222 3 SD_CS=1; //关闭片选
223 3 return(INIT_CMD0_ERROR);//CMD0写入失败
224 3 }
225 2 }while(temp!=0x01);
226 1
227 1 SD_CS=1; //关闭片选
228 1 SD_spi_write(0xff); //按照SD卡的操作时序在这里补8个时钟
229 1 return 0;//返回0,说明复位操作成功
230 1 }
231
232 /******************************************************************
233 - 功能描述:初始化SD卡,使用CMD1
234 - 隶属模块:SD卡模块
235 - 函数属性:外部,供用户调用
236 - 参数说明:无
237 - 返回说明:调用成功,返回0x00,否则返回INIT_CMD1_ERROR (sd.h中有定义)
238 ******************************************************************/
239
240 unsigned char SD_Init() //初始化,使用CMD1(命令1)
241 {
C51 COMPILER V8.09 SD 05/19/2011 23:29:39 PAGE 5
242 1 unsigned char time,temp;
243 1 unsigned char pcmd[] = {0x41,0x00,0x00,0x00,0x00,0xff}; //命令1的字节序列
244 1
245 1 SD_CS=0; //打开片选
246 1
247 1 time=0;
248 1 do
249 1 {
250 2 temp=SD_Write_Cmd(pcmd);
251 2 time++;
252 2 if(time==TRY_TIME)
253 2 {
254 3 SD_CS=1; //关闭片选
255 3 return(INIT_CMD1_ERROR);//CMD1写入失败
256 3 }
257 2 }while(temp!=0);
258 1
259 1 is_init=0; //初始化完毕,将is_init设置为0,为了提高以后的数据传输速度
260 1
261 1 SD_CS=1; //关闭片选
262 1 SD_spi_write(0xff); //按照SD卡的操作时序在这里补8个时钟
263 1 return(0); //返回0,说明初始化操作成功
264 1 }
265
266 /****************************************************************************
267 - 功能描述:将buffer指向的512个字节的数据写入到SD卡的addr扇区中
268 - 隶属模块:SD卡模块
269 - 函数属性:外部,供用户调用
270 - 参数说明:addr:扇区地址
271 buffer:指向数据缓冲区的指针
272 - 返回说明:调用成功,返回0x00,否则返回WRITE_BLOCK_ERROR (sd.h中有定义)
273 - 注:SD卡初始化成功后,读写扇区时,尽量将SPI速度提上来,提高效率
274 ****************************************************************************/
275
276 unsigned char SD_Write_Sector(unsigned long addr,unsigned char *buffer) //向SD卡中的指定地址的扇区写入512
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -