UDP-Server-Client ( verlorene Pakete )



  • @MFK - Da hast du 'leider' völlig recht. Weißt du eine Lösung?

    Leider ist TCP für mein Problem viel zu aufwändig und langsam, da ich mehrere Millionen-Daten verschicken muss und das in Blitzgeschwindigkeit 😉



  • Dieser Thread wurde von Moderator/in HumeSikkins aus dem Forum C++ in das Forum Rund um die Programmierung verschoben.

    Im Zweifelsfall bitte auch folgende Hinweise beachten:
    C/C++ Forum :: FAQ - Sonstiges :: Wohin mit meiner Frage?

    Dieses Posting wurde automatisch erzeugt.



  • MFK schrieb:

    net schrieb:

    die gegenstelle weiss dann, dass sie als nächstes das paket mit zählerwert = vorheriger_wert+1 zu erwarten hat.

    Da bei UDP auch nicht sichergestellt ist, dass die Pakete in derselben Reihenfolge eintreffen, in der sie verschickt wurden, ist das so nicht ganz richtig.

    das macht keinen unterschied ob was fehlt oder vertauscht wurde. angenommen der sender sendet 1,2,3,4,5 und der empfänger bekommt 1,2,4,3,5. wenn der empfänger 4 bekommt sagt der dem sender er will aber 3 haben und ignoriert weitere pakete bis 3 kommt. der sender fängt also bei 3 wieder an d.h. er muss 3,4,5 nochmal senden.



  • Da kann er aber gleich TCP nehmen. UDP ist ja nur so schnell weil nicht kontrolliert wird ob angekommen und in welcher Reihenfolge.
    Wenn er das dann aber erst wieder implementiert hat er ein langsameres TCP.



  • Petommy schrieb:

    @MFK - Da hast du 'leider' völlig recht. Weißt du eine Lösung?

    Leider ist TCP für mein Problem viel zu aufwändig und langsam, da ich mehrere Millionen-Daten verschicken muss und das in Blitzgeschwindigkeit 😉

    Und was ist an TCP so aufwändig?

    RICHTIG, die Datenfluß-Kontrolle und Verbindungssteuerung.

    Klar, da ist noch ein bißchen zusätzlicher Overhead durch den längeren Header, ABER: Bei TCP würde der TCP/IP-Stack für dich diese Überprüfungen erledigen. Und der ist sicherlich optimiert bis zum Äußersten. Ich glaube nicht, daß du eine gleichartige Funktionalität implementieren kannst, ohne mehr Throughput zu verlieren, als der TCP/IP-Stack.

    Nochmal: UDP ist schneller als TCP weil es KEINE GARANTIEN bezüglich Empfang oder Eingangsreihenfolge der gesendeten Pakete macht.

    Wenn du diese Garantie für ALLE Pakete machen musst, dann verwende TCP.

    Wenn du diese Garantie für einen GROßTEIL der Pakete machen musst, baue eine zusätzliche TCP-Verbindung auf und nutze diese nach Bedarf.

    Wenn du diese Garantie für einen KLEINEN Teil der Pakete machen musst, implementiere eine zusätzliche Paketart, die eine Flußkontrolle und Verbindungssteuerung beinhaltet.

    Hinweis: Du kannst natürlich dann Garantien nur innerhalb der der Flußkontrolle unterliegenden Pakete machen. Also "Paket 2 (via TCP) kommt nach Paket 1 (via TCP) an", NICHT "Paket 2 (UDP) kommt nach Paket 1 (TCP)" an.

    Zusammenfassung: Flußkontrolle und Verbindungssteuerung kosten Performance. Diese Eigenschaften sind im TCP-Protokoll nahezu perfekt umgesetzt, so daß eine Neuimplementierung unter UDP wahrscheinlich deutlich langsamer arbeiten wird als eine TCP-Verbindung.



  • Naja es ist immer noch ein Performance-Unterschied zwischen einer UDP-Verbindung die man selbst absichert und einer einfachen TCP-Verbindung.
    Die Überlast-Kontrolle die bei TCP zusätzlich noch dabei ist (und damit auch der TCP Slowstart), kostet ja auch noch mal was an Performance, was man vermeiden kann wenn man ein sichere UDP-Verbindung implementiert.

    Musst du halt selbst abwägen. Viel mehr Geschwindigkeit wirst du dadurch auch nicht erreichen, deshalb ist es wohl wirklich einfacher, wie Sid2k6 schon sagte, einfach TCP zu benutzen.
    Ich musste als Übung mal ein einfaches auf UDP basierndes Protkoll in Java entwickeln, welches Zuverlässigkeit bietet um z.B. Dateien von einem Server runterzuladen. Und das finde zumindest ich nicht unbedingt trivial, sprich du wirst mit sowas doch etwas an Zeit verbingen nehme ich mal an 😉



  • Vielen Dank für die wirklich guten Antworten.

    Es handelt sich um sehr wichtige Daten und zwar um einige Millionen ( 100 Million ca. ).

    Muss mir das ganze mal durch den Kopf gehen lassen.. meld mich wieder.



  • Moin.

    Weisst du, die Datenmenge könne wir daraus nicht wirklich erkennen.

    Aber gut, rechnen wir mal:

    100 Millionen = 100 000 000. Gehen wir davon aus, daß Int16 übertragen werden (haha.):

    200 000 000 Byte = 195312.5 KB ~= 190.7MB.
    (bzw 1 600 000 000 Bit)

    Bei Byte: ~95 MB / Int32: ~381 MB

    Verbindung: 100 MBit/s = 100 000 000 Bit / s

    (Sehr) theoretische Übertragungsdauer für die o.g. Datenmenge: (8) 16 (32) Sekunden.

    Praktisch dauert es aufgrund der nicht berücksichtigten Header, MTU und anderer Eigenheiten deutlich länger, bis die Datei übertragen ist (ich schätze 30 Sekunden für die "Int16"-Version).

    Und da soll die halbe Sekunde für die Flußsteuerung noch ins Gewicht fallen?



  • Also bei so ner Datenmenge stellt sich echt die Frage ob das dann so ins Gewicht fällt... da würd ich wohl auch lieber gleich TCP nehmen und mir das Leben einfacher machen. Vielleicht kannst du ja auch anderen Stellen irgendwie durch Komprimierung oder so an Performanz gewinnen.
    Und so wie sich das anhört hast du ja keine Multimedia-Streaming Anwendung oder so...



  • Nochmals danke.

    Also nein, es ist keine Multimedia anwendung, sondern ein Personenserver.

    Habe einen Client zum erfassen dieser Personen und einen Server der diese Personen speichert. Weitere Funktionen wie das Suchen einer Person erledigt auch der Server. 100 Millionen Personen deshalb, weil D-Land allein schon 60 Million hat und wir europaweit arbeiten. Also die 100 sind nur ungefähr das was ich brauch ^^.

    Problem ist nun, wenn der Client eine Anfrage an den Server sendet und die Person Müller sucht, so kommt es vor das die Person Müller mehrere tausend male gefunden wird und vom Server zum Client geschickt wird. Anforderung ist, dass diese Aktion keine Sekunde dauert. Blöd wäre natürlich wenn genau der Müller den wir suchen verloren gehen würde wegen dem unsicheren UDP-Protokoll.

    Ich hoffe ich konnte das verständlich erklären, damit ihr versteht warum ich am grübbeln bin ...



  • Und warum musst du da grübeln? Ist doch klar das UDP hier ganz falsch ist.



  • Ja also das verstehe ich auch nicht...
    Selbst wenn es z.B. die Person Müller genau 1000 mal gibt, soo schlimm wäre das doch nun auch nicht. Ein Datensatz zu einer Person wird ja nun auch nicht ellenlang sein, vielleicht 2-3 Kb ? Das wären zwar schon ca 2-3 Mb, aber in Zeiten von DSL sollte das ja nun auch nicht soo das Problem darstellen.
    Ausserdem, warum präzisierst du nicht einfach die Suchanfragen ? Z.B. Herr Müller aus Bochum oder sowas, dann kriegst du ja auch nur noch nen Bruchteil deiner Datensätze, und das oben geschilderte Szenario bleibt eher ein Extremfall.
    Hast du auch mal dran gedacht, dass die Datenbankabfrage für solche Personen auch einen großen Teil der Zeit in Anspruch nimmt ?
    Also da an der Verbindung mit UDP/TCP anzusetzen halte ich für ziemlich daneben...



  • Ich hätte das ganze ebenfalls mit TCP gehandelt und die Zig-Millionen Daten nicht in Multimaps gepackt, aber Chef will es so. Datenbankabfrage sowie TCP sind zu langsam sagt er. Hmm...



  • Petommy schrieb:

    Ich hätte das ganze ebenfalls mit TCP gehandelt und die Zig-Millionen Daten nicht in Multimaps gepackt, aber Chef will es so. Datenbankabfrage sowie TCP sind zu langsam sagt er. Hmm...

    Was meinst du wie viele Inteligente Menschen schon versucht haben TCP sicher(Im Bezug auf Verluste) UND schnell zu machen. Da wirst du es schwer haben das mit einer eigenen Implementierung zu überbieten.

    Flußsteuerung verlamsamt die Verbindung nicht wenn man bedenkt was das Neusenden von Paketen in Anspruch nimmt, wenn der Empfänger überlastet wird und eingehende Pakete einfach verwirft.

    Mit UDP wirst du dich mit folgenden Problemen herumschlagen müssen:
    1. verlohrene Pakete
    2. Überlast des Netzes und möglicherweise viele verlorene Pakete (keine Überlastkontrolle)
    3. Überflutung des Empfängers mit Paketen und Verlust dieser (keine Flusskontrolle)
    4. Pakete in Falscher Reihenfolge
    5. Was viele vergessen: Pakete können dubliziert werden und kommen mehrfach an.

    Und das allerfieseste:
    6. Pakete können ankommen von dem Computer der vorher die dynamische IP Adresse des Kommunikationsparters hatte (Auch noch viel später). Ist sehr lustig, wenn man nicht damit gerechnet hat, da diese ein "unerwartetes Format" haben können (Nicht die Daten die du erwartest), aber laut Prüfung ja nicht beschädigt sind und die zu erwartende IP Adresse tragen und wenn du sehr viel Pech hast auch noch den passenden Port... .

    Worauf du dich verlassen kannst: Ankommende Pakete sind unbeschädigt (mit seeeeeehr großer Wahrscheinlichkeit, aber nicht 100% ig aber TCP erkennt Fehler ja auch nur zu einer seeeehr großen Wahrscheinlichkeit und nicht 100% ig), da auch UDP Kontrollen durchführt.(Wenn du das nicht abschaltest)

    Das kannste immer mit der Post vergleichen bei der auch alle Fehler (Bis auf die Dublikate) auftreten können. 😃



  • Also nochmal Danke für die vielen Antworten.

    Ich habe mich nun dafür entschieden ( und auch mein Chef davon überzeugt ) ein Mix zwischen UDP u. TCP zu machen. Bei wichtigen Daten setze ich TCP ein und bei unwichtigen Daten UDP. Ist sowei implementiert und funktioniert auch wunderbar. Jetzt kann ich mir die ganzen Prüfungsroutinen sparen und muss nicht mehr auf verlorene Pakete achten...


Anmelden zum Antworten