Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: SD карта не просыпается
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > AVR
svchost
Добрый день!
Есть связка mega32+SD карта 128M (питание 3,3в)+ программная реализация SPI.
Воспроизводит WAV файлы 8бит 11025Гц.
Установил карту 1G. Не просыпается по CMD1 (в ответ получаю 01).
Подавал связку CMD55 (в ответ получаю 01)+CMD41, CMD8 на обе команды ответ 05 (не существующая команда).
Все команды подаю с правильным CRC. В кардридере все работает. Купил флешку на 2G тоже самое.
Может кто сталкивался, подскажите пожалуйста в чем трабл?

Спасибо.
aaarrr
Cначала нужно дать минимум 74 клока, затем CMD0, затем ACMD41.
svchost
Цитата(aaarrr @ Jun 1 2009, 15:56) *
Cначала нужно дать минимум 74 клока, затем CMD0, затем ACMD41.




все это соблюдается...
у меня работают флешки 32М. 64М, 128М
проблема с 1 и 2G
etoja
Цитата(svchost @ Jun 1 2009, 17:01) *
все это соблюдается...
у меня работают флешки 32М. 64М, 128М
проблема с 1 и 2G



У них в кластере не два, а четыре сектора.
aaarrr
Цитата(svchost @ Jun 1 2009, 17:01) *
все это соблюдается...
у меня работают флешки 32М. 64М, 128М
проблема с 1 и 2G

Значит что-то все-таки не соблюдается - инициализация у всех одинаковая. Большего размера карты могут ощутимо дольше инициализироваться, точно ждете 1 секунду?

Цитата(etoja @ Jun 1 2009, 17:24) *
У них в кластере не два, а четыре сектора.

Да можно и шестнадцать сделать, только при чем тут это?
svchost
Цитата(aaarrr @ Jun 1 2009, 17:31) *
Значит что-то все-таки не соблюдается - инициализация у всех одинаковая. Большего размера карты могут ощутимо дольше инициализироваться, точно ждете 1 секунду?


Да можно и шестнадцать сделать, только при чем тут это?



подаю CMD0 в ответ получаю 01
подаю CMD1 в ответ получаю 01, повторяю команду до 32 раз в ответ 01
ожидаю 1 сек
повторяю CMD1 в ответ 01...

не могу понять в чем дело...
грешил на карту, купил сегодня новую...все один к одному
aaarrr
CMD1 или ACMD41? CMD1 использовать не рекомендуется.
woroba
Цитата(svchost @ Jun 1 2009, 17:42) *
Добрый день!
Есть связка mega32+SD карта 128M (питание 3,3в)+ программная реализация SPI.
Воспроизводит WAV файлы 8бит 11025Гц.
Установил карту 1G. Не просыпается по CMD1 (в ответ получаю 01).
Подавал связку CMD55 (в ответ получаю 01)+CMD41, CMD8 на обе команды ответ 05 (не существующая команда).
Все команды подаю с правильным CRC. В кардридере все работает. Купил флешку на 2G тоже самое.
Может кто сталкивался, подскажите пожалуйста в чем трабл?

Спасибо.


У меня вот это работает с 1G.
Посмотрите может поможет.

unsigned char MMC_Init(void)
{
unsigned char i=0,b=0;
SPICS=1; // disable MMC
for(i=0; i < 10; i++) SPI(0xFF);
SPICS=0; // enable MMC
b=Command(0x40,0,0x95);
i=0;
while (b!=1)
{
i++;
b=SPI(0xFF);
if (i==0) return 1;
}
delay_ms(2000);
b=Command(0x41,0,0xFF);
i=0;
//buf2[i]=b;
while (b!=1)//!=0)
{
i++;
b=SPI(0xFF);
//buf2[i]=b;
if (i==0) return 2;
}
return 0;
}
svchost
Цитата(aaarrr @ Jun 1 2009, 17:44) *
CMD1 или ACMD41? CMD1 использовать не рекомендуется.




ACMD41 не воспринимает
CMD55 (ответ 01)+CMD41(ответ 05 -несуществующая команда)
aaarrr
Цитата(svchost @ Jun 1 2009, 17:56) *
ACMD41 не воспринимает

Так, а карта не SDHC случаем?

Последовательность инициализации такая:

1. 74 или больше "пустых" клоков.
2. CMD0
3. CMD8. Если есть ответ, значит имеем дело с SD 2.0
4. ACMD41. Если нет ответа, значит имеем дело с MMC
5. Читаем OCR, проверяем на предмет Standard или High Capacity.
svchost
Цитата(aaarrr @ Jun 1 2009, 22:39) *
Так, а карта не SDHC случаем?

Последовательность инициализации такая:

1. 74 или больше "пустых" клоков.
2. CMD0
3. CMD8. Если есть ответ, значит имеем дело с SD 2.0
4. ACMD41. Если нет ответа, значит имеем дело с MMC
5. Читаем OCR, проверяем на предмет Standard или High Capacity.



Проблема решена!

1. 74 или больше "пустых" клоков.
2. CMD0 (ответ 01)
3. CMD8 (ответ 05) Если есть ответ, значит имеем дело с SD 2.0 и для инициализации используем ACMD41
(Этот пункт можно пропустить, если предполагается использование только 1.0)
4. СMD1 (ответ 01) Ответа не было в п3.
5. Читаем 255 байт с карты (не принципиально! от числа будет зависит количество циклов) анализируем, на всякий случай,
должно быть FF иначе какая то ошибка.
6. Повторяем п.4, число повторений зависит от карты и НЕ прямопропорционально емкости, как логично было бы
предположить (для 1G около 20, 2G -всего 5, 512M -8).

Думаю можно сделать вывод:
для выполнения инициализации некоторые карты требуется тактировать!


Для эксперимента подавал CMD1 (ответ 01), не выполняя чтения между командами, около 10000 раз
карту не смог инициализировать.

Пока разбирался с инициализации написал подсчет CRC7 на ASM (могу поделиться)

Спасибо.
aaarrr
Для инициализации SD всегда нужно использовать ACMD41, иначе от MMC не отличите. Карты не требуют тактирования, судя по всему, Вы просто не выдерживаете Nrc между командами.
svchost
Цитата(aaarrr @ Jun 2 2009, 00:16) *
Для инициализации SD всегда нужно использовать ACMD41, иначе от MMC не отличите. Карты не требуют тактирования, судя по всему, Вы просто не выдерживаете Nrc между командами.


Тактировать я имел ввиду для выполнения инициализации.
В моем случае ACMD41 не воспринимается CMD55 (ответ 01)+CMD41(ответ 05 -несуществующая команда)
Сколько циклов должно быть Ncr?

Сколько должно быть циклов между CMD55 и CMD41?
aaarrr
Цитата(svchost @ Jun 2 2009, 00:29) *
Сколько циклов должно быть Ncr?

Сколько должно быть циклов между CMD55 и CMD41?

Время Nrc - 8 тактов, между ответом на CMD55 и CMD41 как раз и должно быть Nrc.
sonycman
Ncr может быть от 0 до 8 байт.

Что характерно, действительно после любой команды нужно подавать 1 байт холостого чтения, иначе карта не будет нормально воспринимать следующую команду...
adc
Цитата(svchost @ Jun 2 2009, 00:03) *
...
Пока разбирался с инициализации написал подсчет CRC7 на ASM (могу поделиться)
...

Было бы интересно взглянуть. rolleyes.gif
aaarrr
Цитата(sonycman @ Jun 2 2009, 08:02) *
Ncr может быть от 0 до 8 байт.

Ncr - до 8, Nrc - 1.

Цитата(sonycman @ Jun 2 2009, 08:02) *
Что характерно, действительно после любой команды нужно подавать 1 байт холостого чтения, иначе карта не будет нормально воспринимать следующую команду...

Вот это и есть Nrc.
svchost
Цитата(adc @ Jun 2 2009, 10:19) *
Было бы интересно взглянуть. rolleyes.gif


Пожалуйста...

CLR CRC
...
LDI A,$40
CALL CRC7
...
adc
Цитата(svchost @ Jun 4 2009, 00:08) *
Пожалуйста...
..

Спасибо!
Несколько сыровато. Код непроверенный?
aaarrr
Цитата(adc @ Jun 4 2009, 10:57) *
Несколько сыровато. Код непроверенный?

Да уж, надо было так запутать sad.gif

Вот что получается, если написать просто "в лоб":
Код
; X - указатель на данные,
; b - длина

crc7:
    clr    crc
    ldi    d, 0x12
crc7_0:
    ld    a, X+
    eor    crc, a
    ldi    c, 8
crc7_1:
    lsl    crc
    brcc    PC+0x02
    eor    crc, d
    dec    c
    brne    crc7_1
    dec    b
    brne    crc7_0
    ori    crc, 1
    ret
sonycman
А я в сети нашёл такой код:
Код
u8    CRC7(u8* chr, int cnt)
{
    int i,a;
    u8 crc = 0, data;

    for (a=0; a < cnt; a++)
    {
        data=chr[a];
        for (i=0; i < 8; i++)
        {
            crc <<= 1;
            if ((data ^ crc) & 0x80) crc ^= 0x09;
            data <<= 1;
        }
    }
    return    crc;
}

Интересно, нельзя никак избежать побитного цикла (i), чтобы ускорить рассчёт?
aaarrr
Цитата(sonycman @ Jun 4 2009, 14:57) *
Интересно, нельзя никак избежать побитного цикла (i), чтобы ускорить рассчёт?

Можно, конечно. Хотя ускорять рассчет 5 байт большого смысла нет.
Вот для данных - это другое дело.
sonycman
Цитата(aaarrr @ Jun 4 2009, 15:14) *
Можно, конечно. Хотя ускорять рассчет 5 байт большого смысла нет.

Это понятно, но всё равно интересно - как?
В сети нигде не нашёл работающего примера без битового цикла...

Для данных это да. Но для SPI сумма не нужна (странно, конечно, но неужели надёжность SPI близка к 100%, чтобы в контрольной сумме отпала надобность?), а SDIO контроллеры будут считать её аппаратно...

ЗЫ: вот ваша процедура на Си, она пооптимальнее, чем приведённая мной:
Код
u8    CRC7(u8* chr, int cnt)
{
    int i,a;
    u8 crc = 0;

    for (a=0; a < cnt; a++)
    {
        crc ^= chr[a];
        for (i=0; i < 8; i++)
        {
            if (crc & 0x80)
            {
                crc <<= 1;
                crc ^= 0x12;
            }
            else crc <<= 1;
        }
    }
    crc |= 1;
    return    crc;
}
aaarrr
Цитата(sonycman @ Jun 4 2009, 15:46) *
Это понятно, но всё равно интересно - как?

Табличкой, например.

Цитата(sonycman @ Jun 4 2009, 15:46) *
Для данных это да. Но для SPI сумма не нужна (странно, конечно, но неужели надёжность SPI близка к 100%, чтобы в контрольной сумме отпала надобность?), а SDIO контроллеры будут считать её аппаратно...

Для SPI ее можно не включать, но это не значит, что она не нужна. Я, например, включаю и использую.

Цитата(sonycman @ Jun 4 2009, 15:46) *
ЗЫ: вот ваша процедура на Си, она пооптимальнее, чем приведённая мной:

Спасибо, конечно, а я-то специально на асм переводил smile.gif

Если интересно, то вот вариант для данных:
Код
const u_short sd_crc16_table_a[0x10] =
{
    0x0000, 0x1231, 0x2462, 0x3653,
    0x48c4, 0x5af5, 0x6ca6, 0x7e97,
    0x9188, 0x83b9, 0xb5ea, 0xa7db,
    0xd94c, 0xcb7d, 0xfd2e, 0xef1f
};

const u_short sd_crc16_table_b[0x10] =
{
    0x0000, 0x1021, 0x2042, 0x3063,
    0x4084, 0x50a5, 0x60c6, 0x70e7,
    0x8108, 0x9129, 0xa14a, 0xb16b,
    0xc18c, 0xd1ad, 0xe1ce, 0xf1ef
};

u_int sd_crc16(u_char *buff, u_int len)
{
    u_char data;
    u_short crc = 0;

    while(len--)
    {
        data = *buff++ ^ (crc >> 0x08);
        crc = (sd_crc16_table_a[(data & 0xf0) >> 4] ^ sd_crc16_table_b[data & 0x0f]) ^ (crc << 8);
    }
    return crc;
}
sonycman
Цитата(aaarrr @ Jun 4 2009, 16:00) *
Табличкой, например.

Да, это вариант. Но самое прикольное - это хитрые варианты, когда без таблиц и без цилов, быстрое вычисление всего лишь несколькими командами.
Наверное, такое возможно не всегда...

Цитата(aaarrr @ Jun 4 2009, 16:00) *
Если интересно, то вот вариант для данных:

Спасибо, красивая реализация, небольшие таблички и минимум вычислений smile.gif
svchost
Цитата(aaarrr @ Jun 4 2009, 11:25) *
Да уж, надо было так запутать sad.gif

Вот что получается, если написать просто "в лоб":
Код
; X - указатель на данные,
; b - длина

crc7:
    clr    crc
    ldi    d, 0x12
crc7_0:
    ld    a, X+
    eor    crc, a
    ldi    c, 8
crc7_1:
    lsl    crc
    brcc    PC+0x02
    eor    crc, d
    dec    c
    brne    crc7_1
    dec    b
    brne    crc7_0
    ori    crc, 1
    ret



Подпрограмма CRC7 полностью работоспособна.
У каждого свое решение. Считаю, что мой вариант полностью отражает
алгоритм подсчета CRC7 и вполне понятен.

Спасибо.
aaarrr
Цитата(svchost @ Jun 4 2009, 19:45) *
Подпрограмма CRC7 полностью работоспособна.
У каждого свое решение. Считаю, что мой вариант полностью отражает
алгоритм подсчета CRC7 и вполне понятен.

Я лишь предложил более короткий и быстрый вариант. Не обижайтесь.
ivstech
Цитата(sonycman @ Jun 4 2009, 18:26) *
<br />Да, это вариант. Но самое прикольное - это хитрые варианты, когда без таблиц и без цилов

Когда флэша нехватает, я использую такой код
Код
; in/out YH аккумулятор
; in R18 следующий байт
CRC7Update:
   eor YH, R18
  ; Левый полубайт
   mov R19, YH
   andi R19, 0xF0
   swap R19
   eor YH, R19
   swap R19
   add R19, R19
   brcc CRC7Skip
   ldi YL, 0x01
   eor YH, YL
CRC7Skip:
   mov YL, R19
  ; Правый полубайт
   mov R19, YH
   andi R19, 0x0F
   swap R19
   eor YL, R19
   swap R19
   add R19, R19
   eor YL, R19
   mov YH, YL
   ret

и
Код
; IN:  R4, R5 - аккумулятор CRC
;      R18 - значение
; OUT: R4, R5

; По модулю 0x11021
CRC16Update:
   push R18
   push R19
   eor R4, R18
  ; Левый полубайт
   mov R19, R4
   andi R19, 0xF0
   mov R18, R19
   swap R19
   eor R4, R19
   add R19, R19
   eor R5, R19
  ; Правый полубайт
   mov R19, R4
   andi R19, 0x0F
   eor R18, R19
   swap R19
   eor R5, R19
   add R19, R19
   brcc CRC16Skip
   clr R4
   inc R4
   eor R5, R4
CRC16Skip:
   eor R18, R19
   mov R4, R5
   mov R5, R18
   pop R19
   pop R18
   ret
adc
to ivstech and aaarrr: странно но результат вычисления CRC7 ваших алгоритмов разный.?! это нормально? rolleyes.gif
разница в этой строчке у Вас aaarrr:
Код
ori    crc, 1

Зачем она?
aaarrr
Цитата(adc @ Jun 5 2009, 10:38) *
Зачем она?

Считаем мы CRC7, а это end bit - см. Command Format в спецификации SD.
svchost
Контрольный байт для отправки SD карте получается
вычислением CRC7 путем суммирования команды, 4 аргументов и
смешением результата влево и установкой bit0
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.