Sida 1 av 2
C-kod behöver er hjälp.... (WinAVR)
Postat: 20 juli 2005, 22:28:42
av björn
Skall initiera usarten på en atmega16, men får inte exempelkoden från atmel att funka, säkert något litet fel bara...
Min kod ser ut så här :
#include <avr/io.h>
#define FOSC 1000000 //clock
#define BAUD 4800 //baudrate
#define MYUBRR FOSC/16/BAUD-1
int main (void){
USART_init ( MYUBRR );
for (;;){
/*här kommer kod senare */
}
}
void USART_init (unsigned int ubrr){
/*set budrate*/
UBRRH = (unsigned char)(ubrr>>8);
UBRRL = (unsigned char)ubrr;
/*Enable receiver and transmitter*/
UCSRB = ((1<<RXEN) | (1<<TXEN));
/*set frameformat : 8 databits 2 stop bits*/
UCSRC = (1<<USBS | 3<<UCSZ0);
}
När jag kompilerar så får jag att USART_init ät fel deklarerad, men jag tycker det ser rätt ut, någon som ser felet??
Postat: 20 juli 2005, 23:05:18
av frejo
rent spontant skulle jag vilja ha det så här:
Kod: Markera allt
#include <avr/io.h>
#define FOSC 1000000 //clock
#define BAUD 4800 //baudrate
#define MYUBRR FOSC/16/BAUD-1
void USART_init (unsigned int)
int main (void){
for (;;){
/*här kommer kod senare */
}
}
void USART_init (unsigned int ubrr){
/*set budrate*/
UBRRH = (unsigned char)(ubrr>>8);
UBRRL = (unsigned char)ubrr;
/*Enable receiver and transmitter*/
UCSRB = ((1<<RXEN) | (1<<TXEN));
/*set frameformat : 8 databits 2 stop bits*/
UCSRC = (1<<USBS | 3<<UCSZ0);
}
kolla om det funkar bättre....
är det något annat som strular kan du säkert hitta något matnyttigt här under uart.c, eller bara låna hela libben
http://hubbard.engr.scu.edu/embedded/av ... ource.html
http://hubbard.engr.scu.edu/embedded/av ... index.html
Postat: 20 juli 2005, 23:17:12
av björn
UNDERBART, ibland e man blind....Givetvis skulle funktionen deklareras utanför main.
Tack för hjälpen nu kunde jag kompilera

.
Postat: 21 juli 2005, 00:27:08
av speakman
Fast "snyggast" (enligt mig då iof) är att ha main sist, och anropade funktioner ovanför anropande funktion. Då blir koden betydligt mer lättsökt, och blir det ingen onödig dubbelskrivning (ja e anti sånt vettu)!

Dessutom skulle inte detta fel ha uppstått...

Bara ett tips...
Mvh
speakman
Postat: 21 juli 2005, 10:41:04
av frejo
Nu har jag ingen bra referens men för mig känns det som att deklarera alla funktioner innan main är en del av c-standarden.
Dessutom tycker jag att koden blir mycket mer överskådlig och lättare att felsöka om man lätt ser alla ingående funktioner med argument och returtyper.
Postat: 21 juli 2005, 12:15:50
av björn
OK, tack för tipsen. Men nu har jag ett nytt problem.... jag vill att min avr skall eka tillbaka det jag skickar till den från realterm, men det funkar inte.
Jag har testat fram till avren och det funkar ända fram dit, men min kod verkar inte funka :( .
Ser ni något fel?
#include <avr/io.h>
#define FOSC 1000000 //clock
#define BAUD 4800 //baudrate
#define MYUBRR FOSC/16/BAUD-1
void USART_init (unsigned int);
unsigned char ReceiveByte( void );
void TransmitByte( unsigned char data );
int main (void){
USART_init (MYUBRR);
for (;;){
TransmitByte( ReceiveByte() ); /* Echo the received character */
}
}
void USART_init (unsigned int ubrr){
/*set budrate*/
UBRRH = (unsigned char)(ubrr>>8);
UBRRL = (unsigned char)ubrr;
/*Enable receiver and transmitter*/
UCSRB = ((1<<RXEN) | (1<<TXEN));
/*set frameformat : 8 databits 2 stop bits*/
UCSRC = (1<<USBS | 3<<UCSZ0);
}
/* Read and write functions */
unsigned char ReceiveByte( void )
{
while ( !(UCSRA & (1<<RXC)) ) /* Wait for incomming data */
; /* Return the data */
return UDR;
}
void TransmitByte( unsigned char data )
{
while ( !(UCSRA & (1<<UDRE)) )
; /* Wait for empty transmit buffer */
UDR = data; /* Start transmittion */
}
EDIT: la in rätt kod
Postat: 21 juli 2005, 12:17:23
av speakman
Smaken är ju som baken, som tur är.

Men jag tror anledningen till att deklarationer uppkommit är för att förenkla för kompilatorn, inte underlätta för programmeraren. Men som sagt, jag har heller ingen referens.
Sedan beror det nog en hel del på vilket IDE/vilken editor man använder. Jag kör mest emacs, och använder man då etags-funktionerna så underlättar det väldigt när den först anropade funktionen är längst ner. Då får man också en form av hierarki på koden.

Ibland kommer man dock inte undan att bara "anropa uppåt", men då slänger jag in en deklaration raden ovanför funktionen som anropar.
Nästan alla stora OpenSource-projekt jag fördjupat mig i använder även den här kodstilen (Linux, Asterisk, ...). Men övervägande utvecklare kör ju emacs, så därav säkert anledningen.
Mvh
speakman
Postat: 21 juli 2005, 14:07:35
av björn
Jag blir tokig, vad kan vara fel? se mitt inlägg ovan, jag tycker allt stämmer men ändå funkar det inta att eka tillbaka.
Postat: 21 juli 2005, 14:37:40
av frejo
Inte alls insatt i uart-registrena, men det ser inte direkt fel ut.
Har du jämnfört med den färdiga uart-koden jag länkade till ovan?
Postat: 21 juli 2005, 14:49:01
av speakman
Finns det ingen simulator till AVR? Då kan man stega och se vad som händer. PC'ns serieport brukar vara UARTEN.
Mvh
speakman
Postat: 21 juli 2005, 14:49:56
av björn
jag har kollat lite på den men den är uppbyggd med så mycket mer än det jag behöver, vill helst lära mig det från grunden.
Jag har nu testat att skicka tecken från avr till dator, kretsen skickar något men det enda som visas är nollor.
Vet inte om det är RealTerm som jag inte förstår eller om det är i koden
Jag har ställt in realterm på 8 bitar och 2 stoppbitar, precis som avren och baudrate på 4800, vad kan mer vara fel?
Postat: 21 juli 2005, 15:15:59
av frejo
Jag har använt mig av detta terminalprogram när jag kört med avr:
www.filofaxen.se/term20041226.rar
Går ju att visa binärt också, kanske enklare att se om det överförs korrekt då?
Hur har du kopplat förresten?
Postat: 21 juli 2005, 16:39:17
av björn
Jag har kopplat:
AVR->MAX203
RXD(pin14)->R1OUT(PIN 3)
TXD(PIN15)->T1IN(PIN2)
Sen har jag kopplat från serie porten till max 203 pin4 och pin5.
EDiT:tillägg:Jag får bara nollor i det andra terminalprogrammet med, tex om jag skall skicka 0xff blir det nollor bara.
Postat: 21 juli 2005, 16:42:56
av Icecap
För att testa att allting förutom AVR'n fungerar lyftar du såklart pinnerna från MAX232'an till AVR'n och lägger ihop dom på MAX'en. Därmed får du en hel kedja där RS232 signalen skiftas ner till 5V nivå och sedan skiftas upp igen och retuneras, då ska du få ditt eko. Om du inte får det har du ett fel med MAX'en.
Postat: 21 juli 2005, 16:54:44
av björn
Japp, det har jag gjort och det funkar. så felet är i min kod antar jag.... Vet inte vad jag missat bara...