Forum: Mikrocontroller und Digitale Elektronik ATmega: SPI, while-Schleife und Rechenzeit


von Andreas H. (heilinger)


Lesenswert?

Hallo,

ich benutze einen ATmega 644P und habe eine Frage zum Senden von Daten 
per SPI-Schnittstelle:

Und zwar sieht mein Code momentan so aus, dass ich ein Byte sende:

SPDR = cData;

und dann abwarte, bis das Byte übertragen wurde:

while(!(SPSR & (1<<SPIF)))
  ;

So ist es auch im Datenblatt als Beispiel geschrieben.

Jetzt hänge ich aber natürlich in der while-Schleife solange fest, bis 
das Byte übertragen wurde, ohne dass ich was anderes machen kann. Wäre 
es denn nicht sinnvoller die beiden Zeilen einfach umzudrehen:

while(!(SPSR & (1<<SPIF)))
  ;

SPDR = cData;

So kann ich direkt nach dem Senden weitere Rechnungen durchführen und 
falls es doch passieren sollte, dass ich ein weiteres Byte verschicken 
will, obwohl die aktuelle Sendung noch läuft, dann würde ich vor dem 
nächsten Senden in der while-Schleife hängen?

Also ist es für die Rechenzeit nicht besser die 2. Variante zu nehmen? 
Oder was wäre da der Nachteil?

Gruß

von Werner B. (werner-b)


Lesenswert?

Das Problem ist...

Das SPIF ist i.d.R. gelöscht und wird, falls gesetzt, beim lesen des 
SPSR zurückgesetzt.
Du hängst also in einer Endlosschleife.
Manuell setzen geht nicht.

von Kurt H. (Firma: KHTronik) (kurtharders)


Lesenswert?

Andreas Heil schrieb:
> while(!(SPSR & (1<<SPIF)))
>   ;

Du kannst in der while-Schleife beliebige andere erledigen :-). Oder Du 
steuerst den Versand der Daten per Interrupt.

von Falk B. (falk)


Lesenswert?

@  Andreas Heil (heilinger)

>will, obwohl die aktuelle Sendung noch läuft, dann würde ich vor dem
>nächsten Senden in der while-Schleife hängen?

Ja.

>Also ist es für die Rechenzeit nicht besser die 2. Variante zu nehmen?

Ja.

>Oder was wäre da der Nachteil?

Keiner. Mann muss nur wissen, dass der AVR nen kleinen Bug hat. Nach dem 
Reset müsste das Bit gesetzt sein, weil die Übertragung ja nicht läuft 
bzw. abgeschlossen ist. Ist es aber nicht.

Abhilfe? Einfach am Programmanfang ein beliebiges Byte senden, ohne 
vorher das Statusbit abzufragen.

MFG
Falk

von Peter (Gast)


Lesenswert?

Andreas Heil schrieb:
> Und zwar sieht mein Code momentan so aus, dass ich ein Byte sende:
>
> SPDR = cData;
>
> und dann abwarte, bis das Byte übertragen wurde:
>
> while(!(SPSR & (1<<SPIF)))
>   ;

und warum tauscht du es nicht?

von Andreas H. (heilinger)


Lesenswert?

Peter schrieb:
> und warum tauscht du es nicht?

das war ja meine Frage. Will ja nicht einfach was machen, was evtl. 
Konsequezen hätte, was ich nicht direkt erkenne und wie es aussieht

Falk Brunner schrieb:
> Keiner. Mann muss nur wissen, dass der AVR nen kleinen Bug hat. Nach dem
> Reset müsste das Bit gesetzt sein, weil die Übertragung ja nicht läuft
> bzw. abgeschlossen ist. Ist es aber nicht.
>
> Abhilfe? Einfach am Programmanfang ein beliebiges Byte senden, ohne
> vorher das Statusbit abzufragen.

ist mein Gedanke nicht ganz unbegründet gewesen. Daher werde ich die 
beiden Zeilen nun tauschen und beim Ersten Senden die while-Schleife 
weglassen (so kann es mir egal sein, ob das Bit gesetzt ist oder nicht).

Ich denke so habe ich die Antworten jetzt richtig interpretiert...

von Tek (Gast)


Lesenswert?

Hier:
http://www.mikrocontroller.net/articles/Serial_Peripheral_Interface
findet man den weiterführenden Link zu
http://www.matuschek.net/atmega-spi/

da gehts auch darum.

von Peter D. (peda)


Lesenswert?

In der Regel muß man nach dem Senden das /SS des Slave wieder 
hochziehen.
Also muß man warten.

Aber rechne erstmal aus wie lange ein Byte dauert. Und dann betrachte, 
ob das wirklich zulange ist.


Peter

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.