Witam próbuje skomunikować ze sobą dwie atmegi za pomocą twi. Napisałem skrypt oparty o datasheet jednak mam pare watpliwosci.poszukalem po elektrodzie i nie znalazlem tematu ktory by odp na moje ptyania.
Komunikacja wyglada nastepujaco. Jeden z kontrolerow bedzie Master Reciver a drugi slave transmitter. po inicjalizacji polaczenia slave ma przeslac pewna wartosc.
Oto program dla master:
a to kod dla slave:
Moje pytania sa nastepujace:
1.Czy te programy maja w ogole szanse zadzialac??
2.Jezeli jestem MR to czy moge tak po prostu po zczytaniu kodu poprawnego przyjecia adresu zczytać wartość TWDR??czy musze jeszcze zastosowac jakis warunek??
3.jeżeli jestem MR to czy po prawidłowym odczytaniu kodu odebrania bajtu musze wystawic ACK czy master zrobi to automatycznie??
4.Jezeli jestem ST to czy poprawne jest sprawdzanie flagi jako warunku końca wysyłanych bajtów?? chodzi mi o warunek potw konca bajtu??
poniewaz jestem poczatkujacy w tym temacie kazda pomoc bedzie na wage zlota.
Mam jeszcze jedna prosbe poniewaz przy kompilacji wyskakuje mi nastepujacy blad:
wiem,ze napisane jest o problemie z nawiasami,ale wszystkie wydaja sie ok... moze jestem jz zbyt zmeczony czytaniem o TWI zeby to zauwazyc
wprawne oko na pewno szybko to wychwyci.
Bede bardzo wdzięczny za pomoc. Pozdrawiam
Komunikacja wyglada nastepujaco. Jeden z kontrolerow bedzie Master Reciver a drugi slave transmitter. po inicjalizacji polaczenia slave ma przeslac pewna wartosc.
Oto program dla master:
#include "moje.h"
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#include <stdio.h>
#include <stdlib.h>
#include <avr/delay.h>
#define adres_sl 0x51
unsigned char bufor[1];
volatile uint8_t bd; //bajt danych
void error1(void)
{
LCD_xy(10,0);
write_text("blad1");
_delay_ms(5000);
}
void error2(void)
{
LCD_xy(10,0);
write_text("blad2");
_delay_ms(5000);
}
void error3(void)
{
LCD_xy(10,0);
write_text("blad3");
_delay_ms(5000);
}
TWBR=0x01;
TWSR=(~_BV(TWPS1)|~_BV(TWPS0)); //ustawienie bitow prescalera
SIGNAL(TWI)
{
}
sei();
void main(void)
{
while(1)
{
TWCR=(1<<TWINT)|(1<<TWSTA)|(1<<TWEN); // TWCR=_BV(TWINT)|_BV(TWSTA)|_BV(TWEN);start
while(!(TWCR&(1<<TWINT))) //potw startu
{
}
if ((TWSR&0xF8 != 0x08))
{
error1();
} //spr_kodu_start
TWDR=adres_sl;
TWCR=(1<<TWINT)|(1<<TWEN); //adresowanie(); //adres slave 0101 000 1=0x51
while(!(TWCR&(1<<TWINT)))
{
} //potw_adr();
if ((TWSR&0xF8)!=0x40)
{
error2();
} //spr_kodu_adr();
bd=TWDR;
TWCR=(1<<TWINT)|(1<<TWEA)|(1<<TWEN);
//odb_danych();
if ((TWSR&0xF8)!=0x50)
{
error3();
} // spr_kodu_odb();
void stop(void)
{
TWCR=(1<<TWINT)|(1<<TWEN)|(1<<TWSTO);
} //stop();
LCD_xy(10,0);
write_text("ok");
_delay_ms(5000);
}
}a to kod dla slave:
#include "moje.h"
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#include <stdio.h>
#include <stdlib.h>
#include <avr/delay.h>
#define adres_sl 0x51
//unsigned char bufor[1];
//volatile uint8_t bd;
void error1(void)
{
LCD_xy(10,0);
write_text("blad1");
_delay_ms(5000);
}
void error2(void)
{
LCD_xy(10,0);
write_text("blad2");
_delay_ms(5000);
}
void error3(void)
{
LCD_xy(10,0);
write_text("blad3");
_delay_ms(5000);
}
TWBR=0x01;
TWSR=(~_BV(TWPS1)|~_BV(TWPS0)); //ustawienie bitow prescalera
TWAR=0x51; //UST ADRESU
SIGNAL(TWI)
{
}
sei();
void main(void)
{
while(1)
{
TWCR=(1<<TWINT)|(1<<TWEA)|(1<<TWEN)|~(1<<TWSTA)|~(1<<TWSTO); //uruchom OCZEKIWANIE();
while(!(TWCR&(1<<TWINT)))
{
} //potw wywolania
if ((TWSR&0xF8 != 0xA8))
{
error1();
}
//wysl danych
TWDR=0x34;
TWCR=(1<<TWINT)|(1<<TWEN);
while(!(TWCR&(1<<TWINT))) //potw wysl
{
}
if ((TWSR&0xF8)!=0xB8) //spr kodu wysl
{
error2();
}
TWCR=(1<<TWINT)|(1<<TWEN);
while(!(TWCR&(1<<TWINT))) // potw konca bajtu
{
}
if ((TWSR&0xF8)!=0xC8) //spr kodu wysl
{
error3();
}
TWCR=(1<<TWINT)|~(1<<TWEA)|~(1<<TWSTA)|~(1<<TWSTO);
LCD_xy(10,0);
write_text("ok");
_delay_ms(5000);
}
}Moje pytania sa nastepujace:
1.Czy te programy maja w ogole szanse zadzialac??
2.Jezeli jestem MR to czy moge tak po prostu po zczytaniu kodu poprawnego przyjecia adresu zczytać wartość TWDR??czy musze jeszcze zastosowac jakis warunek??
if ((TWSR&0xF8)!=0x40)
{
error2();
} //spr_kodu_adr();
bd=TWDR;
TWCR=(1<<TWINT)|(1<<TWEA)|(1<<TWEN);
//odb_danych();
3.jeżeli jestem MR to czy po prawidłowym odczytaniu kodu odebrania bajtu musze wystawic ACK czy master zrobi to automatycznie??
4.Jezeli jestem ST to czy poprawne jest sprawdzanie flagi jako warunku końca wysyłanych bajtów?? chodzi mi o warunek potw konca bajtu??
poniewaz jestem poczatkujacy w tym temacie kazda pomoc bedzie na wage zlota.
Mam jeszcze jedna prosbe poniewaz przy kompilacji wyskakuje mi nastepujacy blad:
:/winavr-20080610/lib/gcc/../../avr/include/avr/delay.h:36:2: warning: #warning "This file has been moved to <util/delay.h>."
mainST.c:36: error: expected identifier or '(' before 'volatile'
mainST.c:36: error: expected ')' before '(' token
mainST.c:37: error: expected identifier or '(' before 'volatile'
mainST.c:37: error: expected ')' before '(' token
mainST.c:39: error: expected identifier or '(' before 'volatile'
mainST.c:39: error: expected ')' before '(' token
mainST.c:41: warning: 'TWI' appears to be a misspelled signal handler
mainST.c:45: error: expected '(' before 'volatile'
mainST.c:47: warning: return type of 'main' is not 'int'
mainST.c: In function 'main':
mainST.c:57: warning: suggest parentheses around comparison in operand of &
make.exe: *** [mainST.o] Error 1
wiem,ze napisane jest o problemie z nawiasami,ale wszystkie wydaja sie ok... moze jestem jz zbyt zmeczony czytaniem o TWI zeby to zauwazyc
Bede bardzo wdzięczny za pomoc. Pozdrawiam
