Порядок инициализации:
Код
send_comstr( CMD_0, 0, 6);
ocr = 0;
do {
send_comstr(CMD_55, 0, 6);
send_comstr(ACMD_41, ocr, 6);
ocr = (comstr->arg3)|(comstr->arg2<<8)|(comstr->arg1<<16)|(comstr->arg0<<24);
} while (!(comstr->arg0 & 0x80));
У обычной SD через два-три цикла бит power-up устанавливается.
SDHC отвечает, ответные аргументы и crc совпадают с SD, но power-up не устанавливается.
Нормального даташита на HC нет. Может там другой порядок идентификации.
abcdefg
Mar 29 2008, 13:32
Цитата(KAlex @ Mar 28 2008, 13:25)

Порядок инициализации:
Код
send_comstr( CMD_0, 0, 6);
ocr = 0;
do {
send_comstr(CMD_55, 0, 6);
send_comstr(ACMD_41, ocr, 6);
ocr = (comstr->arg3)|(comstr->arg2<<8)|(comstr->arg1<<16)|(comstr->arg0<<24);
} while (!(comstr->arg0 & 0x80));
У обычной SD через два-три цикла бит power-up устанавливается.
SDHC отвечает, ответные аргументы и crc совпадают с SD, но power-up не устанавливается.
Нормального даташита на HC нет. Может там другой порядок идентификации.
См. ссылку в посте (про команду CMD8) -
http://electronix.ru/forum/index.php?showtopic=35898
Я правильно делаю?
После CMD0 посылаю CMD8 - не отвечает.
SD не HC тоже не отвечают, но работают(power-up устанавливается).
Код
send_comstr( CMD_0, 0, 6);
ocr = 0;
do {
send_comstr( CMD_8, 0, 6); // !!! нет ответа
send_comstr(CMD_55, 0, 6);
send_comstr(ACMD_41, ocr, 6);
ocr = (comstr->arg3)|(comstr->arg2<<8)|(comstr->arg1<<16)|(comstr->arg0<<24);
} while (!(comstr->arg0 & 0x80));
На 55 и 41 отвечает.
Работаю с ARM7 под Jtag. Проходил пошагово. В софте ошибок нет.
И может главное - работаю в SD-mode.
Сделал ещё
send_comstr( CMD_8, 0x1AA, 6); // отвечает 08,00,00,01,AA
Не помогло.
abcdefg
Mar 31 2008, 13:32
аналогичная проблема, CMD55 проходит нормально, а на ACMD41 приходит ответ с busy-битом и неправильной CRC. Если разберетесь - дайте знать
Разобрался. Надо зажигать 30-й бит в ocr.
send_comstr(ACMD_41, ocr | (1<<30), 6);
C инициализацией разобрался.
Вот что непонятно, как адресовать блоки старше 4G?
skripach
Apr 8 2008, 12:38
Не хотел создавать новую тему про SD, итак много, поэтому пишу сдесь.
C SPI режимом проблем не имею всё красиво работает, но не так быстро как это необходимо. В этой связи раэбираюсь с SD-mode. Подскажите пожалусто умные люди, не сочтите за труд, а то устал искать в доке ответы на столь простые вапросы, да и с англиским некоторые проблемы.
Вапросы:
1)Как посчитать CRC для разных команд? или где взять посчитаные?
2)И команды и ответы на команды по линии CMD?
3)В SD-mode данные поступают по 4-м линиям, порядок бит? Как распазнаётся первый байт данных?
Спасибо! С остальным думаю сам разберусь.
Цитата(skripach @ Apr 8 2008, 15:38)

1)Как посчитать CRC для разных команд? или где взять посчитаные?
Код
unsigned char calc_crc7(unsigned char *ptr, signed char count ){
char crc=0;
unsigned char i,data;
while (count--) {
data=*ptr++;
for (i=0;i<8;i++) {
crc <<= 1;
if ((data & 0x80)^(crc & 0x80)) crc ^=0x09;
data <<= 1;
}
}
return((crc<<1)|1);
}
Цитата(skripach @ Apr 8 2008, 15:38)

2)И команды и ответы на команды по линии CMD?
Да.
Цитата(skripach @ Apr 8 2008, 15:38)

3)В SD-mode данные поступают по 4-м линиям, порядок бит? Как распазнаётся первый байт данных?
Всегда старшим вперед. При 4-линиях старшая тетрада вперед.
После отсылки команды на чтение данных ждем(не забывая CLC) "0" на DAT0 - это стартовый бит. Далее пошли данные.
skripach
Apr 9 2008, 11:13
Спасибо, с СRC правда уже и сам разобрался.
skripach
Apr 10 2008, 10:45
А можно пару примеров команд с правильно посчитаной CRC, хочу проверить свою функцию.
40 00 00 00 00 95 CMD_0
77 00 00 00 00 65 CMD_55
69 00 00 00 00 e5 ACMD_41
skripach
Apr 10 2008, 13:16
Спасибо, проверил, всё работает. После отладки выложу свою функцию по расчёту CRC7 (ASM i8051), может кому-то пригодится.
skripach
Apr 10 2008, 22:59
В архиве моя функция по расчету CRC7 с подробнейшими коментариями + пример 'ручного' расчета + дока по CRC вообще.
Надеюсь кому-то будет полезно.
P.S. Возможно функция не самая оптимальная но работает.
skripach
Apr 13 2008, 11:56
Ещё вапросик:
Шлю карте след. команды
cmd0 - ответа нет
cmd55 - отвечает 37 00 00 01 20 83
acmd41 - ответа нет
Так и должно быть?????????
Все команды с нулевым аргументом, карта Apacer 2gb 60x.
Цитата(skripach @ Apr 13 2008, 14:56)

cmd0 - ответа нет
cmd55 - отвечает 37 00 00 01 20 83
acmd41 - ответа нет
На 41 должна отвечать. 3f 00 ff 80 00 ff или подобное.
Карта случаем не HC?
skripach
Apr 14 2008, 11:26
Нет карта не HC.
Уже не знаю на что грешить. На CMD0 не должно быть ответа?
После включения шлю CMD0, потом CMD55 и ACMD41 в цикле, но из цикла не выходит(т.е. на CMD41 нет ответа). Ответа на команду каждую команду жду 255 клоков. Да, второй ответ(когда в цикле крутится) на CMD55 - 37 00 80 01 20 09, на ACMD41 нет никогда ответа(секунд 30 ждал). Пробовал на разной частоте, даже под JTAGом если проходить по шагам одно и тоже:
cmd0 - ответа нет
cmd55 - отвечает 37 00 00 01 20 83
acmd41 - ответа нет
P.S. Как я понял на CMD55 ответ правильный?
CMD55 ответ правильный.
Ну что еще может быть, вот например:
ACMD41 -- No response (non valid command) must be an MMC -- Start MMC initialization process starting at CMD1
skripach
Apr 14 2008, 13:11
Заработало, отвечает на ACMD41 как вы и говорите 3f 00 ff 80 00 ff. Заработало после того как добавил после чтения ответа на CMD55 ещё 255 'пустых' клоков. При чем отвечает с первого раза.
Спасибо за помощ.
Цитата(skripach @ Apr 11 2008, 01:59)

В архиве моя функция по расчету CRC7
Я пошел дальше.
По скольку работаю с ARM, памяти немеряно, решил сделать табличный вариант.
Таблица генерится в RAM при запуске, далее по определению.
!!
!!
Скорость общения с картой поднялась на порядок!
Код
#define CRC7_POLYNOMIAL 0x89 /* x^7 + x^3 + 1 */
static unsigned char crc7_syndrome_table[256];
void gen_crc7_syndrome_table (void) {
int i, j, syndrome;
for (i = 0; i < 256; ++i) {
syndrome = ((i & 0x80) != 0)? i ^ CRC7_POLYNOMIAL : i;
for (j = 0; j < 7; ++j)
if (((syndrome <<= 1) & 0x80) != 0) syndrome ^= CRC7_POLYNOMIAL;
crc7_syndrome_table[i] = (unsigned char) syndrome;
}
}
char crc7 (const unsigned char *ptr) {
unsigned char i, crc7_accum = 0;
for (i = 0; i < 5; ++i) // 6 - адаптировано для SD
crc7_accum = crc7_syndrome_table[(crc7_accum << 1) ^ *ptr++];
return ((crc7_accum<<1)|1); // адаптировано для SD (+ стоп бит)
}
gnomik_
Nov 9 2009, 04:59
Здравствуйте. Работал с SD картами в SPI режиме. Но возникла необходимость заставитьработать карту в SD режиме. Пожалуйста поделитесь полным (не обрезанным) Даташитом.
Спасибо всем кто отзовется.
Для просмотра полной версии этой страницы, пожалуйста,
пройдите по ссылке.