Witam! Chciałbym ( a właściwie to muszę ) odczytać i zapisywać kartę SD w moim układzie. Karta jest podłączona do PIC18LF4550 chodzącego na 3,3V do portu SPI. na liniach portu są pull-upy 1k. do tego oczywiście linia CS. Karta to Panasonic 16MB
Korzystałem z kilku różnych przykładów, chodzi mi o cokolwiek, żeby to zrozumieć, a potem wykorzystywać. inicjacja wygląda u mnie tak:
- Wysyłam 80 cykli zegarowych
- wysyłąm CMD0 R1=0x01
- wysyłam CMD1 R1=0x00
- wysyłam CMD55
- wysyłam ACMD41 R1=0x00
- wysyłam CMD16 z parametrem 8 R1=0x00 //i tu powinna być karta zainicjowana (wygląda na to że jest) przy parametrze 512 (wyskakuje Parameter Error).
Następnie próbuję coś odczytać, ale z pamięci to ni jak ma się do tego co powinno tam być, większość zera + jakieś śmieci. Jak czytam rejestr CID to wychodzi 0x01 (może to jest kod Matsushity, ale nie udało mi się tego znaleźć) potem PASO i dalej śmieci. Ale co dziwne, cokolwiek bym nie próbował odczytać, to co 8 bajt dostaję 0x04 (co wygląda jak error Illegal Command). Mam nadzieję, że ktoś mi coś poradzi. Wklejam oczywiście kod:
pozdrawiam Grzegorz Latocha P.S. sorry za długość posta
//&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& OpenSPI(SPI_FOSC_64, MODE_11, SMPMID); //otwieram port na wolnej prędkości DelayMS(100); //odczekuję, aż karta się uruchomi
SD_CE = 1; for (timeout=0; timeout<10; timeout++) WriteSPI(0xFF); //wysyłam 10 razy 8 cykli - tego wymaga karta
SD_CE = 0; DelayMS(10); //włączam SPI w karcie //Wysyłanie CMD0 do { odpowiedz = SDSendCMD(0x00,0x00000000,0x95); } while(odpowiedz != 0x01); EEPROMWrite(0x00,odpowiedz); //nie ma wyświetlacza, więc tak sprawdzam co przyszło LED1=0;
//wysyłanie CMD1 tak długo, aż karta się uruchomi do { SD_CE = 1; WriteSPI(0xFF); SD_CE = 0; odpowiedz = SDSendCMD(0x01,0x00000000,0xFF); }while((odpowiedz & 0x01)!=0); EEPROMWrite(0x01,odpowiedz); LED2=0; WriteSPI(0xff);
SD_CE = 0; odpowiedz = SDSendCMD(55,0x00000000,0xFF); //przed komendą ACMD41 WriteSPI(0xFF); LED3=0;
do { odpowiedz = SDSendCMD(41,0x00000000,0xFF); } while((odpowiedz & 0x01) !=0); EEPROMWrite(0x02,odpowiedz);
WriteSPI(0xFF);
odpowiedz=SDSendCMD(16,8,0xff); //ustawiam rozmiar bloku na 8B EEPROMWrite(0x03,odpowiedz);
WriteSPI(0xFF);
//odczyt karty chcę odczytać 8 bajtow z adresu 0 ReadData();
LED4 = 0; DelayMS(1000); LED4 = 1;
//888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888 //888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888 void ReadData(void) { SD_CE = 0; if(SDSendCMD(17,0,0xFF)==0x00) LED3=0;
//czekanie na początek danych do { odpowiedz = ReadSPI(); } while(odpowiedz!=0xFE); //czekanie na tokena
EEPROMWrite(0x12,odpowiedz);
LED4=0;
for(Temp=0;Temp<8;Temp++) SD_Buffer[Temp] = ReadSPI(); //czytanie danych
ReadSPI(); //czytanie crc ReadSPI(); WriteSPI(0xFF); //wysyłam clock
SD_CE = 1;
for(Temp=0;Temp<8;Temp++) EEPROMWrite(0x20+Temp,SD_Buffer[Temp]); SD_CE = 1; }