реклама на сайте
подробности

 
 
> STM32 Вопрос про I2C, непонимаю даташит или что-то не то
Vladimir Prokofi...
сообщение Aug 25 2011, 10:22
Сообщение #1


Участник
*

Группа: Участник
Сообщений: 47
Регистрация: 9-03-11
Пользователь №: 63 481



Пытаюсь послать два байта слейву по I2C:
1. Выставляем СТАРТ
2. Получаем в прерывании что старт прошел (Событие 5 ) I2C_EVENT_MASTER_MODE_SELECT:
Шлем 7битный адрес слейва по этому прерыванию
3. Получаем прерывание что отослан адрес. Игнорируем, так как должно сразу придти прерывание TxE
4. По прерыванию о пустоте буфера ( События 8 и 8_2 )
case I2C_EVENT_MASTER_BYTE_TRANSMITTING:
case I2C_EVENT_MASTER_BYTE_TRANSMITTED:
Если первый раз пришло, то шлем БАЙТ1.
Если второй раз пришло, то шлем БАЙТ2.
Если третий раз пришло то:


Вот тут хочется послать стоп. Но это прерывание пришло так как TxE = 1. Реально байт еще не ушел. Когда он уйдет, то, судя по эрате, должен выставиться битик BTF. Поэтому я считаю что его надо ждать. Я бы написал так:
Если третий раз пришло то:
Если BTF == 1 то шлем СТОП
Но этот бит не устанавливается. Прерывания приходят и приходят, БТФ = 0. Почему?


В принципе в эрате написано что СТОП следует выставлять когдв либо TxE = 1 либо BTF = 1;
Если я пошлю СТОП когда TxE = 1 а BTF = 0 то не получится ли так, что СТОП оборвет последний байт?

PS

И непонятно еще такая штука, у меня сложилось понимание, что:
когда срабатывает прерывание TxE, байт начинает слаться. Если ничего не кинуть в буфер, то прерывание не сбросится, и будет постоянно вызываться, пока не установится бит BTF?
Т.е. контроллер будет ждать пока уйдет последний байт в любом случае...


Сообщение отредактировал Vladimir Prokofiev - Aug 25 2011, 10:31
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
dfyz.s
сообщение Feb 6 2013, 05:40
Сообщение #2





Группа: Участник
Сообщений: 13
Регистрация: 10-01-11
Пользователь №: 62 132



Большое спасибо за подробное описание! Не могли ли вы перезалить архив, а то у меня пишет, что поврежден

Сообщение отредактировал dfyz.s - Feb 6 2013, 05:41
Go to the top of the page
 
+Quote Post
KnightIgor
сообщение Feb 6 2013, 20:20
Сообщение #3


Знающий
****

Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725



Цитата(dfyz.s @ Feb 6 2013, 06:40) *
Большое спасибо за подробное описание!

На Ваш вопрос мне в личку я не могу отправить ответ в личку Вам, т.к. мне идет сообщение, что личка у Вас или отключена, или переполнена. Что бум делать?

А пока сюда. Извините, если много букав.

1. Функция Init_I2C() должна быть вызвана на этапе инициализации программы. Если предполагается работа с I2C1, то port равен 0, если работа с I2C2, то port равен 1, а если нужно будет общаться в проекте по двум шинам, надо вызвать Init_I2C() два раза:

Init_I2C(0, 0);
Init_I2C(1, 0);

Если второй параметр равен 0, будет установлена скорость I2C в 400kHz.

Далее, при необходимости произвести обмен по I2C1 или I2C2, нужно вызывать функции, указав им номер порта для обмена.
Например:

Чтение 10-ти байт с устройства I2C с адресом 0x58 на шине I2C2 (port = 1) простейшей функцией ReadW_I2C выглядит так:
Код
{
    unsigned char buffer[1+10] = {0x58};
    int result;

    result = ReadW_I2C(1, buffer, 0, 10); // 0 bytes to write to before, 10 bytes to read
    if (result == 10)
    {
        // full success, all bytes read,
        // the received data are in buffer[1] to buffer[10]
        memcpy(myglobalbuffer, &buffer[1], result); // copy the received bytes to some global buffer
    } else {
        // some error occurred: the result contains an error code if < 0 or
        // maybe less than 10 bytes has been read if result >= 0 and < 10.
        // make a decision what to do...
    }
}

Другой пример чтения 16-ти байт из I2C EEPROM размером до 64KB с адреса 0xAABB в этой памяти, и пусть EEPROM сидит на I2C1 (port = 0). Сама EEPROM имеет адрес 0xA0 на шине.
Код
{
    unsigned char buffer[1+2+16] = {0xA0}; // one byte for the I2C ID, 2 bytes for memory address, 16 bytes for data.
    int result;

    buffer[1] = 0xAABB / 256; // MSB goes first!
    buffer[2] = 0xAABB % 256; // LSB

    result = ReadW_I2C(0, buffer, 2, 16); // 2 bytes of memory address to write to before, 16 bytes to read afterwards
    if (result == 16)
    {
        // full success, all bytes read,
        // the received data are in buffer[3] to buffer[18]
        memcpy(myglobalbuffer, &buffer[3], result); // copy the received bytes to some global buffer
    } else {
        // some error occurred: the result contains an error code if < 0 or
        // maybe less than 16 bytes has been read if result >= 0 and < 16.
        // make a decision what to do...
    }
}

Следует помнить, что функция ReadW_I2C() - блокирующая, то есть не возвращает управление, пока не проделает всю работу. Если устройство "затянет" шину (а такое бывает), все повиснет. Чтобы такое не случилось, следует использовать, например, ReadC_I2C(), которая будет вызывать call back, пока крутится в цикле ожидания. Таким образом, можно в этом call back анализировать время работы и оборвать процесс, если он затянулся. См. комментарии к ReadC_I2C() в коде.

2. О конструкции control[port].rcc и функции RCC_Configuration() заморачиваться пока не нужно. Это моя функция, которая обрабатывает поле структуры control для указанного порта (то есть, для I2C1 или I2C2) с целью включить тактирование периферии, связанной с I2C1 или I2C2. Кстати, коль Вы упомянули, что недавно программируете этот процессор, укажу в этой связи на типичное недопонимание сути его работы (как следует из вопросов на форуме): прежде, чем начать работать с тем или иным периферийным устройством - I2C, USART и т.п. - необходимо сначало включить ему тактирование через узел RCC. Вот этим и занимается RCC_Configuration(), а структура control содержить всякие адреса, флаги и прочие вещи, необходимые для тех или иных операций с I2C. Короче, обо всем "позабочено", см. пункт 1). ответа.

Успехов.

Сообщение отредактировал KnightIgor - Feb 6 2013, 21:10
Go to the top of the page
 
+Quote Post

Сообщений в этой теме
- Vladimir Prokofiev   STM32 Вопрос про I2C   Aug 25 2011, 10:22
- - DmitryDI   Ну и как получилось завести I2C? Может есть вариан...   Aug 25 2011, 14:14
|- - Vladimir Prokofiev   Цитата(DmitryDI @ Aug 25 2011, 18:14) Ну ...   Aug 25 2011, 15:22
|- - KnightIgor   Цитата(Vladimir Prokofiev @ Aug 25 2011, 17...   Aug 29 2011, 08:59
|- - Vladimir Prokofiev   Цитата(KnightIgor @ Aug 29 2011, 12:59) I...   Aug 29 2011, 11:19
|- - KnightIgor   Цитата(Vladimir Prokofiev @ Aug 29 2011, 13...   Aug 29 2011, 12:15
|- - Vladimir Prokofiev   Большое спасибо! Скачал, пошел смотреть!   Aug 30 2011, 08:31
|- - Vladimir Prokofiev   Вроде заработало, но, кажется, основная ошибка был...   Aug 30 2011, 15:25
|- - KnightIgor   Цитата(Vladimir Prokofiev @ Aug 30 2011, 17...   Aug 30 2011, 16:49
|- - Vladimir Prokofiev   Уже считал что все получилось, но тут опять столкн...   Sep 15 2011, 10:47
- - dfyz.s   Здравствуйте! Сейчас разбираюсь с похожей проб...   Feb 5 2013, 18:28
|- - KnightIgor   Цитата(dfyz.s @ Feb 5 2013, 19:28) Сейчас...   Feb 5 2013, 21:41
|- - KnightIgor   Цитата(dfyz.s @ Feb 6 2013, 06:40) Не мог...   Feb 6 2013, 12:05
- - dfyz.s   Да, какая то фигня с личными сообщениями, хотя в н...   Feb 8 2013, 17:10
- - polyname   Непонятно что они курили когда разрабатывали I2C ?...   Feb 8 2013, 17:47
- - dfyz.s   )))) Согласен. Но это не решает проблемы. Сейчас ...   Feb 8 2013, 18:04
|- - KnightIgor   Цитата(dfyz.s @ Feb 8 2013, 19:04) Сейчас...   Feb 8 2013, 20:25
- - dfyz.s   Игорь, большое спасибо за ваши обяснения! Мне...   Feb 10 2013, 19:31
|- - _Артём_   Цитата(dfyz.s @ Feb 10 2013, 21:31) отлад...   Feb 10 2013, 20:07
|- - KnightIgor   Цитата(dfyz.s @ Feb 10 2013, 20:31) Мне с...   Feb 11 2013, 11:02
- - dfyz.s   Да, скорее всего я где-то напортачил. Надо протест...   Feb 11 2013, 12:46
|- - KnightIgor   Цитата(dfyz.s @ Feb 11 2013, 13:46) Пробе...   Feb 12 2013, 08:39
- - dfyz.s   Да, с схемотехнической точки зрения похоже все хор...   Feb 13 2013, 06:34


Reply to this topicStart new topic
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 29th July 2025 - 18:55
Рейтинг@Mail.ru


Страница сгенерированна за 0.01402 секунд с 7
ELECTRONIX ©2004-2016