Forum: Mikrocontroller und Digitale Elektronik TWI-slave empfängt jedes zeichen doppelt


von kirschsaft (Gast)


Angehängte Dateien:

Lesenswert?

Hey leute,

ich bin gerade dabei ein TWI Bus aufzubauen, mit einigen atmega8 und 
einem atmega16 als slaves und einem atmega32 als master. Das Empfangen 
von allen slaves funktioniert wunderbar, nur wenn ich von master Daten 
an einen Slave sende, empfängt dieser jedes zeichen doppelt(also anstatt 
"hello world" "hheelloo  wwoorrlldd"). Dadurch das ich den Master über 
UART mit einem PC verbunden hab sehe ich aber, das der Master jedes 
zeichen nur einmal sendet so wie es sein soll. Jetzt ist die Frage warum 
empfangen die Slaves alles doppelt. Es macht auch keine Unterschied ob 
ich Daten vom Master nur an einen einzelnen Slave sende oder per 
"generall call" an alle. Im Anhang befinden sich die entsprechenden 
Dateien. Hab alles mit Komentaren versehen, sie sollten also hoffe ich 
gut zu verstehen sein. Wäre schön wenn ihr mir helfen könntet. Danke 
schon mal im voraus. :)

von kirschsaft (Gast)


Lesenswert?

Hab das Problemchen jetzt selber gefunden. Es lag an der Sende Funktion 
der TWI_Master.c (TWI_M_Transmit). Das es funktioniert muss diese so 
aussehen:

void TWI_M_Transmit(unsigned char byte) {
  TWDR=byte;
  TWCR&=~(1<<TWSTA)|(1<<TWSTO);
  TWCR |= (1<<TWINT);
}

ich bin jetzt erst mal froh das es funktioniert. Hab jetzt aber noch ein 
anderes Problem das ich mit diesem selbst geschriebenen .c Dateien schon 
öfters hatte. Es geht darum wie ich Daten von der TWI_Master.c in meine 
main.c rein bekomme, sodass beide Dateien den String (Read_buffer), den 
ich zum Empfangen verwendet hab lesen können. Im moment is dieser string 
in der TWI_Master.c global deklariert so kann ihn die TWI_Master.c 
verwenden, aber meine main.c nicht. Danke schon mal im Voraus.

von Peter D. (peda)


Lesenswert?

kirschsaft schrieb:
> TWCR |= (1<<TWINT);

Diese Zeile muß weg!
Es wird ja schon in der Zeile davor gelöscht.

Ansonsten kann es passieren, wenn zwischen beiden Zeile ein langer 
anderer Interrupt passiert, daß Du ein I2C-Ereignis wegwirfst.


Peter

von xfr (Gast)


Lesenswert?

kirschsaft schrieb:
> ich bin jetzt erst mal froh das es funktioniert. Hab jetzt aber noch ein
> anderes Problem das ich mit diesem selbst geschriebenen .c Dateien schon
> öfters hatte. Es geht darum wie ich Daten von der TWI_Master.c in meine
> main.c rein bekomme, sodass beide Dateien den String (Read_buffer), den
> ich zum Empfangen verwendet hab lesen können. Im moment is dieser string
> in der TWI_Master.c global deklariert so kann ihn die TWI_Master.c
> verwenden, aber meine main.c nicht. Danke schon mal im Voraus.

Und wie benachrichtigest Du den Benutzer (also main.c), dass die 
Nachricht fertig empfangen wurde? Da sehe ich in Deinem Code nichts von.

Eine saubere Lösung wäre z.B. eine Callbackfunktion, die in main.c 
implementiert ist und von TWI_Master.c aus aufgerufen wird. Der kannst 
Du den Zeiger auf die empfangene Nachricht und deren Länge übergeben:
1
Transmission_R_done(uint8_t* buffer, uint8_t len)
2
{
3
  // mach etwas mit der Nachricht
4
}

Noch besser wäre außerdem, wenn der Puffer in main.c statt TWI_Master.c 
liegt und Du den Zeiger darauf der Transmission_R()-Funktion übergibst, 
zusammen mit einer maximalen Länge, die empfangen werden darf.

von Karl H. (kbuchegg)


Lesenswert?

kirschsaft schrieb:

> ich zum Empfangen verwendet hab lesen können. Im moment is dieser string
> in der TWI_Master.c global deklariert so kann ihn die TWI_Master.c
> verwenden,

Und das ist auch gut so.

> aber meine main.c nicht. Danke schon mal im Voraus.

FAQ: Globale Variablen über mehrere Dateien
Punkt 8: Globale Variablen über mehrere Dateien

von kirschsaft (Gast)


Lesenswert?

Also die Idee von xfr mit der Callback Funktion find ich richtig gut. 
Werd ich gleich einbauen. In meiner UART Bibliothek werde ich das auch 
verwenden. Und auch der Hinweis von Karl Heinz zu dem FAQ ist sehr 
hilfreich. Da stehn einige interessante Dinge drin. Vielen Dank an euch 
zwei. :)

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.