Diese Seite ist der zweite Beitrag einer Artikelserie, die den Multi-Gigabit-Transceiver (MGT) vorstellt.
Einführung
Multi-Gigabit-Transceiver (MGTs) sind die grundlegenden Bausteine für viele bekannte Protokolle: PCIe, SATA, Gigabit-Ethernet, SuperSpeed-USB, Thunderbolt und DisplayPort. Alle diese Protokolle haben eines gemeinsam: Ein Computer ist beteiligt. Es gibt außerdem mehrere Telekommunikationsprotokolle, die dafür vorgesehen sind, Telefongespräche über eine Glasfaserverbindung zu übertragen.
MGTs sind auch für den Datenaustausch zwischen zwei FPGAs nützlich. Einige Dinge, die bei der Verwendung eines MGTs zu diesem Zweck zu beachten sind, sind auf einer früheren Seite aufgelistet. Offensichtlich wird eine Art Protokoll benötigt, um sicherzustellen, dass die Daten über den physikalischen Kanal korrekt und mit akzeptabler Zuverlässigkeit übertragen werden. Die Implementierung eines solchen Protokolls ist recht kompliziert. Daher stellt sich die Frage, ob es fertige Protokolle oder andere Bausteine gibt, die helfen können.
Diese Seite versucht, die wichtigsten Alternativen zusammenzufassen. Sie sind unten nach dem Komplexitätsgrad der Anwendungslogik geordnet, wobei die am wenigsten komplexe zuerst aufgeführt ist.
Alle unten genannten Protokolle können sowohl als bidirektionale Verbindung (Vollduplex) als auch als Einwegverbindung (Halbduplex) arbeiten, sofern nichts anderes angegeben ist.
Xillyp2p
Xillyp2p ist ein proprietäres Protokoll, das einen zuverlässigen Transport mehrerer Datenströme zwischen zwei FPGAs ermöglicht. Das Protokoll übernimmt die Übertragung, zeitliche Einplanung, Neuübertragung und Flusskontrolle (Flow Control) der Anwendungsdaten – ähnlich wie TCP/IP Daten über ein Netzwerk transportiert: Es ist garantiert, dass alle Daten korrekt auf der Gegenseite ankommen.
Die Anwendungslogik interagiert mit der Implementierung des Protokolls über Standard-FIFOs. Das Protokoll erzeugt die Illusion eines standardmäßigen FIFOs, der sich über die beiden FPGAs erstreckt: Die Schreibseite dieses virtuellen FIFOs befindet sich auf dem einen FPGA, die Leseseite auf dem anderen FPGA.
In jedem der beiden FPGAs ist eine Seite des FIFOs mit der Anwendungslogik verbunden, während die andere Seite mit der Protokolllogik zusammenarbeitet. Die Anwendungslogik auf der sendenden Seite schreibt also Daten in einen FIFO, und die Anwendungslogik auf der empfangenden Seite liest Daten aus einem anderen FIFO. Das Protokoll ist dafür verantwortlich, die Daten vom FIFO auf dem sendenden FPGA zum FIFO auf dem empfangenden FPGA zu bewegen. Die Flusskontrolle des Protokolls stellt sicher, dass der FIFO auf dem ZielfPGA niemals den Status full (voll) erreicht.
Das Protokoll kann mehrere FIFOs in beide Richtungen bedienen. Ein fairer Datenübertragungs-Scheduler sorgt für eine effiziente Nutzung der Bandbreite des MGTs. Die Daten im FIFO auf der Senderseite werden schnell genug übernommen, sodass dieser FIFO nicht den Status full (voll) erreicht (sofern die Bandbreite dies zulässt und die Daten auf der anderen Seite aus dem FIFO gelesen werden).
Das Protokoll besitzt außerdem eine andere Schnittstelle zum Senden von Paketen (mithilfe eines EOP-Ports).
Eine Halbduplex-Option wird ebenfalls unterstützt. In diesem Fall stellt das Protokoll sicher, dass alle ankommenden Daten korrekt sind. Tritt ein Bitfehler auf dem physikalischen Kanal auf, wird der Datenfluss angehalten, bevor fehlerhafte Daten die Anwendungslogik erreichen.
Gigabit-Ethernet
Obwohl Gigabit-Ethernet für die Kommunikation zwischen Computern gedacht ist, lässt es sich auch zum Senden von Paketen zwischen zwei FPGAs verwenden. Einen passenden IP-Core (IP core) stellt der FPGA-Hersteller in der Regel bereit. Die Anwendungslogik ist daher dafür zuständig, Ethernet-Pakete über eine der Standardschnittstellen (GMII, RGMII, XGMII usw.) zu erzeugen und zu empfangen.
Wie bei jeder Ethernet-Verbindung ist es Aufgabe der Anwendungslogik, die Daten in Pakete zu organisieren und Fehler auf der Verbindung zu behandeln (z. B. durch eine Neuübertragung).
Interlaken
Interlaken ist ein offenes Protokoll zur paketweisen Kommunikation zwischen Chips. Es basiert auf der 64b/67b-Kodierung: Der Datenfluss auf der untersten Ebene besteht darin, wiederholt Segmente von 64 Bit zu senden. Vor jedem dieser Segmente werden 3 Bits hinzugefügt, um zwischen Anwendungsdaten und Steuerwörtern zu unterscheiden. Das Protokoll ist für eine Simplex-Verbindung (unidirektionaler physikalischer Kanal) definiert. Wenn eine Vollduplex-Verbindung (bidirektionaler physikalischer Kanal) verwendet wird, funktioniert sie genauso wie eine Simplex-Verbindung, außer dass Flusskontrollnachrichten in der Gegenrichtung gesendet werden können.
Die grundlegende Übertragungseinheit des Protokolls ist ein Burst variabler Länge. Unmittelbar vor und nach jedem solchen Burst wird ein Steuerwort übertragen. Diese beiden Steuerwörter enthalten Informationen, die eine Abstraktion von Paketen und Kanälen ermöglichen. Dazu gehören unter anderem:
- Kanalnummer: Eine Zahl zwischen 0 und 255, die den nachfolgenden Datenburst einem Kanal zuordnet. Es ist möglich, die Anzahl der Kanäle auf bis zu 65536 zu erweitern.
- SOP: Ein Flag, das anzeigt, dass die nachfolgenden Daten den Anfang eines Pakets bilden.
- EOP: Ein Flag, das anzeigt, dass der Burst vor dem Steuerwort die letzten Daten eines Pakets enthielt. Das EOP gibt außerdem die Anzahl der gültigen Bytes im letzten Wort des Bursts an und ob das Paket Fehler enthält.
Die Länge jedes Bursts darf nicht größer als BurstMax und nicht kleiner als BurstShort sein. BurstMax und BurstShort sind Parameter, die für eine bestimmte Anwendung gewählt werden. BurstShort beträgt mindestens 32 Byte (und muss ein Vielfaches von 8 sein), und BurstMax muss ein Vielfaches von 64 Byte sein.
Der Inhalt des Steuerworts und des (gegebenenfalls) davor übertragenen Datenbursts wird mit einer CRC24 auf Bitfehler geprüft.
Wenn ein Burst den CRC24-Test nicht besteht (d. h. ein Bitfehler erkannt wird), kann eine Neuübertragung angefordert werden, wie in der Interlaken Retransmit Extension Protocol Definition festgelegt. Dem vorgeschlagenen Mechanismus zufolge wird diese Anforderung über einen Satz von drei physikalischen Leitungen vom Empfänger zum Sender übertragen. Diese Leitungen heißen FC_CLK, FC_DATA und FC_SYNC und waren ursprünglich für die Out-of-Band-Flusskontrolle (Out-of-Band Flow Control, OOBFC) gedacht. Für das Senden von Flusskontrollanforderungen ist ein einfaches serielles Datenübertragungsprotokoll definiert. Wenn die Neuübertragung aktiviert ist, wird eines dieser Bits „RT“ genannt und zum Anfordern einer Neuübertragung verwendet. Mit anderen Worten: Das Protokoll definiert keine Möglichkeit, die Neuübertragungsanforderung über die MGT-Verbindung selbst zu senden, sondern nur über die drei separaten physikalischen Out-of-Band-Leitungen.
Die Neuübertragungsanforderung enthält keine Information darüber, mit welchem Burst die Neuübertragung beginnen soll. Stattdessen muss die sendende Seite eine festgelegte Menge an Burstdaten in einem Puffer speichern. Wenn eine Neuübertragungsanforderung eintrifft, werden alle Bursts im Puffer erneut übertragen. Die Größe des Puffers muss also groß genug sein, um den verlorenen Burst aufzunehmen. Ist der Puffer jedoch zu groß, werden die Neuübertragungen länger als nötig. Um die Puffergröße festzulegen, muss die Umlaufzeit (Round-Trip-Zeit) sorgfältig berechnet werden: von der Übergabe eines Bursts an die Logik, die das Interlaken-Protokoll implementiert, bis zum Eintreffen einer Neuübertragungsanforderung.
Der Empfänger erkennt neu übertragene Bursts mithilfe eines Zählers, der bei jedem erstmals übertragenen Burst erhöht wird (es ist auch möglich, den Zähler erst nach jeweils 2, 4, 8 usw. Bursts zu erhöhen). Der Wert dieses Zählers wird in dem Multiple-Use-Teil der Steuerwörter übertragen, die vor und nach jedem Burst gesendet werden. Der Empfänger verwendet diesen Zähler, um zwischen einem neuen Burst und einem erneut übertragenen Burst zu unterscheiden.
Das Interlaken-Protokoll besitzt außerdem eine CRC32-Prüfung zu Diagnosezwecken (einmal pro Meta-Frame). Wenn jedoch mit dieser Prüfung ein Fehler erkannt wird, bezieht er sich auf ein großes Datensegment und nicht auf einen bestimmten Burst oder ein bestimmtes Paket. Anders ausgedrückt: Wenn Daten trotz eines Bitfehlers den CRC24-Test bestanden haben, wird das erst später bemerkt – und zwar ohne auf den Burst zeigen zu können, der die fehlerhaften Daten enthält.
Es ist möglich, einen Neuübertragungsmechanismus zu entwerfen und zu implementieren, der auf dem Datenfluss des MGTs in der anderen Richtung basiert. Das Interlaken-Protokoll schlägt für einen solchen Mechanismus keine Methode vor, aber es ist dennoch möglich, ihm einen eigenen Kanal für Pakete zuzuweisen, mit denen Neuübertragungen angefordert werden. Eine solche Lösung kann einen erheblichen Vorteil bringen, da sie gezielter angeben kann, was neu übertragen werden soll. Es ist auch möglich, eine bessere CRC-Prüfung einzusetzen, vielleicht auf Paket- statt auf Burst-Ebene. Wenn man diesen Ansatz wählt, muss der gesamte Mechanismus jedoch in der Anwendungslogik implementiert werden.
Die Flusskontrollmechanismen von Interlaken werden auf einer eigenen Seite besprochen.
Aurora
Aurora ist ein Protokoll, das von Xilinx (jetzt AMD) für seine eigenen FPGAs entwickelt wurde. Die grundlegende Übertragungseinheit dieses Protokolls ist ein einzelnes Wort (mit einer festen Breite, die von der Anzahl der beteiligten MGTs abhängt). Das Protokoll unterstützt allerdings auch die Übertragung von Paketen, die im Protokoll als Frames bezeichnet werden. Die Anwendungslogik teilt den Datenstrom mithilfe eines „last“-Eingangsports in Pakete auf.
Es gibt zwei Varianten von Aurora: mit 8b/10b-Kodierung und mit 64b/66b-Kodierung. Die 64b/66b-Kodierung ist effizienter; diese Variante sollte daher bevorzugt werden, wenn möglich.
Aurora ist für eine Simplex-Verbindung (unidirektionaler physikalischer Kanal) und für eine Vollduplex-Verbindung (bidirektionaler physikalischer Kanal) definiert. Aus Sicht der Anwendungslogik gibt es keinen nennenswerten Unterschied zwischen den beiden Optionen, außer dass Flusskontrolle bei einer Simplex-Verbindung bedeutungslos ist.
Beachten Sie, dass das Aurora-Protokoll – anders als Interlaken – keine Kanäle vorsieht. Mit anderen Worten: Alle über den physikalischen Kanal übertragenen Daten gehören zu einem einzigen Datenstrom. Wenn in dem Protokoll das Wort „Kanal“ verwendet wird, ist damit der physikalische Kanal gemeint und nicht eine Aufteilung der Daten in unabhängige Datenströme. Falls eine solche Aufteilung gewünscht ist, muss die Anwendungslogik dies implementieren, möglicherweise indem sie jedem Paket einen Header voranstellt.
Bitfehler auf dem physikalischen Kanal werden von dem Protokoll nicht korrigiert. Wenn das Protokoll jedoch zum Senden von Paketen verwendet wird, hängt der Sender optional eine CRC an das Ende jedes Pakets an (in Xilinx’ Implementierung des Protokolls). Die Implementierung des Protokolls prüft diese CRC auf der Empfängerseite und teilt der Anwendungslogik mit, ob in dem Paket ein Fehler erkannt wurde. Wenn Aurora ohne Pakete verwendet wird (ohne ein „last“-Signal), unterstützt das Protokoll keine Fehlererkennung.
Die eigenen Steuerinformationen des Protokolls werden ohne Schutz gegen Bitfehler übertragen. Für solche Übertragungen gibt es keine CRC. Treten Bitfehler auf der physikalischen Verbindung auf, kann das Protokoll auf vielfältige Weise fehlfunktionieren.
Neuübertragungsmechanismen, Mehrkanal-Multiplexing und die Planung von Übertragungen müssen von der Anwendungslogik implementiert werden. Eine eigene Seite bespricht die Möglichkeiten zur Implementierung der Flusskontrolle bei Aurora.
Serial Lite
Bei Altera gibt es eine Reihe von Protokollen und IP-Cores (IP cores), die den gemeinsamen Namen Serial Lite tragen:
- SerialLite II: Paketbasierte oder nicht-paketbasierte Schnittstelle zum Empfangen und Senden von Daten („Atlantic Interface“). Unterstützt die Neuübertragung bei Bitfehlern. Nur für frühere FPGAs geeignet (von Arria II bis zu den FPGAs der Serie V).
- Serial Lite III: Unterstützt den Continuous-Modus und den Burst-Modus. Im Continuous-Modus kann der Datenstrom ohne Unterbrechung und ohne Lücken zwischen Sender und Empfänger fließen. Dafür müssen beide Seiten denselben Referenztakt verwenden. Dieses Protokoll basiert intern auf Interlaken, unterstützt aber weder Kanäle noch SOP/EOP. Dementsprechend ist die Datenbreite der Schnittstelle 64 Bit, multipliziert mit der Anzahl der verwendeten MGTs. Bitfehler auf der physikalischen Verbindung werden als Diagnoseereignis in Bezug auf das MGT gemeldet, das sie verursacht hat, nicht jedoch in Bezug auf ein bestimmtes Datensegment. Anwendbar auf FPGAs der Serie V und der Serie 10.
- Serial Lite IV: Basiert auf der Avalon-Streaming-Schnittstelle mit Signalen für den Anfang und das Ende von Paketen (MAC). Eine CRC wird optional vom Sender am Ende der Pakete eingefügt und vom Empfänger geprüft. Es gibt außerdem einen Basic-Modus ohne Unterteilung in Pakete. Anwendbar auf Stratix 10 und Agilex E-tile.
Die IP-Cores sind über die verschiedenen Mitglieder dieser Protokollserie hinweg nicht kompatibel. Nur SerialLite II kann Neuübertragungen auslösen.
RapidIO
RapidIO ist ein paketbasiertes Protokoll, das PCIe insofern ähnelt, als die unterstützten Pakettypen Operationen entsprechen, die von einer CPU benötigt werden. Dazu gehören unter anderem:
- Schreiben (Write): Schreibt Daten an eine Adresse. Für diese Operation gibt es mehrere Varianten; eine davon verlangt eine Antwortmeldung, die anzeigt, dass die Operation abgeschlossen wurde.
- Lesen (Read): Eine Anforderung, Daten von einer Adresse zu lesen. Das Ziel sendet als Antwort auf diese Anforderung ein Antwortpaket.
- Atomares Lesen-Modifizieren-Schreiben (Read-Modify-Write): Eine Anforderung, nach dem Lesen des bisherigen Werts Daten an eine Adresse zu schreiben, und zwar als atomare Operation. Zu den unterstützten Operationen gehören unter anderem: atomares Inkrementieren, atomares Dekrementieren, atomares Tauschen (Atomic Swap) sowie Compare-and-Swap (Vergleichen-und-Tauschen).
- Mehrere Wartungsanforderungen (Maintenance Requests) für die Erkennung, Steuerung und Statusabfrage. Ähnlich dem Konfigurationsregisterraum des PCI-Protokolls greifen diese Wartungsanforderungen auf Capability-Register (CAR) sowie Befehls- und Statusregister (CSR) zu.
Der wichtigste funktionale Unterschied zwischen RapidIO und PCIe besteht darin, dass das PCIe-Protokoll eine zentrale Einheit (einen Root Complex, normalerweise eine CPU) benötigt, die alle Endpunkte im System konfiguriert. Ein RapidIO-System benötigt eine solche zentrale Einheit nicht.
Ein weiterer Unterschied zu PCIe ist, dass die Neuübertragung von Paketen optional ist. Eine Neuübertragung erfolgt nur für Pakete, die als „reliable traffic“ (RT) gesendet werden. Pakete können auch als „continuous traffic“ (CT) gesendet werden. Solche Pakete werden weder quittiert noch neu übertragen.
Das RapidIO-Protokoll definiert alle Aspekte der Kommunikation – von der elektrischen Spezifikation bis hin zu Paketformaten, Neuübertragung und Flusskontrolle.
RapidIO ist wegen der Komplexität des Protokolls möglicherweise kein attraktiver Kandidat für eine einfache Punkt-zu-Punkt-Verbindung zwischen zwei FPGAs. Besser eignet sich RapidIO als Verbindungstechnik zwischen mehreren FPGAs über einen Switch, insbesondere wenn PCIe wegen der benötigten CPU im System nicht geeignet ist.
Zusammenfassung
Es wurden mehrere Protokolle zur Übertragung von Anwendungsdaten vorgestellt. Jedes Protokoll bietet unterschiedliche Methoden, um den Datentransport durchzuführen, den Datenfluss zu steuern und auf Bitfehler zu reagieren (falls überhaupt). Das richtige Protokoll für eine Anwendung findet man, indem man die vom Protokoll gebotenen Funktionen gegen den Aufwand abwägt, der für die Implementierung der fehlenden Teile in der Anwendungslogik nötig ist.
Damit ist die zweite Seite in dieser Serie über MGTs abgeschlossen. Die nächste Seite stellt einige Kodierungsverfahren vor, die bei MGTs häufig eingesetzt werden.