Forum: Compiler & IDEs SPI - MISO


von Thomas (Gast)


Lesenswert?

Hallo,

ich habe gestern schonmal ein Posting
(http://www.mikrocontroller.net/forum/read-2-359493.html) gemacht. Da
ich jetzt noch einen kleinen Fehler habe, mache ich nochmal einen neuen
Thread auf.

Bisher klappt die Datenübertragung nur vom Master (ATMEGA128) zum
Sklave (ATMEGA32), indem der Master in der Überlauf-ISR eines Timers
folgendes macht:
- /SS auf Low
- SPDR laden und warten auf fertig (Flag-Auswertung)
- /SS auf high
(Portrichtung PORTB: /SS, SCK und MOSI output "DDRB = 0x07")

Auf der Sklave-Seite wird via ISR (SPI Data complete) der empfangene
Datenframe an PORTC via "PORTC = SPDR" angezeigt.
(Portrichtung PORTB: alle input)

Soweit klappt alles einwandfrei. Wie kann ich jetzt gleichzeitig einen
Datenframe vom Sklave zum Master übertragen?

Ich habe die Portrichtung des Sklave auf DDRB = 0x40 (MISO -> Output)
gesetzt. Beim Lesen des Datenblattes habe ich ein paar Probleme. Hier
wird beschrieben, dass der Transmitvorgang einfach gepuffert und der
Receive doppelt gepuffert ist. Wie beschreibe ich jetzt in der
richtigen Reihenfolge das SPI-Datenregister SPDR?

Ich wollte es so machen:

- Sklave:
//SPI transfer complete
ISR(SPI_STC_vect)
{
  uint8_t tmp_sreg = SREG; //backup SREG with actual sei()
  cli(); //disable global interrupt

  SPDR = 0x04; //MISO-Dode
  PORTC = SPDR; //MOSI-Data
  SREG = tmp_sreg; //restore SREG
}

-Master:
Auswertung via ISR des eingehenden Datenframes.

Dabei kommt aber nur Mist. Hat jemand eine Idee?

Viele Grüße
Thomas

von Lutz Müller (Gast)


Lesenswert?

Hallo Thomas,
wenn man es nicht besser weiß, soll man lieber den Mund halten. Aber
ich glaube zumindest in der avr-libc vor ca. 2 Jahren mal gelesen zu
haben, daß die ganzen Register (nicht nur SREG) bei Aufruf einer ISR
gepusht und am Ende auch wieder gepoppt werden. Auch das cli() sollte
überflüssig sein, da es auch automatisch gemacht wird, da es wohl fast
ausschließlich so sein sollte (außer man will nested interrupts
machen).

Zur Deiner eigentlichen Frage kann ich leider nix sagen, sorry.

Gruß
Lutz

von johnny.m (Gast)


Lesenswert?

Lutz' Vermutung ist korrekt: Das Sichern der Register und des SREG
geschieht automatisch durch den Compiler, das Löschen des I-Bit im SREG
beim Einsprung in die ISR und das erneute Setzen beim Verlassen macht
die µC-Hardware!

von Thomas (Gast)


Lesenswert?

Vielen Dank für den Hinweis. Ich muss ehrlich sagen, dass ich vor ca. 2
Jahren das GCC-Tutorial durchgearbeitet hatte und da wurde die
Sicherung noch so beschrieben. Irgendwie habe ich das einfach
beibehalten. Wenn es jetzt nicht mehr erforderlich ist, kann ich mir
ein paar Zeilen Code sparen ;-).

Ich werde morgen nochmal systematisch das Datenblatt durchgehen, in
welcher Reihenfolgen des Lesen und Neubeschreiben des
SPI-Datenregisters gemacht werden muss.

Viele Grüße
Thomas

von Christian F. (fasti)


Lesenswert?

Hi!

Also soweit ich weiß musst du die Daten die der Slave übertragen soll
einfach ins SPDR Register schreiben. Sobald der Master eine Übertragung
initialisiert (SS auf low) werden die Bits vom Master in den Slave und
gleichzeitig (weil Ringbuffer) vom Slave in den Master geshiftet. nach
der Übertragung brauchst du nur noch das SPDR Register des Master
auslesen und schon hast du die Daten vom Slave.

mfg

Fasti

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.