Easyelectronics.ru

Электроника для всех
Текущее время: 23 янв 2021, 01:23

Часовой пояс: UTC + 5 часов



JLCPCB – Прототипы печатных плат за $2/5шт. два слоя. $5/5шт. четыре слоя
Крупнейший производитель печатных плат и прототипов. Более 600000 клиентов и свыше 10000 заказов в день!
Получите скидку на почтовую отправку при первом заказе в JLCPCB!

Начать новую тему Ответить на тему  [ Сообщений: 5 ] 
Автор Сообщение
 Заголовок сообщения: TW_REP_START в Atmega8
СообщениеДобавлено: 21 апр 2020, 00:02 
Здравствуйте!

Зарегистрирован: 20 апр 2020, 23:54
Сообщения: 3
Здравствуйте друзья.

Я пытаюсь связаться с Raspberry с Atmega8 по TWI. Со стороны Raspberry я использую библиотеку smbus, которая для чтения использует последовательный старт:
<start|address+write|reg| start | read data | stop>

И тут я застрял. Может кто то стыкался с такой задачей?
Спасибо за любые идеи

Мой код для работы с TWI
Код:
ISR(TWI_vect) {
    static unsigned char i = 0;
    unsigned char twi_status;
    // Disable Global Interrupt
    cli();
    // Get TWI Status Register, mask the prescaler bits (TWPS1,TWPS0)
    twi_status = TWSR & 0xF8;

    switch ( twi_status )
    {
        case TW_SR_SLA_ACK: // 0x60: SLA+W received, ACK returned

            TWCR |= (1 << TWINT); // Clear TWINT Flag
            break;
        case TW_SR_DATA_ACK: // 0x80: data received, ACK returned
            rx_buff[i] = TWDR; // Save to the register data
            i++;
            if ( i == 6 ) {
            if(crc8((unsigned char *)rx_buff, sizeof(rx_buff) - 1) == rx_buff[5] ){
               i2c_slave_action(WRITE_ACTION); // Call Write I2C Action (rw_status = 1)
            }
                i = 0;
            }

            TWCR |= (1 << TWINT); // Clear TWINT Flag
            break;
        case TW_SR_STOP: // 0xA0: stop or repeated start condition received while selected
         i = 0;
            TWCR |= (1 << TWINT); // Clear TWINT Flag
            break;
        case TW_ST_SLA_ACK: // 0xA8: SLA+R received, ACK returned
        case TW_ST_DATA_ACK: // 0xB8: data transmitted, ACK received
         if (i == 0){
            i2c_slave_action(READ_ACTION); // Call Read I2C Action (rw_status = 0)
         }
            
            TWDR  = tx_buff[i];
            i++;
            if ( i > 4 )
            {
                i = 0;
            }
            TWCR |= (1 << TWINT); // Clear TWINT Flag
            break;
      case TW_REP_START: //repeated start detected
         i = 0;
         TWCR |= (1 << TWINT); // Clear TWINT Flag
         break;
         
        case TW_ST_DATA_NACK: // 0xC0: data transmitted, NACK received
        case TW_ST_LAST_DATA: // 0xC8: last data byte transmitted, ACK received
        case TW_BUS_ERROR: // 0x00: illegal start or stop condition
        default:
            //TWCR |= (1 << TWINT); // Clear TWINT Flag
         TWCR =    0<<TWSTA|
            1<<TWSTO|
            1<<TWINT|
            1<<TWEA|
            1<<TWEN|
            1<<TWIE;
         
         TWAR = MCP23008_ADDR & 0xFE; // Set I2C Address, Ignore I2C General Address 0x00
         TWDR = 0x00; // Default Initial Value
         i = 0;
    }
    // Enable Global Interrupt
    sei();
}


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: TW_REP_START в Atmega8
СообщениеДобавлено: 21 апр 2020, 00:53 
Старожил

Зарегистрирован: 08 авг 2013, 09:43
Сообщения: 3051
Цитата:
<start|address+write|reg| start | read data | stop>

Точно так?
Обычно как-то так:
<start|address+write|reg|rep. start|address+read|read data|stop>


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: TW_REP_START в Atmega8
СообщениеДобавлено: 21 апр 2020, 01:19 
Здравствуйте!

Зарегистрирован: 20 апр 2020, 23:54
Сообщения: 3
Вы правы, адрес после второга старта действительно есть


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: TW_REP_START в Atmega8
СообщениеДобавлено: 22 апр 2020, 12:58 
Здравствуйте!

Зарегистрирован: 20 апр 2020, 23:54
Сообщения: 3
Сколько не искал как решить эту проблему, не нашел нормального решения. На AvrFreaks есть упоминание что atmega8 не умеет обрабатывать такую ситуацию вообще.
Есть костыльное решение, smbus умеет читать один байт без rep. start, так что пока буду читать по одному байту за рас.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: TW_REP_START в Atmega8
СообщениеДобавлено: 22 апр 2020, 15:16 
Старожил

Зарегистрирован: 08 авг 2013, 09:43
Сообщения: 3051
Описанная последовательность - стандарнаое чтение со слэйва в i2c.
Возможно проблема какая на стороне пи с smbus.
Вообще тут нужен лог. анализатор и смотреть что происходит на обмене. Или как минимум отладочных сообщений добавить и смотреть в каком месте затык. По коду вашему с одной стороны только гадать, не имея вашего "сетапа" невозможно.


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 5 ] 


Часовой пояс: UTC + 5 часов


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  

Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
Русская поддержка phpBB