Перейти к содержанию
    

CS43L22 (на плате STM32F4DISCOVERY) выдает NACK на I2C

Я не помню точно, надо ли принудительно при инициализации переводить ноги I2C в режим открытого стока или при выборе I2C в альтернативных функциях ноги это происходит автоматически? Не может быть, что у вас нога работает в двухтактном режиме, выдает единицу и ЦАП просто не в силах перетянуть ее во время ACK?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

I2C инициализирован верно

 

I2Ct::I2Ct()
{
	RCC->AHB1ENR |= RCC_AHB1ENR_GPIOBEN;
	GPIOB->OTYPER |= OTYPERset(SCL_PIN) | OTYPERset(SDA_PIN);// Open drain type
	GPIOB->MODER |= MODERset(SCL_PIN, ModeAf) | MODERset(SDA_PIN, ModeAf);
	AFreg(GPIOB) |= AFset(SCL_PIN, 4) | AFset(SDA_PIN, 4);

	RCC->APB1ENR |= RCC_APB1ENR_I2C1EN;
	I2C1->CR1 = I2C_CR1_SWRST;// software reset
	I2C1->CR1 = 0;

	I2C1->CR2 = 24;// frequency in MHz for some internal requiments and interrupts

	//I2C1->CCR = 240;// i2c 100kHz prescaler for 24Mhz APB

	I2C1->CCR = 0xFFF;// i2c 5.6kHz prescaler for 24Mhz APB

	I2C1->TRISE = 25;// maximum rise time

	I2C1->CR1 = I2C_CR1_PE;// enable i2c
}

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Осциллографом посмотрите сигналы, и усе будет видно. 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

1 minute ago, ViKo said:

Осциллографом посмотрите сигналы, и усе будет видно. 

Парой сообщений выше выложил осциллограмму

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Если есть наличие питания на CS43L22 (может свитч какой на плате отключен) и сигналы I2C приходят на пины чипа CS43L22

то возможно ОНО замерзло (не вышло) из режима PowerDown. (The CS43L22 enters a Power-Down state upon initial power-up.)

ps

-проверьте длительность ~Reset

-проверьте (так как SCL меделенный), что Reset не накладываетя на передачу по I2C (для отладки поставьте _delay(400) между командами )

 

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

! Вы гений!

Отладка появилась у меня очень давно. И давным давно я зачем-то на нижней стороне резанул одну дорожку. Резанул очень аккуратно и не заметно. И забыл. Это оказался Reset =)

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

4 часа назад, RadiatoR сказал:

I2C инициализирован верно

Да ладно! Неуместное заявление, когда у вас не работает что то подключенное туда. Так можно утверждать только если всё работает как ожидалось.

У меня на плате с F429 на I2C-шину подключено 4 слэйва. И все работают нормально и стабильно по много часов. И то я не совсем уверен в правильности его инициализации  :wink2:

 

4 часа назад, RadiatoR сказал:

RCC->AHB1ENR |= RCC_AHB1ENR_GPIOBEN; GPIOB->OTYPER |= OTYPERset(SCL_PIN) | OTYPERset(SDA_PIN);// Open drain type GPIOB->MODER |= MODERset(SCL_PIN, ModeAf) | MODERset(SDA_PIN, ModeAf); AFreg(GPIOB) |= AFset(SCL_PIN, 4) | AFset(SDA_PIN, 4); RCC->APB1ENR |= RCC_APB1ENR_I2C1EN; I2C1->CR1 = I2C_CR1_SWRST;// software reset I2C1->CR1 = 0;

Ну как можно так топорно делать!!? Вы точно открывали даташит??

1. Почему операции "|=" не внутри критических секций? Есть гарантия, что данная процедура не прервётся ISR-м или другой задачей, в которой будет модификация тех же регистров? Да и не только эти операции, а вообще всё, что касается записи в регистры, которые могут использоваться в других местах программы. Типа регистров конфигурирования GPIO, включения тактирования блоков и т.п.?

2. Да и после записи в регистры включения тактирования, очень не помешает команда типа DMB. А у вас - сразу идёт обращение к регистрам. А может они ещё не тактируются в момент этого обращения?

3. Почему инициализация ног делается ДО инициализации периферии, к которой они принадлежат? По уму сперва инитят периферию, а уже ПОСЛЕ, когда периферия уже в устаканившемся состоянии - ноги.

4. А это что такое?:

4 часа назад, RadiatoR сказал:

I2C1->CR1 = I2C_CR1_SWRST;// software reset I2C1->CR1 = 0; 

Вообще непонятно чего вы ожидаете от этого. Открываем RM, читаем:

Bit 15 SWRST: Software reset
When set, the I2C is under reset state. Before resetting this bit, make sure the I2C lines are 
released and the bus is free.
0: I2C Peripheral not under reset
1: I2C Peripheral under reset state
Note: This bit can be used to reinitialize the peripheral after an error or a locked state. As an 
example, if the BUSY bit is set and remains locked due to a glitch on the bus, the 
SWRST bit can be used to exit from this state.

Т.е. - просто так записать "1" и сразу записать "0" - это не сброс. Я даже не уверен, что "1" вообще успеет дойти до периферии до последующего "0". По уму в таких случаях обязательна DMB. А иногда и DMB мало - бывает нужно сделать обратное чтение регистра. Уже не говоря о том, что RM явно рекомендует "перед снятием reset-а убедитесь, что SCL & SDA свободны (т.е. - на них лог."1")".

 

Ещё для проверки работоспособности, я бы рекомендовал:

1) Попробовать сделать отправку адреса I2C программно, ногодрыгом, с соблюдением всех таймингов.

2) Подключить какой-нить заведомо рабочий I2C-slave-чип. Любой. Например I2C-EEPROM. И проверить работу с ним. Может даже на других ногах МК.

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

8 minutes ago, RadiatoR said:

. . .  Это оказался Reset =) 

"Легко отделался":biggrin:  Все могло быть намного хуже.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...