Hi, ich habe hier ein USB-Gerät, welches als CDC-Device arbeitet (d.h. es taucht im System als COMx bzw. /dev/ttyACMx auf). Dieses Gerät erwartet Datenpakete, welche immer nur aus ein paar Bytes bestehen. Wenn solche Daten per Ethernet übertragen werden, dann ist es sinnvoll, diese zu sammeln und erst ab einer bestimmten Paketgröße zu senden. Wie ist das jetzt bei so einem USB-CDC-Device? Ist es da - wie bei einer echten seriellen Schnittstellenhardware - egal ob ich die Daten jeweils einzeln absende oder ist es wie bei Ethernet schneller, den Krempel zu sammeln und immer größere Pakete auf einen Rutsch durchzuschicken? Ich kann es leider nicht mal eben so ausprobieren, da die entsprechenden Änderungen in der Software doch etwas größer sind, deswegen die Frage. Danke!
Hallo, USB überträgt die Daten in Pakete. "Im Vergleich zu den früheren Lösungen bietet USB deutlich höhere Datenübertragungsraten. Die Daten werden jedoch in Paketen übertragen, für manche zeitkritische Anwendungen ist es deshalb weniger geeignet – etwa bei mit nur wenigen Bytes belegten Paketen, die die Übertragungsrate senken, oder wenn das Sammeln von Bytes zum Füllen eines Pakets die Übertragung verzögern würde." [https://de.wikipedia.org/wiki/Universal_Serial_Bus#Einsatzgebiete_des_USB] Mit freundlichen Grüßen Guido
OK...gibt's eine Möglichkeit herauszufinden, wie große diese Pakete sind? Bei meiner Netzwerkschnittstelle weiß ich, dass die Gegenseite mit 1460 Nutzlast arbeitet.
Die Frage ist was du dir davon erhoffst? Durch das Sammeln von mehr Daten für ein Paket steigt die Latenz noch weiter. Dafür wird der Overhead kleiner. Was ist das Ziel der Aktion?
Hallo, SpacerX schrieb: > OK...gibt's eine Möglichkeit herauszufinden, wie große diese Pakete > sind? Bei meiner Netzwerkschnittstelle weiß ich, dass die Gegenseite mit > 1460 Nutzlast arbeitet. da kann ich Dir leider nicht weiterhelfen. Hier http://www.beyondlogic.org/usbnutshell/usb3.shtml#USBPacketTypes steht einiges, vielleicht hilft Dir dies weiter. Mit freundlichen Grüßen Guido
Peter II schrieb: > Durch das Sammeln von mehr Daten für ein Paket steigt die Latenz noch > weiter. Dafür wird der Overhead kleiner. Genau das ist mein Ziel: durch geringeren Overhead mehr Daten in kürzerer Zeit übertragen. Die Latenz ist dabei zweitrangig.
SpacerX schrieb: > Peter II schrieb: >> Durch das Sammeln von mehr Daten für ein Paket steigt die Latenz noch >> weiter. Dafür wird der Overhead kleiner. > > Genau das ist mein Ziel: durch geringeren Overhead mehr Daten in > kürzerer Zeit übertragen. Die Latenz ist dabei zweitrangig. Unter der Annahme, dass dein USB Bus bisher nicht voll ausgelastet ist, erhöht das Sammeln nicht den Durchsatz. Du hast höchstens weniger USB Interrupte auf deinem Gerät und häufig lassen sich die gesammelten Daten leichter verarbeiten.
Für Bulk Endpoints ist die Paketgröße im Deskriptor angegeben. Meist sind das 512 Byte. Soweit ich das überblicke wird der Treiber buffern, wenn du schnell genug Daten nachschiebst. Im Zweifel probier es aus (Wireshark hilft). Natürlich ist es trotzdem effizienter, wenn du nicht für jedes Byte einzeln write() aufrufst.
Sven B. schrieb: > Für Bulk Endpoints ist die Paketgröße im Deskriptor angegeben. Meist > sind das 512 Byte. Bei CDC würde ich eher 64 Byte erwarten, das ist auch das Maximum für Full Speed. Allerdings lohnen sich eventuell auch größere Transfers. SpacerX schrieb: > Wie ist das jetzt bei so einem USB-CDC-Device? Ist es da - wie bei einer > echten seriellen Schnittstellenhardware - egal ob ich die Daten jeweils > einzeln absende oder ist es wie bei Ethernet schneller, den Krempel zu > sammeln und immer größere Pakete auf einen Rutsch durchzuschicken? Problem: Es ist sowohl vom Host als auch vom Device abhängig. Zwar erhöhen größere Transfers in aller Regel den Durchsatz, aber man sollte trotzdem immer mit dem konkreten Device testen - es könnte sich ja an großen Paketen "verschlucken" - Pufferüberlauf.
Die Durchsatzerhöhung kommt dadurch zustande, dass man der Bulktransfer eine größere Datenmenge "in einem Rutsch" übertragen kann. Hat man diese Datenmenge jedoch nicht, erhöht dies die Latenz. Die frei werdende Kapazität auf dem USB Bus steht anderen Anwendungen zur Verfügung. Der eigene Gesamt-Durchsatz wird nicht erhöht, sondern statt mehrerer kleiner Bulktransfers, von denen jede ms einer angestoßen werden kann wird ein großer nach vielen ms durchgeführt. Speziell beobachte ich dies bei Anwendungen, welche eigentlich für die RS232 geschrieben wurden und nun mit der virtuellen COM Schnittstelle genutzt werden.
>Genau das ist mein Ziel: durch geringeren Overhead mehr Daten in
kürzerer Zeit übertragen. Die Latenz ist dabei zweitrangig.
Das geht so nicht. Wenn man groessere Mengen zB 1MByte + uebertragen
will, ist ueblicherweise die Latenz das Problem, speziell wenn mit
Bestaetigungen gearbeitet wird. Wenn also ueber die serielle
Schnittstelle viele Daten schnell uebertragen werden sollen. muss die
Blockgroesse rauf, aber vom originalen Protokoll. Die Blockgroesse kann
man adaptiv gestalten, dass die Blocke immer laenger werden solange
keine Retries erfolgen muessen.
Dabei sollte man die Restriktionen beachten. Ein 16bit CRC kann nur
2^16bit schuetzen. Also 8kbyte. Bei groesseren Bloecken muss auf einen
laengeren CRC gewechselt werden. Allenfalls verwendet man auch
Feedforward Error Correction, dh. einen ECC.
Des weiteren kann man das ACK, dh die Bestaetigung, verzoegern, muss
dafuer aber Zwischenspeichern. Und muss das kaputte Packet nach dem
Retry noch einfuegen koennen.
So erreicht man dann maximalen Durchsatz, kann den Kanal buendig
belegen.
Oder D. schrieb: > Ein 16bit CRC kann nur 2^16bit schuetzen. Also 8kbyte. Selten so wirres Zeugs gelesen. Erstmal ist der CRC unabhängig von der Anzahl der Bytes über die gerechnet wird - bei 16 Bit CRC wird halt einer von 64k (Mehrbit-) Fehlern nicht erkannt. Außerdem sind 2^16 = 65536 und nicht nur 8192.
Jim M. schrieb: > Außerdem sind 2^16 = 65536 und nicht nur 8192. Genau hinsehen. 8192 Byte sind 2^16 Bit.
> es taucht im System als COMx bzw. /dev/ttyACMx
Auf der PC-Seite musst du dir gar keine Gedanken machen. Das
Betriebssystem kümmert sich selbst um die ideale Paketgröße. Die
USB-Treiber und das TCP/IP über dem Ethernet erzeugen selbst die
optimale Paketgröße aus dem Datenstrom.
Ganz anders sieht es aus, wenn du das Device baust. Hier musst du dir
Gedanken über die Puffergröße machen. Du rechnest aus, 512 Byte wären
ideal, aber dein MC hat gar nicht so viel RAM.
Noch einer schrieb: > Auf der PC-Seite musst du dir gar keine Gedanken machen. Das > Betriebssystem kümmert sich selbst um die ideale Paketgröße. nein. Woher soll es denn wissen ob man niedrige Latenz oder hohen Durchsatz will? Die ideale größe ist aber davon abhängig. Nicht umsonst gibt es Flags wie TCP_NODELAY.
Schickt man ein einzelnes Byte über den USB-Bus an ein CDC-Device, hat man (mindestens) 8 Bytes Overhead. Jedem Nutzdatenpaket muß ein Setup-Paket (das sagt, welches Gerät auf dem Bus man meint und was man von dem erwartet) vorausgehen. Und das ist nun mal 8 Bytes lang. Den "optimalen" Datendurchsatz dürfte man bei Full-Speed mit 64 Bytes Nutzdaten und bei High-Speed mit 512 Bytes Nutzdaten erreichen (das sind die jeweils maximalen Paketgrößen für Bulk-Transfers). Das setzt natürlich voraus, daß der Treiber auch wirklich Bulk-Transfers macht.
:
Bearbeitet durch User
Peter II schrieb: > Die ideale größe ist aber davon abhängig. Nicht umsonst gibt es Flags > wie TCP_NODELAY. Das gibt's hauptsächlich, damit man mit TCP auch irgendwie noch Dinge hinkriegt, für die es eigentlich nicht geeignet ist.
Noch einer schrieb: > Ganz anders sieht es aus, wenn du das Device baust. Hier musst du dir > Gedanken über die Puffergröße machen. Du rechnest aus, 512 Byte wären > ideal, aber dein MC hat gar nicht so viel RAM. Die USB-Endpoints haben ihre eigenen physikalischen Speicherbereiche zum Senden und Empfangen. Controller mit integriertem USB 2.0 haben mehr als genug RAM um 512 Byte irgendwo hin zu senden.
Was für ein wirres Durcheinander. Um das mal auf den Punkt zu bringen: Guido C hat recht, alles andere in diesem Thread reicht dann von "genau so richtig" bis "völliger Quatsch". Ich habe den Transfer jetzt hostseitig umgestellt. Statt meine 3 bis 10 Byte großen Kommandos jedes mal sofort auf den Weg zu bringen, sammele ich die Daten jetzt und sende sie erst ab, wenn mindestens 1024 Bytes zusammen gekommen sind. Das dann abgesendete Datenpaket ist ebenfalls immer genau 1024 Bytes groß und damit in jedem Fall ein ganzzahliges Vielfaches der in Frage kommenden Puffergrößen. Ergebnis: bei großen Datentransfers ist die Übertragung um ca. den Faktor 10 schneller (nicht exakt gemessen, nur grob mit vorherigen Transferzeiten verglichen). Also findet bei CDC-Devices eine paketweise Übertragung mit offensichtlich fester Paketgröße statt.
Rufus Τ. F. schrieb: > Genau hinsehen. 8192 Byte sind 2^16 Bit. Ja, aber vermutlich nur im inneren eines schwarzen Loches oder nahe der Lichtgeschwindigkeit. Ansonsten sind und bleiben 2^16 = 65535.
Ja, Bit und Byte kann man schon schwer auseinander halten. Bei uns hat ein Byte aber meistens noch 8 Bit.
SpacerX schrieb: > OK...gibt's eine Möglichkeit herauszufinden, wie große diese Pakete > sind? Natürlich. Man schaut einfach in den Standard, da steht das doch glatt schwarz auf weiss drinne. Tipp: CDC benutzt Bulk-Transfers für den Payload, also schaut man nach der maximalen Größe von Bulk-Transfers. Und diese hängt nun wiederum vom "Speed-Grade" des Gerätes ab. Auch das steht in dem Standard. Man muß ihn nur einfach mal lesen... Du musst also zuerst herausfinden, ob es sich um ein Full-, High- oder Super- oder Super+- Speed-Gerät handelt (Low-Speed-Geräten sind Bulk-Transfers aus unerfindlichen Gründen vom Standard her grundsätzlich nicht erlaubt). Allerdings beschränken sich real existierende CDC-Geräte wohl in aller Regel auf Full-Speed. In Einzelfällen mögen auch High-Speed-CDC-Geräte vorkommen. Mir persönlich ist allerdings nie eins über den Weg gelaufen. Soll heissen: du kannst Full-Speed mehr oder weniger als gegeben für ein CDC-Gerät ansehen...
c-hater schrieb: > Allerdings beschränken sich real existierende CDC-Geräte wohl in aller > Regel auf Full-Speed. In Einzelfällen mögen auch High-Speed-CDC-Geräte > vorkommen. Mir persönlich ist allerdings nie eins über den Weg gelaufen. > Soll heissen: du kannst Full-Speed mehr oder weniger als gegeben für ein > CDC-Gerät ansehen... Da bei USB HS CDC aller 125µs ein Transfer ausgelöst werden kann, bekommt man hier bei wenig Daten die Latenz besser in den Griff und das Interface verhält sich ähnlicher zu einer realen RS232. Aber dies war dem TO nicht so wichtig.
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.