|
i2c меджу двумя ATmega8 |
|
|
|
Feb 15 2009, 19:12
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Привет всем. Пишу курсовую, в ней есть схемка, где две ATmega8 соединены по i2c (27,28 ноги). На Master есть 2 кнопки, идут с плюса через сопротивление на порты PD2 (Кнопка SB1), PD3 (Кнопка SB2) и один светодиод (VD4), также с плюса через сопротивление на PD4. У "раба" почти тоже самое, только вместо кнопок светодиоды(VD1 и VD2). Сетодиод на PD4 на обоих процах для сигнализирования ошибки. Требуется при нажатии на клавишу SB1 найти "раба" по коду (AF) и отослать ему комбинацию DD AF 1C, тот в свою очередь примет и зажжёт светодиод VD1. Кнопка SB2 по комбинации DD AF 1D зажжёт VD2. Если кто-то может и нетрудно, напишите код для Master и Slave (WinAVR). Искал разные примеры, много чего перепробовал и сторонние библиотеки, и стандартный (util/twi.h), непомогло, никак немогу понять когда реагировать на приёмы, и как чего отсылать. Если нужна схемка, то выложу почти в любых форматах (кроме Автокадского  за неимением онного) От модератора. Если Вы предлагаете работу, то я перенесу это сообщение в соответствующий раздел. Если же просите помощи, то давайте к обсуждению более полную информацию (схему, исходники и где чего у Вас не получается).
|
|
|
|
|
Feb 16 2009, 05:24
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Цитата(smalcom @ Feb 16 2009, 05:48)  баксов за пятьдесят наверное Лучшеб ты не отвечал. Цитата От модератора. Если Вы предлагаете работу, то я перенесу это сообщение в соответствующий раздел. Если же просите помощи, то давайте к обсуждению более полную информацию (схему, исходники и где чего у Вас не получается). Какая работа? Что больше людей не осталось которые просто могут по Человечески помочь? Если кто нибудь может, помогите, в аттаче схема.
Эскизы прикрепленных изображений
|
|
|
|
|
Feb 16 2009, 07:29
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Цитата(rushack @ Feb 16 2009, 07:24)  Какая работа? Что больше людей не осталось которые просто могут по Человечески помочь? Помочь - это когда Вы что-то делаете сами, если что-то не выходит - задаёте осмысленные вопросы и Вам на них отвечают. А если надо всё сделать за Вас - то это не помочь, а подрядиться под работу, которая должна быть оплачена. Какая разница, по сути - курсовий нерадивому студенту нужен или простой пульт заказчику, который толком сам не может объяснить что ему надо? Почему в первом случае нужно работать бесплатно? Почему желание кого-то нагрузить вместо себя маскируется под просьбу "по человечески помочь"? Тем более, что разница есть... И назывется она Цитата Что больше людей не осталось которые просто могут по Человечески учиться?
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
|
Feb 16 2009, 09:19
|
Частый гость
 
Группа: Validating
Сообщений: 94
Регистрация: 18-01-09
Из: Красноармейск
Пользователь №: 43 560

|
Цитата(rushack @ Feb 15 2009, 22:12)  Искал разные примеры, много чего перепробовал и сторонние библиотеки, и стандартный (util/twi.h), непомогло, никак немогу понять когда реагировать на приёмы, и как чего отсылать. Давай сюда примеры, как именно и чего пробовал. Там не все так сложно, как кажется. Поможем, если будет над чем размышлять.
|
|
|
|
|
Feb 16 2009, 11:30
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Цитата(ReAl @ Feb 16 2009, 10:29)  Помочь - это когда Вы что-то делаете сами, если что-то не выходит - задаёте осмысленные вопросы и Вам на них отвечают. А если надо всё сделать за Вас - то это не помочь, а подрядиться под работу, которая должна быть оплачена. Какая разница, по сути - курсовий нерадивому студенту нужен или простой пульт заказчику, который толком сам не может объяснить что ему надо? Почему в первом случае нужно работать бесплатно? Почему желание кого-то нагрузить вместо себя маскируется под просьбу "по человечески помочь"? Тем более, что разница есть... И назывется она Цитата Что больше людей не осталось которые просто могут по Человечески учиться? Не нужно оскорблять, про нерадивых студентов, это второе высшее будет. Ни на ком выезжать не собираюсь, а прошу помочь. Хватит уже, про это твердить. У меня устройство значительно больше, в нём несколько рабов + мастер общается с ПК по rs232 (типа консоли) Пока не могу исходник приложить он дома, я на работе.
|
|
|
|
|
Feb 16 2009, 14:12
|

Познающий...
     
Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125

|
Цитата(rushack @ Feb 16 2009, 19:30)  Не нужно оскорблять, про нерадивых студентов Вас никто не оскорбляет. Не знаю, как на других форумах, но на этом принято именно помогать, а не делать работу бесплатно. Вы думаете, что написать программы, которые Вы просите легко? Ведь это нужно потратить время, отладить их. Кому это надо, когда у всех есть основная работа (тут в основном взрослые дяди и тети общаются у которых нет много времени). Под помощью предполагается, что Вы пишите все программы самостоятельно и когда что-то не получается, задаете вопрос. Например написали код, а он ни в какую не компилится. Вы мучаетесь, а толку нет. Вот тогда задаете вопрос. С приложенным логом и кодом. Вот это помощь. А то, чего Вы хотите это не "по человечески помочь", это уже предложение работы. Тем более, что это Цитата(rushack @ Feb 16 2009, 19:30)  второе высшее будет. Цитата(rushack @ Feb 16 2009, 19:30)  Пока не могу исходник приложить он дома, я на работе. Вот это уже другой разговор будет. Просьба без обид  Я и сам попадал в просак Просто спокойно займитесь проблемой и у Вас все получится! Успехов!
--------------------
Выбор.
|
|
|
|
|
Feb 16 2009, 18:31
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Цитата(SysRq @ Feb 16 2009, 20:30)  Схемка-то в части TWI неправильная, SDA и SCL к высокому уровню не подтянуты как полагается... Я протериусе эмулирую, с подтяжкой дело даже до посылки бита адреса недоходит. Без неё " S, адрес , A , код, A , P" проходит нормально, slave отвечает.
|
|
|
|
|
Feb 16 2009, 19:34
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Исходник раба (частично/только i2c) Непомню откуда качал пример, часть была сделана так. Тут я просто пытаюсь поймать символ "a"/0x61 , и инвертировать состояние порта PB0 CODE #include <avr/io.h> #include <util/twi.h> #include <avr/interrupt.h>
#define TWI_RX_BUFFER_SIZE 8
// receive buffer (incoming data) static uint8_t i2crxbuffer[TWI_RX_BUFFER_SIZE]; static uint8_t i2crxindex; uint8_t i2c_rxbuffer[TWI_RX_BUFFER_SIZE]; static void (*i2cSlaveReceive)(uint8_t receiveDataLength, uint8_t* recieveData); void twi_init(uint8_t adress); // I2C (TWI) interrupt service routine SIGNAL(SIG_2WIRE_SERIAL) {
switch (TWSR & 0xF8) { case TW_SR_SLA_ACK: // 0x60: own SLA+W has been received, ACK has been returned case TW_SR_ARB_LOST_SLA_ACK: // 0x68: own SLA+W has been received, ACK has been returned case TW_SR_GCALL_ACK: // 0x70: GCA+W has been received, ACK has been returned case TW_SR_ARB_LOST_GCALL_ACK: // 0x78: GCA+W has been received, ACK has been returned i2crxindex = 0; TWCR |= (1 << TWINT) | (1 << TWEA); break; case TW_SR_DATA_ACK: // 0x80: data byte has been received, ACK has been returned case TW_SR_GCALL_DATA_ACK: // 0x90: data byte has been received, ACK has been returned i2crxbuffer[i2crxindex++] = TWDR; if(i2crxindex < TWI_RX_BUFFER_SIZE) TWCR |= (1 << TWINT) | (1 << TWEA); // receive data byte and return ACK else TWCR |= (1 << TWINT); // receive data byte and return NACK break; case TW_SR_DATA_NACK: // 0x88: data byte has been received, NACK has been returned case TW_SR_GCALL_DATA_NACK: // 0x98: data byte has been received, NACK has been returned TWCR |= (1 << TWINT); break; case TW_SR_STOP: // 0xA0: STOP or REPSTART has been received while addressed as slave TWCR |= (1 << TWINT) | (1 << TWEA); // switch to SR mode with SLA ACK if (i2cSlaveReceive) i2cSlaveReceive(i2crxindex, i2crxbuffer); // i2c receive is complete, call i2cSlaveReceive break; case TW_BUS_ERROR: // 0x00: Bus error due to illegal start or stop condition TWCR |= (1 << TWINT) | (1 << TWSTO) | (1 << TWEA); // reset internal hardware and release bus break; } }
void twi_slave_setrxhandler(void (*i2cSlaveRx_func)(uint8_t receiveDataLength, uint8_t* recieveData)) { i2cSlaveReceive = i2cSlaveRx_func; }
void twi_init(uint8_t adress) { i2cSlaveReceive = 0; TWAR = adress; TWCR = (1 << TWIE) | (1 << TWEA) | (1 << TWEN); sei(); }
void i2c_rxservice(uint8_t length, uint8_t* data) { uint8_t counter; for (counter = 0; counter <= length; counter++) i2c_rxbuffer[counter] = *data++;
switch (i2c_rxbuffer[0]) { case 'a': PORTB ^=0x01; break; default: break; } }
int main( void ) { DDRB =0x01; twi_init(0xAA); while(1) { twi_slave_setrxhandler(i2c_rxservice); } } В протериусе через дебагер и2ц посылаю S- стартует, адрес - отвечает ACK, 0x61 - отвечает АСК, P - связь как и должно быть разрывается, но во время посылки 0x61 ничего не происходит. Слышал что в протериусе отладчик кода есть сейчас попробую, может через него ошибки найду?
Причина редактирования: Уменьшение видимого размера цитаты исходника.
|
|
|
|
|
Feb 17 2009, 12:45
|

Группа: Участник
Сообщений: 13
Регистрация: 14-02-09
Из: Нижний Новгород
Пользователь №: 44 857

|
Цитата(haker_fox @ Feb 17 2009, 15:28)  И как после этого симуляторам верить? В реальной жизни без подтяжек работать не будет (см. спецификацию шины I2C). Версия старая была, поставил апдейт, без подтяжки перестал работать
|
|
|
|
|
Feb 17 2009, 16:15
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Цитата(rushack @ Feb 16 2009, 21:34)  Код case TW_SR_DATA_ACK: case TW_SR_GCALL_DATA_ACK: i2crxbuffer[i2crxindex++] = TWDR; if(i2crxindex < TWI_RX_BUFFER_SIZE) TWCR |= (1 << TWINT) | (1 << TWEA); else TWCR |= (1 << TWINT); break; Пробежался по диагонали не вникая толком в суть (я пока слейва не писал и по этой части докумнтацию не читал). Вот что мне в этом коде не нравится, так это то, что вся работа с TWCR идёт через |=Оставил небольшой фрагмент. В предыдущем прерывании ( TW_SR_SLA_ACK) бит TWEA был установлен (собственно, он и раньше был установлен, иначе прерывание не прошло бы). А в данном перывании этот бит никогда не будет сброшен, так как TWCR |= (1 << TWINT); не изменит его. Лучше бы каждый раз записывать в регистр константу (и кода меньше, и надёжнее). Можно для уменьшения писанины что-то в духе Код #define TWCR_DEFAULT ((1<<TWINT) | (1<<TWEN) | (1 << TWIE) | (1<<TWEA)) // таки TWEA чаще в 1-ке нужен
... if(i2crxindex < TWI_RX_BUFFER_SIZE) TWCR = TWCR_DEFAULT; else TWCR = TWCR_DEFAULT & ~(1 << TWEA); break; ... case TW_BUS_ERROR: TWCR = TWCR_DEFAULT | (1 << TWSTO); break; И ещё сразу маленькая подсказка по GCC. Лучше так: Код uint8_t twi_sr = TWSR & TW_STATUS_MASK;
switch (twi_sr) { При этом лишний регистр занят не будет, компилятор видит, что дальше переменная не используется и регистр идёт под другие нужды. Но в случае switch(TWSR & TW_STATUS_MASK) результат переключающего выражения по стандарту имеет тип int, дальше идут константы тоже типа int и тут оптимизатор, к сожалению, не замечет, то старший байт выражения гарантированно нулевой, как и старшие байты констант. По крайней мере когда я заглядывал в скомпиированный код - было так. Идёт 16-битное сравнение вместо 8-битного, что раздувает код и замедляет работу. А подсказка в виде переключения по 8-битной переменной ему помогает.
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|