Hallo Leute! Habe hier ein Testaufbau mit zwei µCs die über SPI verbunden sind. An einem µC ist ein LCD für die Ausgabe angeschlossen. Erklärung der beiden Programme: Der Master sendet 3 Bytes zum Slave. Der Slave empfängt, und rechnen bei allen Bytes +1 und versendet dann wieder. Der Master empfängt die 3 Bytes und zeigt das Ergebnis im LCD an. Das Problem was ich habe, das erste empfangene Byte entspricht immer genau dem letzten gesendeten Byte des Masters. Außerdem verstehe ich nicht, wenn ich im Programm des Slaves den Wait Befehl ausklammer, Kommen nur nullen beim Master an. Warum? Danke für eure Beiträge.... LG....
>Das Problem was ich habe, das erste empfangene Byte entspricht immer >genau dem letzten gesendeten Byte des Masters. Das ist auch korrekt so. Du hast SPI nicht verstanden.
Wie versendet der Slave ? Schau dir das mal an und lass uns dann teilhaben.
Christian Betzen schrieb: > Hallo Leute! > > Habe hier ein Testaufbau mit zwei µCs die über SPI verbunden sind. > An einem µC ist ein LCD für die Ausgabe angeschlossen. > > Erklärung der beiden Programme: > > Der Master sendet 3 Bytes zum Slave. Der Slave empfängt, und rechnen bei > allen Bytes +1 und versendet dann wieder. Nö. Der Slave versendet nicht. Der Slave kann überhaupt nicht aktiv senden. Es ist immer der Master, der die Kontrolle hat. D.h. dein Master gibt 3 Bytes an den Slave. Und dann will er 3 Bytes haben! Dabei ist es ihm schei...egal, ob der Slave schon fertig ist oder nicht. Mittels Spiin Y(1) , 3 erzwingt er vom Slave das Herausrücken von 3 Bytes. Genau genommen ist es bei SPI nicht so prickelnd von Senden und Empfangen zu sprechen. Eine SPI Übertragung ist ein Austausch von Bytes. Während 1 Byte vom Master zum Slave geht, wird 1 Byte vom Slave zum Master übertragen. Das ganze hat als mehr etwas von Du sitzt am Tisch deinen Kumpel gegenüber. Jeder von euch beiden hat vor sich einen Zettel und einen Bleistift und kann eine Zahl (0-255) auf diesen zettel schreiben. Auf ein Signal von dir schiebt jeder mit seiner rechten Hand seinen Zettel zum Gegenüber, während er gleichzeitig mit der linken Hand den Zettel übernimmt, der ihm zugeschoben wird. So funktioniert SPI eigentlich. D.h. 'Senden' und 'Empfangen' sind eigentlich dasselbe, weil ein Austausch an Bytes erfolgt. Das man Senden und Empfangen trotzdem unterscheidet, liegt daran, weil man irgendwann ja auch mal festlegen will, was auf den Austauschzettel geschrieben werden soll, bzw. man daran interessiert ist, was auf dem Zettel stand, den man selbst gekriegt hat. Aber der springende Punkt ist: Dein Kumpel hat keinbe Chance selbst aktiv zu werden. Du bist der Master und auf dein Signal hin werden die Zettel getauscht. Es spielt dabei keine Rolle ob dein Kumpel überhaupt schon was auf seinen Zettel geschrieben hat oder ob da noch das drauf stand, was du selber rübergeschoben hast. Wenn dein Kumpel kurz aufs Klo ging, dann ist es sehr wahrscheinlich, dass du dann genau wieder das zurück kriegst, was du selber zuletzt rüber geschoben hast.
:
Bearbeitet durch User
Hi! Ich habe noch nie was mit SPI gemacht. Sind die ersten Gehversuche. Aber danke für den Hinweis, dass ichs nicht verstanden hab. Ich glaube ich habe da schon ne Lösung gefunden. Ich muss immer noch ein Dummybyte mitsenden. Damit das Register alle wichtigen Bytes in das Programm überträgt und nix wichtiges im Register stehen bleibt. Beim empfangen, kommt dann erst das Dummybyte, weil es noch im Register steht. Das verwerfe ich dann. Die danach empfangenen Bytes sind dann die, die ich haben will. Wenn ich gleich wieder vorm PC bin probier ich das mal aus. Kann mir jetzt noch einer sagen, warum ich ohne Wait nur nullen empfange? Richtig?
Der Vorgang hat noch eine weitere logische Ebene. Das hast Du mit dem "Dummy-Byte" eben mal so berührt, ohne es zu wissen. Die Peripheriegeräte (das LCD etc.) reagieren nämlich aufgrund ihres gegenwärtigen Zustandes auf die vom Master gesendeten Daten mit dem zurücksenden von Daten die eben von diesem Zustand abhängen. Das bezeichnet man als "Protokoll". Die Beschreibung des Protokolls geht aus dem Datenblatt hervor. Falls Du dazu weitere Fragen hast, poste uns bitte einen Link auf das Datenblatt.
Hi! Dein Beispiel mit den Zetteln find ich toll. Hätte das nur mit Kartoffeln, Braten und Gemüse gemacht. Wenn man so will, hat der Slave Gemüse für den Master in der Hand. Der Master gibt jetzt die Kartoffeln an den Slave und erhält dann das Gemüse. Wenn der Slave jetzt den Braten haben will, muss er erst n Zettel schreiben wo Kartoffeln drauf steht und in die Hand holen. Aber erst wenn der Master dem Slave wieder das Gemüse zurück gibt, erhält der Master die Bestellung. Der Master kann jetzt gleich einen Austausch anstoßen und den Braten versenden und erhält dann wieder das Gemüse zurück. Sry, ich bin beim Essen ;)
SPI-Slave Senden ist beim AVR ein Albtraum, da ungepuffert. Im Prinzip muß man folgendes machen: - Master zieht /SS auf low und dreht Däumchen. - Slave löst damit einen Interrupt aus und schreibt was in das SPI-Register - wenn Master lange genug gewartet hat, schreibt er ein Dummybyte, um das Byte des Slave zu empfangen. - Master liest das Byte und dreht wieder Däumchen. - Slave kriegt Interrupt und schreibt das nächste Byte in das SPI-Register- - wenn Master lange genug gewartet hat, schreibt er ein Dummybyte, um das Byte des Slave zu empfangen. - Master liest das Byte und dreht wieder Däumchen. - Slave kriegt Interrupt und schreibt das nächste Byte in das SPI-Register usw. usw.
Christian Betzen schrieb: > Ich habe noch nie was mit SPI gemacht. Sind die ersten Gehversuche. Aber > danke für den Hinweis, dass ichs nicht verstanden hab. SPI sind einfach hintereinandergeschaltete Schieberegister: http://www.lothar-miller.de/s9y/categories/17-SPI Wenn man das mal kapiert hat, wird es auf einmal ganz einfach...
SPI macht Appetit und ist auf die Geselligkeit der Mitwirkenden dringend angewiesen. Das konnte man hier sehr gut erklärt erfahren. ;-) MfG Paul
Also gut! In Bascom kann man aber jetzt leider keine Kartoffeln oder Gemüse austauschen, sondern nur Zahlen. Auszug aus Beispielprogramm: Master: Spiout A(1) , 4 '4 Byte senden Spiin Y(1) , 4 '4 Byte empfangen Slave: Spiin A(1) , 4 '4 Bytes empfangen Spiout A(1) , 4 'die gleichen 4 Bytes wieder zurück senden Das Ergebnis aus dem Programm ist, dass beim Master Y(1), a(4) entspricht. Das liegt wohl daran, weil a(4) das letzte Byte noch im Register liegt, und dann beim empfangen wieder zurück in das erste Byte geschoben wird. Wie mach ich das jetzt, dass er das erste Byte verwirft. LG
Christian Betzen schrieb: > Wie mach ich das jetzt, dass er das erste Byte verwirft. Du ignorierst es einfach. So wie du im Bahnhof den Zug ignorierst, der vor deinem Zug am selben Gleis abfährt. > Master: > Spiout A(1) , 4 '4 Byte senden > Spiin Y(1) , 4 '4 Byte empfangen > > Slave: > Spiin A(1) , 4 '4 Bytes empfangen > Spiout A(1) , 4 'die gleichen 4 Bytes wieder zurück > senden Ich weiß nicht, ob Bascom schon richtig reif für SPI ist. Denn ein Slave kann nicht erst 4 Bytes empfangen und dann von sich aus die 4 Bytes wieder zurücksenden. SPI empfängt und sendet immer gleichzeitig! (ich war versucht, hier mindestens 5 Ausrufezeichen zu machen!) Das kannst du mit diesen Befehlen nicht abbilden... :-/
:
Bearbeitet durch Moderator
Alles klar, also sagen wir mal so... Master: Spiout A(1) , 4 '4 Byte senden Spiin Y(1) , 4 '4 Byte empfangen y(1) = y(2) y(2) = y(3) y(3) = y(4) Slave: Spiin A(1) , 4 '4 Bytes empfangen Spiout A(1) , 4 'die gleichen 4 Bytes wieder zurück senden Damit werden dann die Empfangenen Bytes einfach in die andere Variable darunter verschoben. Funktioniert aber leider nicht :(
Hi! > Ich weiß nicht, ob Bascom schon richtig reif für SPI ist. Denn ein Slave > kann nicht erst 4 Bytes empfangen und dann von sich aus die 4 Bytes > wieder zurücksenden. SPI empfängt und sendet immer gleichzeitig! > (ich war versucht, hier mindestens 5 Ausrufezeichen zu machen!) > Das kannst du mit diesen Befehlen nicht abbilden... :-/ In der Bascom Hilfe wird der Befehl "spiin" und "spiout" aber so vorgeschlagen.... spiin x(1), 5 'Die fünf Bytes senden von x(1) bis x(5) usw... :-/
Also gut! Nachdem wohl alle ihr Pulver verschossen haben, im Anhang wie ich s gelöst habe. Es ist das Prinzip Ich beachte den Zug nicht der da gerade abfährt...
>SPI-Slave Senden ist beim AVR ein Albtraum, da ungepuffert. >Im Prinzip muß man folgendes machen: >usw........ Ja stimmt (auch xmega hat das, wieso machen so en Schei?? etliche Jahre lang ohne es abzustellen??). Allerdings, es geht doch continuierlich (also ohne 'dreht wieder Däumchen') wenn die SCLK so langsam gewählt wird (oder der Slave so schnell 'gemacht' wird) dass er zwischen 2 SCLKs genug Zeit hat das Byte zum SPI-TX zu schreiben. (oder man macht Handshake) >SPI sind einfach hintereinandergeschaltete Schieberegister: Ja, aber die Frage ist, wie s ein/ausgelesen wird.
Christian Betzen schrieb: > Hi! > >> Ich weiß nicht, ob Bascom schon richtig reif für SPI ist. Denn ein Slave >> kann nicht erst 4 Bytes empfangen und dann von sich aus die 4 Bytes >> wieder zurücksenden. SPI empfängt und sendet immer gleichzeitig! >> (ich war versucht, hier mindestens 5 Ausrufezeichen zu machen!) >> Das kannst du mit diesen Befehlen nicht abbilden... :-/ > > In der Bascom Hilfe wird der Befehl "spiin" und "spiout" aber so > vorgeschlagen.... Das Problem ist eher, dass auch in BASCOM alle SPI nur als Master benutzen. Beim Master gibt es an sich kein (allzugroßes) Problem. Aber wenn SPI als Slave eingesetzt werden soll, dann macht das Ärger.
huhu, das ist ein sehr leckerer Thread, der gefällt mir! best wishes dat Beast
Christian Betzen schrieb: > In der Bascom Hilfe wird der Befehl "spiin" und "spiout" aber so > vorgeschlagen.... Ich würde dieser Bibliothek erst trauen, wenn ich ihre Implementierung gesehen habe. Wenn tatsächlich solche Befehlssequenzen funktionieren Spiout A(1) , 4 '4 Byte senden Spiin Y(1) , 4 '4 Byte empfangen dann muss irgeneine Art von Puffer eingebaut sein, oder die Funktion Spiin eine Beziehnung zu Spiout haben. Denn eines ist klar: wenn ich mit SPI 4 Bytes ausgebe, bekomme ich genauso 4 Bytes zurück.
Christian Betzen schrieb: > Nachdem wohl alle ihr Pulver verschossen haben, im Anhang wie ich s > gelöst habe. Du bekämpfst die Wirkung, aber nicht das Problem. Du wirst daher bald damit auf die Nase fallen. Der Slave muß erstmal erkennen, wann ein neues Paket überhaupt anfängt. Also muß er mit der fallenden Flanke des /SS einen Interrupt auslösen und dann das 1. Byte ins SPDR schreiben. D.h. /SS mit einem INT-Pin verbinden oder als Pin-Change Interrupt konfigurieren.
Der Slave Select SS wird doch über die Zeile SPI config aktiviert. In meiner Schaltung passiert auch nur was, wenn ich die Verbindung der beiden ss nutze. Der Austausch von Bytes funktioniert jedenfalls. Es ergibt sich aber ein neues Problem. Wenn ich jetzt z.b. über nen 1W Bus nen Temperatursensor auslesen will, funktioniert die Übertragung der Bytes nicht mehr. Was muss ich da beachten? Ich kann leider kein Programmschnipsel hier einbringen, bin z.Z. Unterwegs. Schreibt einfach mal was euch dazu einfällt.
Christian Betzen schrieb: > Wenn ich jetzt z.b. über nen 1W Bus nen Temperatursensor > auslesen will, funktioniert die Übertragung der Bytes nicht mehr. Was vollkommen logisch ist. Dein Testprogramm benutzt ja 100% der CPU-Zeit für das SPI. Sobald Du noch was anderes machen willst, mußt Du Interrupts benutzen. Der externe Interrupt am /SS schreibt alle Bytes in einen Puffer und gibt dann den SPI-Interrupt frei.
Peter Dannegger schrieb: > Also muß er mit der fallenden Flanke des /SS einen Interrupt auslösen > und dann das 1. Byte ins SPDR schreiben. > D.h. /SS mit einem INT-Pin verbinden oder als Pin-Change Interrupt > konfigurieren. quark, ein spi interrupt loest automatisch aus, wenn ein byte empfangen ist wenn der zettel beim slave angekommen ist, dann kriegt der automatisch mit, dass was da ist. der slave hat so lange zeit, das register zu lesen oder zu schreiben, bis der master das naechste byte gewechselt hat. das spi register ist naemlich gelatcht macht euch mal schlau, bevor ihr anfaengern irgendwelchen mist erzaehlt spiin, spiout, spimove sind alles nur master befehle. wuerde ja auch keinen sinn beim slave machen.
Interrupt schrieb: > das spi register ist naemlich gelatcht Das Empfangsregister schon. Aber wenn du mit deinem AVR ein Slave bist und ein Byte versenden sollst, dann hast du das Problem, dass du vor dem ersten SCK-Impuls die zu versendenden Daten ins SPDR schreiben musst, denn das Senderegister ist nicht gepuffert. > macht euch mal schlau, bevor ihr anfaengern irgendwelchen mist erzaehlt Ja, so ist es. Du hast das Problem nicht korrekt erfasst.
:
Bearbeitet durch Moderator
Interrupt schrieb: > quark, ein spi interrupt loest automatisch aus, wenn ein byte empfangen > ist Dann mußt Du aber beim Slave den Hellseherinterrupt aktivieren, damit er das erste zu sendende Byte in das SPDR schreibt, kurz bevor der Master SCK taktet. Und wie soll der Slave wissen, ob es das erste Byte eines Pakets ist, wenn er keinen /SS-Interrupt auslöst?
Peter Dannegger schrieb: > Interrupt schrieb: >> quark, ein spi interrupt loest automatisch aus, wenn ein byte empfangen >> ist > > Dann mußt Du aber beim Slave den Hellseherinterrupt aktivieren, damit er > das erste zu sendende Byte in das SPDR schreibt, kurz bevor der Master > SCK taktet. > > Und wie soll der Slave wissen, ob es das erste Byte eines Pakets ist, > wenn er keinen /SS-Interrupt auslöst? Oder man kopiert das zu schreibende Byte in den Puffer, sobald er ausgelesen wurden.
Walter Tarpan schrieb: > Oder man kopiert das zu schreibende Byte in den Puffer, sobald er > ausgelesen wurden. Je nach Abstand der Pakete kann dieses aber schon hoffnungslos veraltet sein. SPI-Slave ohne MC werten immer die /SS-Flanke aus, um den Beginn eines Pakets festzustellen. In der Regel ist dann das erste Byte ein Kommandobyte, welches z.B. Daten senden bedeuten kann. D.h. ein Slave ohne MC sendet frühestens ab dem 2.Byte gültige Daten. Ich habe SPI noch nie zur MC-MC Verbindung benutzt. Das ist mir einfach zu umständlich und vorallem zu unsicher.
:
Bearbeitet durch User
Peter Dannegger schrieb: > Je nach Abstand der Pakete kann dieses aber schon hoffnungslos veraltet > sein. Stimmt. Erst das zweite Byte kann aktueller sein.
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.