#include #include //////////////////////////////////////////////////////////////////////////////////////////// // ATmega8: //////////////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////// // microSD (HC) 3,3 V // TX - // RX - 7 mA. // Ожидание - 0 mA. //////////////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////// crc (!) System unsigned int crc; // crc unsigned int bcrc; // crc буфер unsigned int a; // a - счёт unsigned int b; // b - счёт /////////////////////////////////////////////// счёт unsigned char x; // x - счёт /////////////////////////////////////////////// счёт unsigned char x1; // x1 - счёт ///////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////// fcrc: void fcrc(void) { crc ^= bcrc; for( a = 0; a < 16; a++ ){ if (crc & 0x8000) crc = ( crc << 1 ) ^ 0x1021; // CRC-16-CCITT // 0x1021 else crc = crc << 1; }; } ///////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////// microSD: /////////////////////////////////////////////// программный SPI3 microSD: unsigned char tx3; // tx3 - SPI3 unsigned char rx3; // rx3 - SPI3 unsigned char mask3; // mask3 - SPI3 ////////////////////////////////////////// программный SPI3/4МГц/0.000.060 microSD: void SPI3(void) { rx3=0; // сброс RX mask3=0b10000000; do { if (tx3 & mask3) PORTD.7 = 1;// выход MOSI else PORTD.7 = 0;// выход MOSI delay_us(2); PORTD.6=1; // выход SCK if (PIND.5) rx3 |= mask3; // вход MISO PORTD.6=0; // выход SCK mask3=(mask3>>1); } while (mask3); delay_us(2); PORTD.7 = 0; // сброс MOSI } /////////////////////////////// таймаут microSD: unsigned char tm_microSD; // таймаут microSD. /////////////////////////////// error microSD: unsigned char error_microSD_EEPROM; // error_microSD_EEPROM. -начальное 0. /////////////////////////////// буфер microSD: unsigned char bufer_microSD[512]={ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 }; ////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////// TX_microSD: void TX_microSD(unsigned long x) { /////////////////////// crc bufer_microSD[512]: crc=0xFFFF; for (b=0;b<510;b=b+2) { bcrc=bufer_microSD[b]; bcrc=(bcrc<<8)|bufer_microSD[b+1]; fcrc(); }; bufer_microSD[510]=(crc>>8); // crc bufer_microSD[511]=crc; // crc /////////////////////////////////////////////// PORTB.0=0; // SS microSD /////////////////////// запись Data: tx3=0x58; SPI3(); // 01xx xxxx + Номер команды - CMD24 tx3=(x>>24); SPI3(); // адрес tx3=(x>>16); SPI3(); // адрес tx3=(x>>8); SPI3(); // адрес tx3=x; SPI3(); // адрес tx3=0x00; SPI3(); // 0000 0000. CRC - 0 // ответ R1: 0000 0000 - команда microSD принята tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); // STATUS R1 0000 0000 //////////////////////////////////////////////////////////////////////////////// метка: tx3=0xFE; SPI3(); // 0xFE метка для команды - CMD24 ////////////////////// for (a=0; a<512; a++) { tx3=bufer_microSD[a]; SPI3(); // bufer_microSD > microSD }; //////////////////// tx3=0x00; SPI3(); // CRC - 0 tx3=0x00; SPI3(); // CRC - 0 /////////////////////////////////////////////////////////// ответ - данные приняты 0xE5: tx3=0xFF; SPI3(); // SPI пустой /////////////////////////////////////////////////// ждём окончания записи... OUT = 0xFF: while ( (x1 != 0xFF) && (tm_microSD != 255) ) { tx3=0xFF; SPI3(); x1=rx3; // MOSI 0x00 > MOSI 0xFF // -цикл 34...53 tm_microSD++; }; ////////////// if (tm_microSD == 255) { // таймаут microSD: error_microSD_EEPROM |= 0b00010000; // 0001 0000 - error microSD_TX }; tm_microSD = 0; // сброс таймаут tm_microSD. //////////////////////////////////////////////////////////////// PORTB.0=1; // SS microSD //////////////////////////////////////////////////////////////////////////////////////// // microSD - ток = 0 mA. } //////////////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////// RX_microSD: void RX_microSD(unsigned long x) { PORTB.0=0; // SS microSD /////////////////////// читать Data: tx3=0x51; SPI3(); // 01xx xxxx + Номер команды - CMD17 tx3=(x>>24); SPI3(); // адрес по 512 байт tx3=(x>>16); SPI3(); // адрес по 512 байт tx3=(x>>8); SPI3(); // адрес по 512 байт tx3=x; SPI3(); // адрес по 512 байт tx3=0x00; SPI3(); // 0000 0000. CRC - 0 // ответ R1: 0000 0000 - команда microSD принята tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); x1=rx3; // STATUS R1 0000 0000 ////////////////////////////////////////////////////////////////////// ждём метку (0xFE): while ( (x1 != 0xFE) && (tm_microSD != 255) ) { tx3=0xFF; SPI3(); x1=rx3; // MOSI 0xFF > MOSI 0xFE // -цикл ...5 tm_microSD++; }; ////////////// if (tm_microSD == 255) { // таймаут microSD: error_microSD_EEPROM |= 0b00000100; // 0000 0100 - error microSD_RX }; ////////////// tm_microSD = 0; // сброс таймаут tm_microSD. //////////////////////////////////////////////////////////////////////////// читать Data: for (a=0; a<512; a++) { tx3=0xFF; SPI3(); bufer_microSD[a]=rx3;// microSD > bufer_microSD ////////////////////////////////////////////////////////// }; tx3=0x00; SPI3(); // CRC - 0 tx3=0x00; SPI3(); // CRC - 0 /////////////////////// PORTB.0=1; // SS microSD ////////////////////////////////////////////////////////////////////////////// tx3=0xFF; SPI3(); // SPI пустой (!) // microSD - ток = 0 mA. ///////////////////// crc bufer_microSD[512] RX: crc=0xFFFF; for (b=0;b<512;b=b+2) { bcrc=bufer_microSD[b]; bcrc=(bcrc<<8)|bufer_microSD[b+1]; fcrc(); }; /////////////////////////// проверка crc: if (crc != 0) { error_microSD_EEPROM |= 0b00000010; // error_microSD_crc }; /////////////////////////////////////////////// } ///////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////// void main(void) { ////////////////////////////////////////////// SPI2 программный microSD DDRD.5=0; // MISO PORTD.5=1; // MISO +(!) 0xFF DDRD.6=1; // SCK PORTD.6=0; // SCK DDRD.7=1; // MOSI PORTD.7=0; // MOSI DDRB.0=1; // SS PORTB.0=1; // SS //////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////// инициализация microSD: ///////////////////////////////// Преамбула - 80 синхроимпульсов. for (x=0; x<10; x++) { tx3=0xFF; SPI3(); }; // "11111111" PORTB.0=0; // SS microSD ///////////////////////////////////////////////////////////////// //сброс microSD и перевод в режим SPI: tx3=0x40; SPI3(); // 01xx xxxx + Номер команды - CMD0 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x95; SPI3(); // CRC7 // ответ R1: 0000 0001 - команда microSD принята tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); x1 = rx3; // STATUS R1 0000 0001 //состояния интерфейса microSD (напряжение хоста и любой шаблон): tx3=0x48; SPI3(); // 01xx xxxx + Номер команды - CMD8 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x01; SPI3(); // 0000 0001 -напряжение хоста 2.7 – 3.6 V tx3=0xAA; SPI3(); // 1010 1010 -1010 1010 -проверочный шаблон tx3=0x87; SPI3(); // CRC7 // ответ R7: 0000 0001; 0000 0000; 0000 0000; 0000 0001; 1010 1010 tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); // STATUS R1 0000 0001 tx3=0xFF; SPI3(); // 0000 0000 tx3=0xFF; SPI3(); // 0000 0000 tx3=0xFF; SPI3(); // 0000 0001 -напряжение хоста 2.7 – 3.6 V tx3=0xFF; SPI3(); x1 = rx3; // 1010 1010 -проверочный шаблон ///////////////////////////////////////////////////////////////// while ( (x1 != 0x00) && (tm_microSD != 255) ) { // MOSI 0xFF > MOSI 0x00 // -цикл 2...21 //////////////////////////////// ждём ответ R1: 0000 0000 STATUS: //старт microSD: // microSD версия v.2 и выше. tx3=0x77; SPI3(); // 01xx xxxx + Номер команды - CMD55 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // CRC7 // ответ R1: 0000 0001 - команда microSD принята tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); x1 = rx3; // STATUS R1 0000 0001 // tx3=0x69; SPI3(); // 01xx xxxx + Номер команды - CMD41 tx3=0x40; SPI3(); // 0100 0000 - хост поддерживает карту памяти высокой емкости SD tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // 0000 0000 tx3=0x00; SPI3(); // CRC7 // ответ R1: 0000 0000 - инциализация microSD завершена. tx3=0xFF; SPI3(); // задержка 1 байт 0xFF tx3=0xFF; SPI3(); x1 = rx3; // STATUS R1 0000 0000 ///////////////////////////////////////////////////////////////////// tm_microSD++; // таймаут microSD. }; ////////////// if (tm_microSD == 255) { // таймаут microSD: error_microSD_EEPROM |= 0b00000001; // 0000 0001 - error init microSD }; tm_microSD = 0; // сброс таймаут tm_microSD. /////////////////////////////////////////// PORTB.0=1; // SS microSD ////////////////////////////////////////////////////////////////////////////////// // microSD - ток = 7 mA. ////////////////////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////////////////////////// RX_microSD(x); TX_microSD(x); ////////////////////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////////////////////////// }