05.04.2020, 18:03
|
|
Временная регистрация
Регистрация: 19.08.2010
Сообщений: 94
Сказал спасибо: 8
Сказали Спасибо 35 раз(а) в 25 сообщении(ях)
|
не могу запустить I2C
Здравствуйте. Подскажите, ребята, кто может.
Что-то никак не получается запустить I2C на STM32F103RC.
Никакой реакции на выводах. Только короткий импульс на SCL.
Где-то ошибка, но увидеть не могу.
Да, ещё BUSY в SR2 всё время в единице.
часть программы:
GPIOB-›CRL&=0x00000000;
GPIOB-›CRL|=0xff000000; //PB6,PB7-альтернативны функция SCL,SDA, открытый сток
RCC-›APB1ENR|=RCC_APB1ENR_I2C1EN;
I2C1-›CR2|=I2C_CR2_FREQ_1; //тактовая частота 2 мГц
I2C1-›CCR|=0x0a; //5000 нс
I2C1-›TRISE=0x03; //1000 нс
//************************************************** ********************************
while(1)
{
T_msec=10;
while(T_msec!=0) //пауза 10 мс
{}
I2C1-›CR1|=I2C_CR1_PE;
I2C1-›SR1=0;
I2C1-›CR1|=I2C_CR1_START; //старт
while((I2C1-›SR1&I2C_SR1_SB)==0) //ожидание установки бита SB
{}
I2C1-›SR1; //очистка бита SB
I2C1-›DR=0xa0; //адрес ведомого 24C04
while((I2C1-›SR1&I2C_SR1_ADDR)==0)
{}
I2C1-›SR1;
I2C1-›SR2; //сброс бита ADDR
I2C1-›DR=0x01; //адрес ячейки памяти
while((I2C1-›SR1&I2C_SR1_BTF)==0)
{}
I2C1-›CR1|=I2C_CR1_START; //повторный старт
while((I2C1-›SR1&I2C_SR1_SB)==0) //ожидание установки бита SB
{}
I2C1-›SR1; //очистка бита SR1
I2C1-›DR=0xa1; //адрес ведомого, 1 в младшем бите-чтение
while((I2C1-›SR1&I2C_SR1_ADDR)==0)
{}
I2C1-›SR1;
I2C1-›SR2;
while((I2C1-›SR1&I2C_SR1_RXNE)==0)
{}
data_eeprom=I2C1-›DR;
}
}
|
|
|
|
06.04.2020, 15:40
|
|
Прописка
Регистрация: 05.12.2008
Адрес: Россия, Омск
Сообщений: 145
Сказал спасибо: 39
Сказали Спасибо 29 раз(а) в 22 сообщении(ях)
|
Re: не могу запустить I2C
Добавьте подтяжки к плюсу питания резисторами на пинах PB6, PB7.
Перед запуском I2C модуля убедитесь, что линии действительно вытянулись к плюсу питания, иначе будет бесконечно висеть BUSY.
Пролистал референс. Внутреняя подтяжка работает только на вход. Open-Drain по какой-то причине не может иметь подтяжки к плюсу.
Последний раз редактировалось -Alan-; 06.04.2020 в 15:43.
|
|
|
|
06.04.2020, 16:09
|
|
Почётный гражданин KAZUS.RU
Регистрация: 12.02.2013
Сообщений: 1,015
Сказал спасибо: 43
Сказали Спасибо 273 раз(а) в 214 сообщении(ях)
|
Re: не могу запустить I2C
Сообщение от fox327
|
Где-то ошибка, но увидеть не могу.
|
while(!(I2C2-›SR1 & I2C_SR1_SB)){}; // waiting setting SB flag
А вот где...
|
|
|
|
06.04.2020, 18:55
|
|
Временная регистрация
Регистрация: 19.08.2010
Сообщений: 94
Сказал спасибо: 8
Сказали Спасибо 35 раз(а) в 25 сообщении(ях)
|
Re: не могу запустить I2C
Подтяжка резисторами есть-10 кОм.
По поводу цикла while-прокомментируйте, пожалуйста,
а то никак не могу увидеть разницу.
Хотя причина скорее всего в этом, так как зависает именно в нём.
|
|
|
|
06.04.2020, 19:43
|
|
Почётный гражданин KAZUS.RU
Регистрация: 12.02.2013
Сообщений: 1,015
Сказал спасибо: 43
Сказали Спасибо 273 раз(а) в 214 сообщении(ях)
|
Re: не могу запустить I2C
Сообщение от fox327
|
По поводу цикла while-прокомментируйте, пожалуйста,
а то никак не могу увидеть разницу.
|
Да разницы с виду нет. Но мой код работает (и в инете это делается именно так), а ваш может так быть соптимизирован, что всегда истина.
Попробуйте расставить break point ы после каждого while и найдите где программа зацикливается - тогда будет совсем понятно.
|
|
|
|
06.04.2020, 20:21
|
|
Прописка
Регистрация: 05.12.2008
Адрес: Россия, Омск
Сообщений: 145
Сказал спасибо: 39
Сказали Спасибо 29 раз(а) в 22 сообщении(ях)
|
Re: не могу запустить I2C
В отладчике видите, что происходит и на какой именно строке останавливается код?
Кстати, можете попробовать увеличить
I2C1-›TRISE = 0x10; // Ожидание восстановления шины к единице.
У меня код чтения байта из регистра чипа (адрес подбрасывается в функцию) работает таким образом:
Код:
|
uint8_t I2C_Read_Byte(uint8_t DevAddr, uint16_t Address, uint8_t *Data) {
I2C1-›CR1 |= I2C_CR1_START;
while (!(I2C1-›SR1 & I2C_SR1_SB));
I2C1-›DR = (DevAddr ‹‹ 1);
while (!(I2C1-›SR1 & (I2C_SR1_ADDR | I2C_SR1_AF)));
if (I2C1-›SR1 & I2C_SR1_AF) {
I2C1-›SR1 = 0;
I2C1-›CR1 |= I2C_CR1_STOP;
while (I2C1-›SR2 & I2C_SR2_BUSY);
return -1;
} else {
(void) I2C1-›SR1;
(void) I2C1-›SR2;
I2C1-›DR = (Address ›› 8) & 0xFF;
while (!(I2C1-›SR1 & (I2C_SR1_TXE)));
I2C1-›DR = (Address & 0xFF);
while (!(I2C1-›SR1 & (I2C_SR1_TXE)));
I2C1-›CR1 |= I2C_CR1_START; // Restart
while (!(I2C1-›SR1 & I2C_SR1_SB));
I2C1-›DR = (DevAddr ‹‹ 1) + 1; // Read
while (!(I2C1-›SR1 & (I2C_SR1_ADDR | I2C_SR1_AF)));
(void) I2C1-›SR1;
(void) I2C1-›SR2;
*Data = I2C1-›DR;
};
I2C1-›CR1 |= I2C_CR1_STOP;
while (I2C1-›SR2 & I2C_SR2_BUSY);
return 0;
}; |
Ну и опять же, во время инициализации:
Код:
|
I2C1-›CR1 |= I2C_CR1_SWRST;
I2C1-›CR1 &= ~I2C_CR1_SWRST; |
|
|
|
|
06.04.2020, 20:57
|
|
Временная регистрация
Регистрация: 19.08.2010
Сообщений: 94
Сказал спасибо: 8
Сказали Спасибо 35 раз(а) в 25 сообщении(ях)
|
Re: не могу запустить I2C
Установку и сброс SWRST пробовал делать-никаких изменений.
Что касается точек останова-отладчика у меня нет. Поэтому я вставлял в тело цикла строчку GPIOC-›ODR^=GPIO_ODR_OD11.
Идут импульсы с высокой частотой, что говорит о том, что из цикла проверки бита SB программа не выходит.
Спасибо за советы, попробую проверить.
|
|
|
|
Ваши права в разделе
|
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения
HTML код Выкл.
|
|
|
Часовой пояс GMT +4, время: 00:09.
|
|