Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
SDFileSystem.cpp
00001 /* mbed Microcontroller Library - SDFileSystem 00002 * Copyright (c) 2008-2009, sford 00003 * 00004 * Introduction 00005 * ------------ 00006 * SD and MMC cards support a number of interfaces, but common to them all 00007 * is one based on SPI. This is the one I'm implmenting because it means 00008 * it is much more portable even though not so performant, and we already 00009 * have the mbed SPI Interface! 00010 * 00011 * The main reference I'm using is Chapter 7, "SPI Mode" of: 00012 * http://www.sdcard.org/developers/tech/sdcard/pls/Simplified_Physical_Layer_Spec.pdf 00013 * 00014 * SPI Startup 00015 * ----------- 00016 * The SD card powers up in SD mode. The SPI interface mode is selected by 00017 * asserting CS low and sending the reset command (CMD0). The card will 00018 * respond with a (R1) response. 00019 * 00020 * CMD8 is optionally sent to determine the voltage range supported, and 00021 * indirectly determine whether it is a version 1.x SD/non-SD card or 00022 * version 2.x. I'll just ignore this for now. 00023 * 00024 * ACMD41 is repeatedly issued to initialise the card, until "in idle" 00025 * (bit 0) of the R1 response goes to '0', indicating it is initialised. 00026 * 00027 * You should also indicate whether the host supports High Capicity cards, 00028 * and check whether the card is high capacity - i'll also ignore this 00029 * 00030 * SPI Protocol 00031 * ------------ 00032 * The SD SPI protocol is based on transactions made up of 8-bit words, with 00033 * the host starting every bus transaction by asserting the CS signal low. The 00034 * card always responds to commands, data blocks and errors. 00035 * 00036 * The protocol supports a CRC, but by default it is off (except for the 00037 * first reset CMD0, where the CRC can just be pre-calculated, and CMD8) 00038 * I'll leave the CRC off I think! 00039 * 00040 * Standard capacity cards have variable data block sizes, whereas High 00041 * Capacity cards fix the size of data block to 512 bytes. I'll therefore 00042 * just always use the Standard Capacity cards with a block size of 512 bytes. 00043 * This is set with CMD16. 00044 * 00045 * You can read and write single blocks (CMD17, CMD25) or multiple blocks 00046 * (CMD18, CMD25). For simplicity, I'll just use single block accesses. When 00047 * the card gets a read command, it responds with a response token, and then 00048 * a data token or an error. 00049 * 00050 * SPI Command Format 00051 * ------------------ 00052 * Commands are 6-bytes long, containing the command, 32-bit argument, and CRC. 00053 * 00054 * +---------------+------------+------------+-----------+----------+--------------+ 00055 * | 01 | cmd[5:0] | arg[31:24] | arg[23:16] | arg[15:8] | arg[7:0] | crc[6:0] | 1 | 00056 * +---------------+------------+------------+-----------+----------+--------------+ 00057 * 00058 * As I'm not using CRC, I can fix that byte to what is needed for CMD0 (0x95) 00059 * 00060 * All Application Specific commands shall be preceded with APP_CMD (CMD55). 00061 * 00062 * SPI Response Format 00063 * ------------------- 00064 * The main response format (R1) is a status byte (normally zero). Key flags: 00065 * idle - 1 if the card is in an idle state/initialising 00066 * cmd - 1 if an illegal command code was detected 00067 * 00068 * +-------------------------------------------------+ 00069 * R1 | 0 | arg | addr | seq | crc | cmd | erase | idle | 00070 * +-------------------------------------------------+ 00071 * 00072 * R1b is the same, except it is followed by a busy signal (zeros) until 00073 * the first non-zero byte when it is ready again. 00074 * 00075 * Data Response Token 00076 * ------------------- 00077 * Every data block written to the card is acknowledged by a byte 00078 * response token 00079 * 00080 * +----------------------+ 00081 * | xxx | 0 | status | 1 | 00082 * +----------------------+ 00083 * 010 - OK! 00084 * 101 - CRC Error 00085 * 110 - Write Error 00086 * 00087 * Single Block Read and Write 00088 * --------------------------- 00089 * 00090 * Block transfers have a byte header, followed by the data, followed 00091 * by a 16-bit CRC. In our case, the data will always be 512 bytes. 00092 * 00093 * +------+---------+---------+- - - -+---------+-----------+----------+ 00094 * | 0xFE | data[0] | data[1] | | data[n] | crc[15:8] | crc[7:0] | 00095 * +------+---------+---------+- - - -+---------+-----------+----------+ 00096 */ 00097 00098 #include "SDFileSystem.h" 00099 00100 #define SD_COMMAND_TIMEOUT 5000 00101 00102 SDFileSystem::SDFileSystem(PinName mosi, PinName miso, PinName sclk, PinName cs, const char* name) : 00103 FATFileSystem(name), _spi(mosi, miso, sclk), _cs(cs) { 00104 _cs = 1; 00105 } 00106 00107 int SDFileSystem::disk_initialize() { 00108 00109 _spi.frequency(100000); // Set to 100kHz for initialisation 00110 00111 // Initialise the card by clocking it a bit (cs = 1) 00112 for(int i=0; i<16; i++) { 00113 _spi.write(0xFF); 00114 } 00115 00116 // send CMD0, should return with all zeros except IDLE STATE set (bit 0) 00117 if(_cmd(0, 0) != 0x01) { 00118 fprintf(stderr, "Not in idle state\n"); 00119 return 1; 00120 } 00121 00122 // ACMD41 to give host capacity support (repeat until not busy) 00123 // ACMD41 is application specific command, so we send APP_CMD (CMD55) beforehand 00124 for(int i=0;; i++) { 00125 _cmd(55, 0); 00126 int response = _cmd(41, 0); 00127 if(response == 0) { 00128 break; 00129 } else if(i > SD_COMMAND_TIMEOUT) { 00130 fprintf(stderr, "Timeout waiting for card\n"); 00131 return 1; 00132 } 00133 } 00134 00135 _sectors = _sd_sectors(); 00136 00137 // Set block length to 512 (CMD16) 00138 if(_cmd(16, 512) != 0) { 00139 fprintf(stderr, "Set block timeout\n"); 00140 return 1; 00141 } 00142 00143 _spi.frequency(1000000); // Set to 1MHz for data transfer 00144 return 0; 00145 } 00146 00147 int SDFileSystem::disk_write(const char *buffer, int block_number) { 00148 // set write address for single block (CMD24) 00149 if(_cmd(24, block_number * 512) != 0) { 00150 return 1; 00151 } 00152 00153 // send the data block 00154 _write(buffer, 512); 00155 return 0; 00156 } 00157 00158 int SDFileSystem::disk_read(char *buffer, int block_number) { 00159 // set read address for single block (CMD17) 00160 if(_cmd(17, block_number * 512) != 0) { 00161 return 1; 00162 } 00163 00164 // receive the data 00165 _read(buffer, 512); 00166 return 0; 00167 } 00168 00169 int SDFileSystem::disk_status() { return 0; } 00170 int SDFileSystem::disk_sync() { return 0; } 00171 int SDFileSystem::disk_sectors() { return _sectors; } 00172 00173 // PRIVATE FUNCTIONS 00174 00175 int SDFileSystem::_cmd(int cmd, int arg) { 00176 _cs = 0; 00177 00178 // send a command 00179 _spi.write(0x40 | cmd); 00180 _spi.write(arg >> 24); 00181 _spi.write(arg >> 16); 00182 _spi.write(arg >> 8); 00183 _spi.write(arg >> 0); 00184 _spi.write(0x95); 00185 00186 // wait for the repsonse (response[7] == 0) 00187 for(int i=0; i<SD_COMMAND_TIMEOUT; i++) { 00188 int response = _spi.write(0xFF); 00189 if(!(response & 0x80)) { 00190 _cs = 1; 00191 return response; 00192 } 00193 } 00194 _cs = 1; 00195 return -1; // timeout 00196 } 00197 00198 int SDFileSystem::_read(char *buffer, int length) { 00199 _cs = 0; 00200 00201 // read until start byte (0xFF) 00202 while(_spi.write(0xFF) != 0xFE); 00203 00204 // read data 00205 for(int i=0; i<length; i++) { 00206 buffer[i] = _spi.write(0xFF); 00207 } 00208 _spi.write(0xFF); // checksum 00209 _spi.write(0xFF); 00210 00211 _cs = 1; 00212 return 0; 00213 } 00214 00215 int SDFileSystem::_write(const char *buffer, int length) { 00216 _cs = 0; 00217 00218 // indicate start of block 00219 _spi.write(0xFE); 00220 00221 // write the data 00222 for(int i=0; i<length; i++) { 00223 _spi.write(buffer[i]); 00224 } 00225 00226 // write the checksum 00227 _spi.write(0xFF); 00228 _spi.write(0xFF); 00229 00230 // check the repsonse token 00231 if((_spi.write(0xFF) & 0x1F) != 0x05) { 00232 _cs = 1; 00233 return 1; 00234 } 00235 00236 // wait for write to finish 00237 while(_spi.write(0xFF) == 0); 00238 00239 _cs = 1; 00240 return 0; 00241 } 00242 00243 static int ext_bits(char *data, int msb, int lsb) { 00244 int bits = 0; 00245 int size = 1 + msb - lsb; 00246 for(int i=0; i<size; i++) { 00247 int position = lsb + i; 00248 int byte = 15 - (position >> 3); 00249 int bit = position & 0x7; 00250 int value = (data[byte] >> bit) & 1; 00251 bits |= value << i; 00252 } 00253 return bits; 00254 } 00255 00256 int SDFileSystem::_sd_sectors() { 00257 00258 // CMD9, Response R2 (R1 byte + 16-byte block read) 00259 if(_cmd(9, 0) != 0) { 00260 fprintf(stderr, "Didn't get a response from the disk\n"); 00261 return 0; 00262 } 00263 00264 char csd[16]; 00265 if(_read(csd, 16) != 0) { 00266 fprintf(stderr, "Couldn't read csd response from disk\n"); 00267 return 0; 00268 } 00269 00270 // csd_structure : csd[127:126] 00271 // c_size : csd[73:62] 00272 // c_size_mult : csd[49:47] 00273 // read_bl_len : csd[83:80] 00274 00275 int csd_structure = ext_bits(csd, 127, 126); 00276 int c_size = ext_bits(csd, 73, 62); 00277 int c_size_mult = ext_bits(csd, 49, 47); 00278 int read_bl_len = ext_bits(csd, 83, 80); 00279 00280 if(csd_structure != 0) { 00281 fprintf(stderr, "This disk tastes funny! I only know about type 0 CSD structures"); 00282 return 0; 00283 } 00284 00285 int blocks = (c_size + 1) * (1 << (c_size_mult + 2)); 00286 int block_size = 1 << read_bl_len; 00287 00288 if(block_size != 512) { 00289 fprintf(stderr, "This disk tastes funny! I only like 512-byte blocks"); 00290 return 0; 00291 } 00292 00293 return blocks; 00294 }
Generated on Thu Jul 21 2022 14:33:32 by
1.7.2