Wie benutzt man SPI auf einem Arduino?


Antworten:


80

Einführung in SPI

Die SPI-Schnittstelle ( Serial Peripheral Interface Bus ) wird für die Kommunikation zwischen mehreren Geräten über kurze Entfernungen und mit hoher Geschwindigkeit verwendet.

Typischerweise gibt es ein einzelnes "Master" -Gerät, das die Kommunikation initiiert und die Uhr liefert, die die Datenübertragungsrate steuert. Es kann einen oder mehrere Slaves geben. Für mehr als einen Slave hat jeder sein eigenes "Slave-Auswahl" -Signal, das später beschrieben wird.


SPI-Signale

In einem vollwertigen SPI-System haben Sie vier Signalleitungen:

  • Master Out, Slave In ( MOSI ) - Daten, die vom Master zum Slave übertragen werden
  • Master In, Slave Out ( MISO ) - das sind die Daten, die vom Slave zum Master gelangen
  • Serial Clock ( SCK ) - Wenn dies sowohl das Master- als auch das Slave-Sample umschaltet, wird das nächste Bit abgetastet
  • Slave Select ( SS ) - Dies weist einen bestimmten Slave an, "aktiv" zu werden.

Wenn mehrere Slaves an das MISO-Signal angeschlossen sind, wird von ihnen erwartet, dass sie diese MISO-Leitung im Tristate-Zustand (bei hoher Impedanz) halten, bis sie durch Aktivieren von Slave Select ausgewählt werden. Normalerweise geht Slave Select (SS) auf Low, um dies zu bestätigen. Das heißt, es ist aktiv niedrig. Sobald ein bestimmter Slave ausgewählt ist, sollte er die MISO-Leitung als Ausgang konfigurieren, damit Daten an den Master gesendet werden können.

Dieses Bild zeigt, wie Daten ausgetauscht werden, wenn ein Byte gesendet wird:

SPI-Protokoll mit 4 Signalen

Beachten Sie, dass drei Signale vom Master (MOSI, SCK, SS) ausgegeben werden und eines ein Eingang (MISO) ist.


Zeitliche Koordinierung

Die Reihenfolge der Ereignisse ist:

  • SS geht auf low, um es zu aktivieren und den Slave zu aktivieren
  • Die SCKZeile wechselt, um anzuzeigen, wann die Datenzeilen abgetastet werden sollen
  • Die Daten werden sowohl vom Master als auch vom Slave an der Vorderflanke von SCK(unter Verwendung der Standardtaktphase) abgetastet.
  • Sowohl Master als auch Slave bereiten sich auf das nächste Bit an der Rückflanke von SCK(unter Verwendung der Standardtaktphase) vor, indem sie MISO/ MOSIfalls erforderlich ändern
  • Sobald die Übertragung beendet ist (möglicherweise nachdem mehrere Bytes gesendet wurden), wird SSder High-Pegel aktiviert, um sie zu deaktivieren

Beachten Sie, dass:

  • Das höchstwertige Bit wird zuerst gesendet (standardmäßig)
  • Daten werden gleichzeitig gesendet und empfangen (Vollduplex)

Da Daten im selben Takt gesendet und empfangen werden, kann der Slave nicht sofort auf den Master reagieren. SPI-Protokolle erwarten normalerweise, dass der Master bei einer Übertragung Daten anfordert und bei einer nachfolgenden eine Antwort erhält.

Wenn Sie die SPI-Bibliothek auf dem Arduino verwenden, sieht eine einzelne Übertragung im Code folgendermaßen aus:

 byte outgoing = 0xAB;
 byte incoming = SPI.transfer (outgoing);

Beispielcode

Beispiel für das Senden nur (alle eingehenden Daten ignorieren):

#include <SPI.h>

void setup (void)
  {
  digitalWrite(SS, HIGH);  // ensure SS stays high
  SPI.begin ();
  } // end of setup

void loop (void)
  {
  byte c;

  // enable Slave Select
  digitalWrite(SS, LOW);    // SS is pin 10

  // send test string
  for (const char * p = "Fab" ; c = *p; p++)
    SPI.transfer (c);

  // disable Slave Select
  digitalWrite(SS, HIGH);

  delay (100);
  } // end of loop

Verdrahtung nur für SPI-Ausgang

Der obige Code (der nur sendet) kann verwendet werden, um ein serielles Ausgangsschieberegister anzusteuern. Dies sind reine Ausgabegeräte, sodass wir uns keine Gedanken über eingehende Daten machen müssen. In ihrem Fall könnte der SS-Pin als "Speicher" - oder "Verriegelungs" -Pin bezeichnet werden.

SPI-Protokoll mit 3 Signalen

Beispiele hierfür sind das serielle Schieberegister 74HC595 und verschiedene LED-Streifen, um nur einige zu nennen. Diese 64-Pixel-LED-Anzeige wird beispielsweise von einem MAX7219-Chip angesteuert:

64-Pixel-LED-Anzeige

In diesem Fall können Sie sehen, dass der Board-Hersteller etwas andere Signalnamen verwendet hat:

  • DIN (Data In) ist MOSI (Master Out, Slave In)
  • CS (Chip Select) ist SS (Slave Select)
  • CLK (Clock) ist SCK (Serial Clock)

Die meisten Boards folgen einem ähnlichen Muster. Manchmal ist DIN nur DI (Data In).

Hier ist ein weiteres Beispiel, diesmal eine 7-Segment-LED-Anzeigetafel (ebenfalls basierend auf dem MAX7219-Chip):

7-Segment-LED-Anzeige

Dies verwendet genau die gleichen Signalnamen wie die andere Karte. In beiden Fällen ist zu sehen, dass die Platine nur fünf Drähte benötigt, die drei für SPI sowie Strom und Masse.


Taktphase und Polarität

Es gibt vier Möglichkeiten, die SPI-Uhr abzutasten.

Das SPI-Protokoll ermöglicht Änderungen der Polarität der Taktimpulse. CPOL ist die Taktpolarität und CPHA ist die Taktphase.

  • Modus 0 (Standardeinstellung) - Der Takt ist normalerweise niedrig (CPOL = 0), und die Daten werden beim Übergang von niedrig nach hoch (Vorderflanke) abgetastet (CPHA = 0).
  • Modus 1 - Takt ist normalerweise niedrig (CPOL = 0) und die Daten werden beim Übergang von hoch zu niedrig (Rückflanke) abgetastet (CPHA = 1)
  • Modus 2 - Takt ist normalerweise hoch (CPOL = 1) und die Daten werden beim Übergang von hoch zu niedrig (Vorderflanke) abgetastet (CPHA = 0)
  • Modus 3 - Takt ist normalerweise hoch (CPOL = 1) und die Daten werden beim Übergang von niedrig zu hoch (Rückflanke) abgetastet (CPHA = 1)

Diese sind in dieser Grafik dargestellt:

SPI-Taktphase und Polarität

Beziehen Sie sich auf das Datenblatt Ihres Geräts, um die richtige Phase und Polarität zu erhalten. Es wird normalerweise ein Diagramm geben, das zeigt, wie die Uhr abgetastet wird. Zum Beispiel aus dem Datenblatt für den 74HC595-Chip:

74HC595 Uhr

Wie Sie sehen, ist der Takt normalerweise niedrig (CPOL = 0) und wird an der Vorderflanke abgetastet (CPHA = 0), daher ist dies der SPI-Modus 0.

Sie können die Taktpolarität und -phase in Code wie folgt ändern (natürlich nur einen auswählen):

SPI.setDataMode (SPI_MODE0);
SPI.setDataMode (SPI_MODE1);
SPI.setDataMode (SPI_MODE2);
SPI.setDataMode (SPI_MODE3);

Diese Methode ist ab Version 1.6.0 der Arduino IDE veraltet. Für neuere Versionen ändern Sie den Uhrzeitmodus im SPI.beginTransactionAufruf wie folgt:

SPI.beginTransaction (SPISettings (2000000, MSBFIRST, SPI_MODE0));  // 2 MHz clock, MSB first, mode 0

Datenbestellung

Der Standardwert ist das höchstwertige Bit zuerst. Sie können jedoch die Hardware so einstellen, dass das niedrigstwertige Bit zuerst verarbeitet wird:

SPI.setBitOrder (LSBFIRST);   // least significant bit first
SPI.setBitOrder (MSBFIRST);   // most significant bit first

Auch dies ist in den Versionen 1.6.0 und höher der Arduino IDE veraltet. Für neuere Versionen ändern Sie die Bitreihenfolge im SPI.beginTransactionAufruf wie folgt:

SPI.beginTransaction (SPISettings (1000000, LSBFIRST, SPI_MODE2));  // 1 MHz clock, LSB first, mode 2

Geschwindigkeit

Die Standardeinstellung für SPI ist die Verwendung der Systemtaktrate geteilt durch vier, dh eines SPI-Taktimpulses alle 250 ns, unter der Annahme eines 16-MHz-CPU-Takts. Sie können den Taktteiler folgendermaßen ändern setClockDivider:

SPI.setClockDivider (divider);

Wo "Teiler" ist einer von:

  • SPI_CLOCK_DIV2
  • SPI_CLOCK_DIV4
  • SPI_CLOCK_DIV8
  • SPI_CLOCK_DIV16
  • SPI_CLOCK_DIV32
  • SPI_CLOCK_DIV64
  • SPI_CLOCK_DIV128

Die schnellste Rate ist "Dividieren durch 2" oder ein SPI-Takt alle 125 ns, unter der Annahme eines 16-MHz-CPU-Takts. Dies würde daher 8 · 125 ns oder 1 us benötigen, um ein Byte zu übertragen.

Diese Methode ist ab Version 1.6.0 der Arduino IDE veraltet. In den letzten Versionen ändern Sie die Übertragungsgeschwindigkeit im SPI.beginTransactionAnruf wie folgt:

SPI.beginTransaction (SPISettings (4000000, MSBFIRST, SPI_MODE0));  // 4 MHz clock, MSB first, mode 0

Empirische Tests haben jedoch gezeigt, dass zwei Taktimpulse zwischen den Bytes erforderlich sind, sodass die maximale Rate, mit der Bytes ausgelesen werden können, jeweils 1,125 µs beträgt (mit einem Taktteiler von 2).

Zusammenfassend kann jedes Byte mit einer maximalen Rate von eins pro 1,125 us (mit einem 16-MHz-Takt) gesendet werden, was eine theoretische maximale Übertragungsrate von 1 / 1,125 us oder 888.888 Bytes pro Sekunde ergibt (außer Overhead wie das Setzen von SS auf niedrig und so weiter) auf).


Verbinden mit Arduino

Arduino Uno

Anschluss über digitale Pins 10 bis 13:

Arduino Uno SPI-Pins

Verbindung über den ICSP-Header:

ICSP Pinbelegung - Uno

ICSP-Header

Arduino Atmega2560

Anschluss über digitale Pins 50 bis 52:

Arduino Mega2560 SPI-Pins

Sie können auch den ICSP-Header verwenden, ähnlich dem obigen Uno.

Arduino Leonardo

Im Gegensatz zu Uno und Mega legen Leonardo und Micro die SPI-Pins der digitalen Pins nicht frei. Sie können nur die ICSP-Header-Pins verwenden, wie oben für Uno dargestellt.


Mehrere Sklaven

Ein Master kann mit mehreren Slaves kommunizieren (jedoch jeweils nur mit einem). Dies geschieht, indem SS für einen Sklaven aktiviert und für alle anderen deaktiviert wird. Der Slave, bei dem SS aktiviert ist (normalerweise bedeutet dies LOW), konfiguriert seinen MISO-Pin als Ausgang, damit der Slave und nur dieser Slave auf den Master reagieren können. Die anderen Slaves ignorieren ankommende Taktimpulse, wenn SS nicht aktiviert ist. Daher benötigen Sie für jeden Slave ein zusätzliches Signal:

Mehrere SPI-Slaves

In dieser Grafik können Sie sehen, dass MISO, MOSI und SCK von beiden Slaves gemeinsam genutzt werden. Jeder Slave verfügt jedoch über ein eigenes SS-Signal (Slave Select).


Protokolle

Die SPI-Spezifikation spezifiziert keine Protokolle als solche, so dass es Sache der einzelnen Master / Slave-Paarungen ist, zu vereinbaren, was die Daten bedeuten. Während Sie Bytes gleichzeitig senden und empfangen können, kann das empfangene Byte keine direkte Antwort auf das gesendete Byte sein (da sie gleichzeitig zusammengestellt werden).

Daher wäre es logischer, wenn ein Ende eine Anfrage senden würde (z. B. 4 bedeutet "Plattenverzeichnis auflisten") und dann Übertragungen durchführen würde (möglicherweise nur Nullen nach außen senden), bis es eine vollständige Antwort erhält. Die Antwort wird möglicherweise mit einem Zeilenumbruch oder einem 0x00-Zeichen beendet.

Lesen Sie im Datenblatt Ihres Slave-Geräts nach, welche Protokollsequenzen es erwartet.


So machen Sie einen SPI-Slave

Das vorherige Beispiel zeigt den Arduino als Master, der Daten an ein Slave-Gerät sendet. Dieses Beispiel zeigt, wie der Arduino ein Sklave sein kann.

Hardware-Setup

Verbinden Sie zwei Arduino Unos mit den folgenden Stiften, die miteinander verbunden sind:

  • 10 (SS)
  • 11 (MOSI)
  • 12 (MISO)
  • 13 (SCK)

  • + 5v (falls erforderlich)

  • GND (zur Signalrückgabe)

Auf dem Arduino Mega sind die Pins 50 (MISO), 51 (MOSI), 52 (SCK) und 53 (SS).

In jedem Fall MOSI an einem Ende mit MOSI an dem anderen verbunden ist, können Sie nicht tauschen sie um (die Sie ist nicht über MOSI <-> MISO). Die Software konfiguriert ein Ende von MOSI (Master-Ende) als Ausgang und das andere Ende (Slave-Ende) als Eingang.

Master-Beispiel

#include <SPI.h>

void setup (void)
{

  digitalWrite(SS, HIGH);  // ensure SS stays high for now

  // Put SCK, MOSI, SS pins into output mode
  // also put SCK, MOSI into LOW state, and SS into HIGH state.
  // Then put SPI hardware into Master mode and turn SPI on
  SPI.begin ();

  // Slow down the master a bit
  SPI.setClockDivider(SPI_CLOCK_DIV8);

}  // end of setup


void loop (void)
{

  char c;

  // enable Slave Select
  digitalWrite(SS, LOW);    // SS is pin 10

  // send test string
  for (const char * p = "Hello, world!\n" ; c = *p; p++)
    SPI.transfer (c);

  // disable Slave Select
  digitalWrite(SS, HIGH);

  delay (1000);  // 1 seconds delay
}  // end of loop

Slave Beispiel

#include <SPI.h>

char buf [100];
volatile byte pos;
volatile bool process_it;

void setup (void)
{
  Serial.begin (115200);   // debugging

  // turn on SPI in slave mode
  SPCR |= bit (SPE);

  // have to send on master in, *slave out*
  pinMode (MISO, OUTPUT);

  // get ready for an interrupt
  pos = 0;   // buffer empty
  process_it = false;

  // now turn on interrupts
  SPI.attachInterrupt();

}  // end of setup


// SPI interrupt routine
ISR (SPI_STC_vect)
{
byte c = SPDR;  // grab byte from SPI Data Register

  // add to buffer if room
  if (pos < sizeof buf)
    {
    buf [pos++] = c;

    // example: newline means time to process buffer
    if (c == '\n')
      process_it = true;

    }  // end of room available
}  // end of interrupt routine SPI_STC_vect

// main loop - wait for flag set in interrupt routine
void loop (void)
{
  if (process_it)
    {
    buf [pos] = 0;
    Serial.println (buf);
    pos = 0;
    process_it = false;
    }  // end of flag set

}  // end of loop

Der Slave ist vollständig interruptgesteuert und kann daher andere Aufgaben ausführen. Die eingehenden SPI-Daten werden in einem Puffer gesammelt und ein Flag gesetzt, wenn ein "signifikantes Byte" (in diesem Fall eine neue Zeile) ankommt. Dies weist den Slave an, einzusteigen und mit der Datenverarbeitung zu beginnen.

Beispiel für die Verbindung von Master zu Slave über SPI

Arduino SPI Master und Slave


Wie bekomme ich eine Antwort von einem Sklaven?

In Anlehnung an den obigen Code, der Daten von einem SPI-Master an einen Slave sendet, wird im folgenden Beispiel gezeigt, wie Daten an einen Slave gesendet werden, damit etwas getan wird und eine Antwort zurückgegeben wird.

Der Master ähnelt dem obigen Beispiel. Ein wichtiger Punkt ist jedoch, dass wir eine leichte Verzögerung hinzufügen müssen (etwa 20 Mikrosekunden). Andernfalls hat der Slave keine Möglichkeit, auf die eingehenden Daten zu reagieren und etwas damit zu tun.

Das Beispiel zeigt das Senden eines "Befehls". In diesem Fall "a" (etwas hinzufügen) oder "s" (etwas subtrahieren). Dies soll zeigen, dass der Slave tatsächlich etwas mit den Daten tut.

Nach dem Aktivieren von Slave-Select (SS) zum Initiieren der Transaktion sendet der Master den Befehl, gefolgt von einer beliebigen Anzahl von Bytes, und löst dann SS aus, um die Transaktion zu beenden.

Ein sehr wichtiger Punkt ist, dass der Slave nicht gleichzeitig auf ein eingehendes Byte reagieren kann. Die Antwort muss im nächsten Byte sein. Dies liegt daran, dass die Bits, die gesendet werden, und die Bits, die empfangen werden, gleichzeitig gesendet werden. Um also etwas zu vier Zahlen hinzuzufügen, benötigen wir fünf Überweisungen, wie diese:

transferAndWait ('a');  // add command
transferAndWait (10);
a = transferAndWait (17);
b = transferAndWait (33);
c = transferAndWait (42);
d = transferAndWait (0);

Zuerst fordern wir eine Aktion für Nummer 10 an. Bis zur nächsten Überweisung (die für 17) erhalten wir jedoch keine Antwort. Für die Antwort auf 10 wird jedoch ein "a" gesetzt. Schließlich senden wir eine "Dummy" -Nummer 0, um die Antwort für 42 zu erhalten.

Master (Beispiel)

  #include <SPI.h>

  void setup (void)
    {
    Serial.begin (115200);
    Serial.println ();

    digitalWrite(SS, HIGH);  // ensure SS stays high for now
    SPI.begin ();

    // Slow down the master a bit
    SPI.setClockDivider(SPI_CLOCK_DIV8);
    }  // end of setup

  byte transferAndWait (const byte what)
    {
    byte a = SPI.transfer (what);
    delayMicroseconds (20);
    return a;
    } // end of transferAndWait

  void loop (void)
    {

    byte a, b, c, d;

    // enable Slave Select
    digitalWrite(SS, LOW);

    transferAndWait ('a');  // add command
    transferAndWait (10);
    a = transferAndWait (17);
    b = transferAndWait (33);
    c = transferAndWait (42);
    d = transferAndWait (0);

    // disable Slave Select
    digitalWrite(SS, HIGH);

    Serial.println ("Adding results:");
    Serial.println (a, DEC);
    Serial.println (b, DEC);
    Serial.println (c, DEC);
    Serial.println (d, DEC);

    // enable Slave Select
    digitalWrite(SS, LOW);

    transferAndWait ('s');  // subtract command
    transferAndWait (10);
    a = transferAndWait (17);
    b = transferAndWait (33);
    c = transferAndWait (42);
    d = transferAndWait (0);

    // disable Slave Select
    digitalWrite(SS, HIGH);

    Serial.println ("Subtracting results:");
    Serial.println (a, DEC);
    Serial.println (b, DEC);
    Serial.println (c, DEC);
    Serial.println (d, DEC);

    delay (1000);  // 1 second delay
    }  // end of loop

Der Code für den Slave erledigt im Prinzip fast alles in der Interruptroutine (wird aufgerufen, wenn eingehende SPI-Daten ankommen). Es nimmt das eingehende Byte und addiert oder subtrahiert gemäß dem gespeicherten "Befehlsbyte". Beachten Sie, dass die Antwort das nächste Mal über die Schleife "gesammelt" wird. Aus diesem Grund muss der Master eine letzte "Dummy" -Übertragung senden, um die endgültige Antwort zu erhalten.

In meinem Beispiel verwende ich die Hauptschleife, um einfach zu erkennen, wann SS hoch geht, und den gespeicherten Befehl zu löschen. Auf diese Weise wird das erste Byte als Befehlsbyte betrachtet, wenn SS für die nächste Transaktion wieder auf niedrig gesetzt wird.

Zuverlässiger würde dies mit einem Interrupt geschehen. Das heißt, Sie würden SS physisch mit einem der Interrupt-Eingänge verbinden (z. B. auf dem Uno Pin 10 (SS) mit Pin 2 (einem Interrupt-Eingang) verbinden oder einen Pin-Wechsel-Interrupt auf Pin 10 verwenden.

Dann könnte der Interrupt verwendet werden, um zu bemerken, wenn SS niedrig oder hoch gezogen wird.

Slave (Beispiel)

// what to do with incoming data
volatile byte command = 0;

void setup (void)
  {

  // have to send on master in, *slave out*
  pinMode(MISO, OUTPUT);

  // turn on SPI in slave mode
  SPCR |= _BV(SPE);

  // turn on interrupts
  SPCR |= _BV(SPIE);

  }  // end of setup


// SPI interrupt routine
ISR (SPI_STC_vect)
  {
  byte c = SPDR;

  switch (command)
    {
    // no command? then this is the command
    case 0:
      command = c;
      SPDR = 0;
      break;

    // add to incoming byte, return result
    case 'a':
      SPDR = c + 15;  // add 15
      break;

    // subtract from incoming byte, return result
    case 's':
      SPDR = c - 8;  // subtract 8
      break;

    } // end of switch

  }  // end of interrupt service routine (ISR) SPI_STC_vect

void loop (void)
  {

  // if SPI not active, clear current command
  if (digitalRead (SS) == HIGH)
    command = 0;
  }  // end of loop

Beispielausgabe

Adding results:
25
32
48
57
Subtracting results:
2
9
25
34
Adding results:
25
32
48
57
Subtracting results:
2
9
25
34

Logikanalysator-Ausgang

Dies zeigt das Timing zwischen Senden und Empfangen im obigen Code:

SPI Master und Slave Timing


Neue Funktionen ab IDE 1.6.0

Die IDE-Version 1.6.0 hat die Funktionsweise von SPI in gewissem Maße geändert. Sie müssen dies noch tun, SPI.begin() bevor Sie SPI verwenden können. Das richtet die SPI-Hardware ein. Aber jetzt, wenn Sie sind mit einem Slave starten Kommunikation Sie auch tun SPI.beginTransaction()SPI einzurichten (für diesen Slave) mit dem richtigen:

  • Taktfrequenz
  • Bitreihenfolge
  • Taktphase und Polarität

Wenn Sie mit dem Slave fertig sind, rufen Sie an SPI.endTransaction(). Zum Beispiel:

SPI.beginTransaction (SPISettings (2000000, MSBFIRST, SPI_MODE0));
digitalWrite (SS, LOW);        // assert Slave Select
byte foo = SPI.transfer (42);  // do a transfer
digitalWrite (SS, HIGH);       // de-assert Slave Select
SPI.endTransaction ();         // transaction over

Warum SPI verwenden?

Ich würde eine vorläufige Frage hinzufügen: Wann / warum würden Sie SPI verwenden? Eine Multi-Master-Konfiguration oder eine sehr große Anzahl von Slaves würde die Waage in Richtung I2C neigen.

Dies ist eine ausgezeichnete Frage. Meine Antworten sind:

  • Einige Geräte (nicht wenige) unterstützen nur die SPI-Übertragungsmethode. Zum Beispiel das 74HC595-Ausgangsschieberegister, das 74HC165-Eingangsschieberegister, der MAX7219-LED-Treiber und einige LED-Streifen, die ich gesehen habe. Sie können es also verwenden, da das Zielgerät es nur unterstützt.
  • SPI ist die schnellste verfügbare Methode für Atmega328-Chips (und ähnliche). Die oben angegebene schnellste Rate beträgt 888.888 Bytes pro Sekunde. Mit I 2 C können Sie nur ungefähr 40.000 Bytes pro Sekunde erhalten. Der Overhead des I 2 C ist ziemlich hoch, und wenn Sie versuchen, eine sehr schnelle Schnittstelle zu schaffen, ist SPI die bevorzugte Wahl. Nicht wenige Chipfamilien (z. B. MCP23017 und MCP23S17) unterstützen tatsächlich sowohl I 2 C als auch SPI, sodass Sie häufig zwischen Geschwindigkeit und der Möglichkeit wählen können, mehrere Geräte an einem einzigen Bus zu haben.
  • Die Geräte SPI und I 2 C werden beide in der Hardware des Atmega328 unterstützt, so dass Sie möglicherweise gleichzeitig mit I 2 C eine Übertragung über SPI durchführen können , die Ihnen einen Geschwindigkeitsschub verschafft.

Beide Methoden haben ihren Platz. Mit I 2 C können Sie viele Geräte an einen einzigen Bus anschließen (zwei Drähte plus Masse), sodass dies die bevorzugte Wahl ist, wenn Sie eine erhebliche Anzahl von Geräten abfragen müssen, möglicherweise ziemlich selten. Die Geschwindigkeit von SPI könnte jedoch für Situationen relevanter sein, in denen eine schnelle Ausgabe (z. B. ein LED-Streifen) oder eine schnelle Eingabe (z. B. ein ADC-Wandler) erforderlich ist.


Verweise


Wirst du die Verrücktheit verdecken, die der SPI des Fälligen ist? Wo die Konfiguration des SPI-Ports an den verwendeten SS-Pin gebunden ist und dem SPI-Port (IIRC) 4 Hardware-SS-Pins zugewiesen sind?
Majenko

Ein weiterer Punkt zur Auswahl: Manchmal haben Sie wirklich keine Wahl, weil der Sensor, den Sie verwenden möchten / müssen, nur als I2C verfügbar ist.
Igor Stoppa

Are you going to cover the weirdness that is the Due's SPI?- Ich weiß nichts über die SPI des Due (abgesehen von der Annahme, dass das Gesamtprotokoll dasselbe ist). Sie können gerne eine Antwort hinzufügen, die diesen Aspekt abdeckt.
Nick Gammon

Wann kommt das Hörbuch dieser Antwort heraus, und werden Sie es selbst lesen
?

1
@AMADANONInc. Vielleicht ein Musikvideo? Oder eine Animation? Ich bin nicht sicher, ob mein australischer Akzent verständlich wäre. : P
Nick Gammon
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.