Forum: Mikrocontroller und Digitale Elektronik AVR GCC, Atmega32u2 und SPI über USART Problem


von Mike (Gast)


Lesenswert?

Hallo,

ich habe hier gerade einen Atmega32u2 vor mir liegen. Ich benötige sein 
SPI-Protokoll über den USART, um eine SPI-Kette ansteuern zu können.

Ich arbeite dabei mit gcc avr und einer Makefile unter Codelite unter 
Linux.

Die Konfiguration der SPI-Protokolls klappt jedoch nicht, da der 
Compiler die Registernamen (z.B. UBRRn, XCKn_DDR, UCSRnC etc.) nicht 
auflösen kann. Alle Standards wie PORTx, DDRx, Timer und andere kann er 
auflösen.

Ist das ein bekanntes Problem oder mache ich etwas falsch? Angeblich 
soll der Atmega32u2 von avr-libc unterstützt werden.

Ich wäre sehr dankbar für einen kleinen Hinweis

Mit Gruß

Mike

von OldMan (Gast)


Lesenswert?

Mike schrieb:
> da der
> Compiler die Registernamen (z.B. UBRRn, XCKn_DDR, UCSRnC etc.) nicht
> auflösen kann.

Richtiger Include-File für den Prozessor?
Auch im Makefile den richtigen Prozessor gesetzt?
Ohne Deinen Code und Makefile ist das alles nur Glaskugel.

von Mike (Gast)


Lesenswert?

Hallo,

vielen Dank für deine Antwort.

Den gesamten Code anzuhängen dürfte schwierig werden. Der Fehler lässt 
sich aber sehr gut einschränken und vielleicht ist das ja ein bekannter 
Bug oder eine bekannte Problematik.

Die USART-Init wurde 1:1 von Atmel übernommen. Da steht grob (wegen 
Urheberrechts...)

void Init( void )
{
UBRRn = 0;
XCKn_DDR |= (1<<XCKn);
UCSRnC = (1<<UMSELn1)|(1<<UMSELn0);
UCSRnB = (1<<RXENn)|(1<<TXENn);
UBRRn = foo;
}

keine Registerbezeichnung wird beim build aufgelöst.

In der Makefile steht
MCU = atmega32u2

diese ist laut avr-libc auch so definiert.

Was genau meinst du mit: Include-File für den Prozessor? Ich habe die 
io.h, interrupt.h und stdlib.h included. Gibt es da noch was 
prozessorspezifisches?


Der Rest funktioniert. Nur die Register für die USART-Konfiguration für 
SPI will nicht erkannt werden. Und ich möchte nicht wegen nur eines 
Chips wieder zu Win zurück :(




Gruß

Mike

von spess53 (Gast)


Lesenswert?

HI

>UBRRn = 0;
     ^

Steht in deinem Programm wirklich UBRRn?

MfG Spess

von Bastler (Gast)


Lesenswert?

Das kleine n steht im Atmel-Code als Platzhalter für die UART Nummer. 
Also 0 falls der Chip mindestens eine UART hat, 1 falls es noch eine 
zweite gibt.

von spess53 (Gast)


Lesenswert?

Hi

>Das kleine n steht im Atmel-Code als Platzhalter für die UART Nummer.
>Also 0 falls der Chip mindestens eine UART hat, 1 falls es noch eine
>zweite gibt.

Es gibt aber auch AVRs bei denen gibt es nur eine USART und die heißt 
auch so. Und die Register nennen sich dann auch nur UBRR, UDR, UCSRA, 
UCSRB ... .
Dazu gehört auch der Atmega32u2.

MfG Spess

von Dieter F. (Gast)


Lesenswert?

spess53 schrieb:
> Es gibt aber auch AVRs bei denen gibt es nur eine USART und die heißt
> auch so

Die heissen dann nicht ...1.., obwohl lt. Pinout so bezeichnet?

Hatte ich noch nicht, deshalb frage ich ...

von Dieter F. (Gast)


Lesenswert?

Habe jetzt auch mal ins Datenblatt geschaut - die Register sind auch mit 
...n.. bezeichnet. Daher würde ich doch von UDR1, UCSR1A, etc. ausgehen.

von spess53 (Gast)


Lesenswert?

Hi

>Die heissen dann nicht ...1.., obwohl lt. Pinout so bezeichnet?
>Hatte ich noch nicht, deshalb frage ich ...

Das trifft auf ältere AVRs (z.B. ATMega8/16/32) zu. Und im Pinout taucht 
auch keine USART-Nummer auf.

Beim  Atmega32u2 muss ich mich allerdings korregieren. Dort heißt die 
USART wirklich USART1 und die Register UDR1, UCSR1A, UCSR1B, UCSR1C, 
UCSR1D, UBRR1H und UBRR1L.

MfG Spess

von Mike (Gast)


Lesenswert?

Hallo,

das mit den "n" war mir bekannt. Nur leider die exakte Nummerierung 
nicht.

Mittlerweile frisst der Compiler nun einen Teil des Codes. Exakt:

UBRR1 = 0;
DDRD |= (1 << PD5);
UCSR1C |= (1 << UMSEL11) | (1 << UMSEL10);
UCSR1B |= (1 << RXEN1) | (1 << TXEN1);

UBRR1 = foo;

Und so ganz vollständig scheint das alles auch nicht zu sein. So 
existiert das angegebene Register XCKn_DDR wohl gar nicht. Der Versuch, 
den Pin als Ausgang zu deklarieren "DDRD |= (1 << PD5)" bringt leider 
keinen Effekt. Der µC schreibt nun zwar auf dem USART einzelne Bytes 
aus, erzeugt dazu aber kein XCK-Signal. Der Pegel bleibt kostant auf 
high.

Einen Schluss gegen GND oder Versorgung habe ich ausgeschlossen.

Hat einer einen Hinweis?

Mit Gruß

Mike

von c-hater (Gast)


Lesenswert?

Mike schrieb:

> Mittlerweile frisst der Compiler nun einen Teil des Codes. Exakt:
>
> UBRR1 = 0;
> DDRD |= (1 << PD5);
> UCSR1C |= (1 << UMSEL11) | (1 << UMSEL10);
> UCSR1B |= (1 << RXEN1) | (1 << TXEN1);
>
> UBRR1 = foo;
>
> Und so ganz vollständig scheint das alles auch nicht zu sein.

Doch, das ist es. Nur leider nicht korrekt. In Zeile 2 und 3 mußt du den 
Zuweisungsoperator "=" verwenden und nicht "|=".

von Bastler (Gast)


Lesenswert?

Ok, ich hatte mir gespart das DB des Atmega32u2 anzuschauen.
 Ich benutze im Normalfall Eclipse mit AVR-Plugin, da schreibe ich 
einfach UBBR und bekomme angezeigt welche es wirklich gibt. (muß ich 
noch SHIFT SPACE drücken? Erlich, ich weiß es nicht, das machen meine 
Fingenr vermutlich schon automatisch. Und hier auf dem Apfelbrett kann 
ich's nicht ausprobieren)
 Und wenn man Code hat, der auf verschiedenen AVR's laufen muß, dann kan 
man per #if(def) abprüfen welches es aktuell ist. Oder man definiert es 
gleich auf den gewünschten Namen um.

von Dieter F. (Gast)


Lesenswert?

Mike schrieb:
> UBRR1 = foo;

Was steht denn in "foo" ?

Mike schrieb:
> So existiert das angegebene Register XCKn_DDR wohl gar nicht.

Die Transferleitung, das "n" durch eine "1" zu ersetzen hast Du 
geleistet?
Ich vermute mal, wenn Du das gemacht hast wird es auch erkannt.

Der Pin muss als Ausgang geschaltet sein, das sonst auf einen externen 
Takt vom "slave" gewartet wird (so zumindest deute ich das Datenblatt - 
dessen Lektüre nicht dümmer macht ...)

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Mike schrieb:
> Ist das ein bekanntes Problem
Es ist ein bekanntes Problem, dass man aus dem Datenblatt nicht nur 
irgendwas herauskopieren, sondern die Zeilen davor und danach noch 
lesen und verstehen sollte...

> oder mache ich etwas falsch?
Du verwendest Code ohne ihn zu verstehen.

Mike schrieb:
> Und ich möchte nicht wegen nur eines Chips wieder zu Win zurück :(
Diesen Satz möchte ich mir nochmal auf der Zunge zergehen lassen.

Du solltest versuchen, die Toolchain zu verstehen. Es sind nur ein 
paar Textdateien, die das Verhalten des Controllers und das darauf 
laufende Programm beschreiben. Die kann man öffenen und zur Not darin 
editieren. Wenn dieser eine Chip tatsächlich nicht unerstützt werden 
würde, dann könnte man sich dort die fehlenden paar Register einfach 
definieren. Denn das sind nur Buchstabenhaufen, keine 
Naturkonstanten...

Mike schrieb:
> So existiert das angegebene Register XCKn_DDR wohl gar nicht.
Auch das ist nur ein Buchstabenhaufen, der von dieser "n" Thematik 
zusätzlich betroffen ist. Wenn du da mal eine 1 einsetzt und dann Google 
bemühst (https://www.google.de/search?q=XCK1_DDR), dann findest du raus, 
dass damit nur ein define für ein Richtungsregister gemeint ist, also 
z.B. #define XCK1_DDR DDRD

: Bearbeitet durch Moderator
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.