2. Transportprotokolle

2.1. Überblick

Nachdem Sie sich im Kapitel 1 mit den Protokollen der Internet-Schicht (Network Layer oder Internet Layer) beschäftigt haben, wollen wir uns im Kapitel 2 den Transportprotokollen, d.h. den Protokollen der zwischen der Internet- und der Anwendungsschicht (Application Layer) gelegenen Transportschicht (Transport Layer) zuwenden. Deren Einordnung in das Schichtenmodell des Internet zeigt die folgende Abbildung:

Auf der Ebene der Internet-Schicht werden die Kommunikationspartner durch IP-Adressen identifiziert. Eine solche IP-Adresse ist dabei eindeutig einem Netzwerk-Interface eines Computers zugeordnet. Damit ist es möglich, Daten zwischen verschiedenen Rechnern, nicht aber gezielt zwischen den auf ihnen ausgeführten Programmen auszutauschen.

Eine wesentliche Aufgabe der Transportschicht besteht deshalb darin, separate Kommunikationsbeziehungen zwischen potentiell auf verschiedenen Computern ablaufenden Anwendungsprogrammen zu ermöglichen, weshalb auch der Begriff End-zu-End-Kommunikation verwendet wird. Zur Unterscheidung der einzelnen Programme einer Maschine dienen Portnummern. Durch die Angabe eines aus IP-Adresse und Portnummer bestehenden Paares läßt sich daher gezielt ein gewünschtes Programm bzw. der von ihm erbrachte Dienst auf einem bestimmten Rechner ansprechen.

Zu den weiteren Aufgaben der Transportschicht gehören die Steuerung des Informationsflusses sowie die Gewährleistung einer zuverlässigen (reliable) Kommunikation, die zwar auf der ungesicherten Zustellung von IP-Datagrammen (Best-effort Delivery) basiert, bei der Fehler jedoch bemerkt und nach Möglichkeit durch geeignete Maßnahmen wie Bestätigungen und Sendewiederholungen automatisch behoben werden. Die vom Sender abgeschickten Daten treffen somit unverfälscht und in der richtigen Reihenfolge beim Empfänger ein.

Je nach Anwendungszweck kommen in der Transportschicht verschiedene Protokolle zum Einsatz. Die mit Abstand wichtigsten Transportprotokolle des Internet sind

Die herausragende Bedeutung von TCP kommt auch darin zum Ausdruck, daß die Bezeichnung TCP/IP häufig als Synonym für die gesamte Protokoll-Familie des Internet steht.

Sowohl TCP als auch UDP werden wir jeweils in einem eigenen Kapitel detaillierter untersuchen. Der nachfolgende Überblick über wesentliche Eigenschaften dieser beiden Protokolle soll helfen, die vielen Details richtig in das Gesamtsystem einordnen zu können.

TCP arbeitet verbindungsorientiert und bietet den Anwendungen jeweils einen zuverlässigen, innerlich aber nicht strukturierten Bytestrom, über den sie mit einer anderen Anwendung kommunizieren können.

Die durch TCP hergestellten Verbindungen werden mitunter auch als Virtual Circuits bezeichnet. Das Attribut "virtuell" drückt aus, daß die Transportschicht den Anwendungen lediglich den Eindruck vermittelt, ihnen würde ein eigens für sie geschalteter Kanal zur Verfügung stehen. In Wirklichkeit erfolgt der reale Datentransport durch ein paketvermitteltes IP-Netz, das keine Kanäle kennt, sondern Datagramme verschickt (ohne deren Eintreffen beim Empfänger zu garantieren).

Da TCP die Zuverlässigkeit der Kommunikation bereits auf der Ebene der Transportschicht garantiert, braucht sich die Anwendungsschicht nicht mehr um die zahlreichen Einzelheiten der Fehlererkennung und -behandlung zu kümmern. Es genügt, die dazu benötigten, vielfach nicht gerade trivialen Algorithmen genau einmal solide zu implementieren. Dann können alle Anwendungen darauf zurückgreifen, was zur Verringerung von Code-Größe und Komplexität der einzelnen Anwendungen, zu einer deutlichen Entlastung des Anwendungs-Programmierers sowie zu einer höheren Robustheit der Software beitragen dürfte.

Im Gegensatz zu TCP ist UDP genau wie IP ein verbindungsloses Protokoll, das keinerlei Garantien dafür gibt, daß die in Form von Datagrammen übertragenen Informationen auch tatsächlich beim Empfänger ankommen. Wird Zuverlässigkeit benötigt, so ist sie durch die Anwendung selbst zu organisieren.

UDP bietet aus Sicht des Anwenders im Vergleich zu IP zwei Zusätze:

Es sei hier noch einmal daran erinnert, daß sich die Prüfsumme des IP-Kopfes nur auf den Kopf selbst, nicht jedoch auf die Daten bezieht.

Die Auswahl eines geeigneten Transportprotokolls hängt von der konkreten Situation ab. Douglas Comer und David Stevens empfehlen im dritten Band des "Klassikers" Internetworking with TCP/IP, der den Untertitel Client-Server Programming and Applications trägt, bei der Entwicklung von Client-Server-Systemen nach Möglichkeit immer TCP zu verwenden. UDP sollte ihrer Meinung nach nur in den folgenden drei Fällen zur Anwendung kommen:

Viele bekannte Anwendungsprotokolle (z.B. Telnet, FTP, Secure Shell und SMTP) nutzen tatsächlich ausschließlich TCP. Sie profitieren in hohem Maße von dessen verbindungsorientiertem Charakter sowie der garantierten Zuverlässigkeit.

Im Vergleich zu dem sehr simplen UDP ist TCP allerdings ein recht komplexes Protokoll, das einen relativ hohen Implementationsaufwand erfordert und einen zusätzlichen Overhead bei einer Kommunikation verursacht. Dieser Mehraufwand ist nicht in allen Fällen erwünscht bzw. vertretbar. Daher kommt in bestimmten Situationen ganz bewußt UDP zum Einsatz. Neben dem geringen Overhead kann auch die Verbindungs- und Zustandslosigkeit für die Verwendung von UDP ausschlaggebend sein, da sie die Realisierung robuster Systeme vereinfacht. Ein Beispiel soll das verdeutlichen.

Nehmen wir an, die Bilder einer an einen PC angeschlossenen Kamera sollen per WWW zugänglich gemacht werden, wobei sie keinen ernsten Zweck erfüllen müssen, sondern mehr der Unterhaltung der Web-Surfer dienen mögen. WWW-Server und PC seien zwei separate, über ein LAN (Local Area Network) verbundene Rechner. Dann können wir bei der Implementierung folgende Strategie anwenden:

Stürzt einer der beiden Server ab, so ist nach dessen Neustart keine Synchronisation zwischen PC und WWW-Server erforderlich, da das von beiden verwendete Protokoll absolut zustandslos arbeitet.

Hätten wir uns nicht für UDP, sondern für TCP entschieden, wäre deutlich mehr zu tun. TCP ist im Gegensatz zu UDP zustandsbehaftet. Somit bewirkt der Crash eines Partners, daß alle seine TCP-Verbindungen zerstört werden. Wir müssen diese Situation im Programm erkennen und anschließend die Verbindung erneut aufbauen. Da es bei UDP keine Verbindungen gibt, können sie logischerweise auch nicht zusammenbrechen.

In unserem Kamera-Beispiel stellt UDP nicht nur wegen der Robustheit der darauf aufbauenden Lösung eine gute Wahl dar. Die Fehlerbehandlungsmechanismen des TCP werden von uns de facto nicht benötigt, da in einem LAN in der Regel sehr geringe Datenverluste eintreten. Sofern einzelne Pakete nicht beim WWW-Server ankommen, entsteht dadurch kein Problem. Dann muß eben der Web-Surfer etwas länger mit einem alten Bild vorliebnehmen.

Douglas Comer weist im ersten Band von Internetworking with TCP/IP darauf hin, daß viele auf UDP basierende Anwendungen in einem größeren Netz scheitern, da sie in einem LAN entwickelt und getestet wurden, allerdings dort ganz andere Bedingungen als in einem WAN (Wide Area Network - Fernnetz) gelten. Im Gegensatz zur lokalen Umgebung ist im Internet immer damit zu rechnen, daß Datagramme beschädigt, dupliziert, umgeordnet oder vernichtet werden.

Durch die Versendung eines kompletten Bildes in einem eigenen UDP-Datagramm kann der Empfänger sehr einfach erkennen, welche Bytes zu einem Bild gehören. Das ist bei dem durch TCP organisierten unstrukturierten Bytestrom nicht so einfach möglich. Für eine geeignete Markierung der Bildgrenzen ist der Anwender selbst verantwortlich. Das ist nicht sonderlich kompliziert, muß aber programmiert werden. Eine Möglichkeit besteht darin, vor den eigentlichen Bilddaten deren Byteanzahl zu senden.

Da TCP aber keine Kenntnis von unseren anwendungsspezifischen Markierungen hat, kann es auch nicht sicherstellen, daß alle zu einem Bild gehörenden Daten geschlossen an die Anwendung weitergereicht werden. Vielmehr muß der Klient davon ausgehen, daß er die Daten portionsweise erhält, so daß er selbst für das Zusammensetzen der einzelnen Bilder verantwortlich ist. Im Gegensatz dazu kommt ein UDP-Datagramm entweder geschlossen oder überhaupt nicht bei einem Programm an.

Es gibt mehrere ernsthafte Netzanwendungen, die aus verschiedenen Gründen UDP statt TCP verwenden. Mit DNS hatten Sie in Kapitel 1B bereits einen derartigen Dienst kennengelernt. Hier folgen weitere Beispiele:

Bisher haben wir schon allerhand zu den Protokollen und Diensten, aber noch kein Wort zur praktischen Realisierung gesagt. Für einen potentiellen Programmierer von Netzwerk-Anwendungen stellt sich sicher die Frage, welche Dienste ihm seitens des Systems angeboten werden und wie er darauf aus seiner Anwendung heraus zugreifen kann.

In modernen Betriebssystemen ist eine Implementierung von IP, TCP und UDP bereits im Kern enthalten. Den Anwendungen steht eine Programmierschnittstelle (Application Programming Interface, kurz API) zur Verfügung, die es ihnen relativ leicht ermöglicht, wahlweise unter Verwendung von TCP oder UDP mit anderen Anwendungen, die auf dem lokalen oder einem entfernten Rechner laufen, zu kommunizieren.

Eine sehr weit verbreitete API ist die Socket-Schnittstelle, die ca. im Jahre 1982 mit dem damals aktuellen Berkeley UNIX 4.1cBSD eingeführt und später auf viele andere Systeme übernommen wurde. Über Sockets kann eine Anwendung auf die TCP/IP-Implementierung des Kerns zugreifen, wobei sie in der Mehrzahl der Fälle ein Transportprotokoll, also TCP oder UDP, nutzt.

Je nach System besteht daneben die Möglichkeit, über spezielle Sockets auch direkt die Dienste der IP- oder gar der Subnetz-Schicht in Anspruch zu nehmen, wobei diese für die meisten Anwender geringe bis gar keine Relevanz besitzen. Sie sind vor allem für System-Werkzeuge wie ping oder tcpdump interessant, die Sie schon kennengelernt haben.

Neben den beiden klassischen Transportprotokollen TCP und UDP wollen wir mit RTP, dem Real-time Transport Protocol, auch noch eine relativ neue Entwicklung betrachten, die speziell auf die Unterstützung von Echtzeit-Anwendungen, wie wir sie z.B. im Video- und Audio-Bereich vorfinden, abzielt.

Der Transport von Echtzeit-Daten im Internet spielte zu der Zeit, als IP, TCP und UDP entstanden, allein schon wegen der damals sehr knapp bemessenen Hardware-Ressourcen keine Rolle. Insofern ist es nicht verwunderlich, daß für neuartige Anwendungen auch neue Protokolle gesucht werden, die den entstandenen Bedürfnissen besser Rechnung tragen als die bisher verfügbaren.


Literaturhinweise:

Als besonders empfehlenswert erscheinen aus unserer Sicht hauptsächlich wieder die bereits im Kapitel 1A als Grundlagenwerke angegebenen Bücher von Stevens und Comer:

Beide diskutieren in gut verständlicher Form die Grundprinzipien der zentralen Internet-Protokolle sowie viele Details und vermitteln so fundierte Kenntnisse. Der Einstieg in die Thematik ist mit ihrer Hilfe wesentlich einfacher als durch Lesen von RFCs und verschiedensten Papers.

Comers stellt die Protokolle selbst, nicht deren Implementierungen in den Vordergrund. Stevens erörtert dagegen theoretische Fragen vielfach am Beispiel konkreter Kommunikationsabläufe, wobei er für seine Experimente verschiedene UNIX-Derivate, das von ihm stammende Testwerkzeug sock sowie den Netzwerk-Monitor tcpdump einsetzt.

Praktisch relevante Internet-Protokolle sind in der Regel in Form von RFCs bzw. Internet Drafts beschrieben. Diese Dokumente finden Sie auf vielen öffentlich zugänglichen FTP-Servern, u.a. auch in Chemnitz. Eine Übersicht über alle RFCs gibt die Datei rfc-index.txt. Im RFC 2400 beschreiben John Postel und Joyce K. Reynolds die aktuelle Situation der Standardisierung der im Internet genutzten Protokolle.

Die offiziellen Standards für UDP und TCP finden sich in den folgenden beiden Dokumenten:

Wichtige Ergänzungen und Klarstellungen sowie mehrere Korrekturen zu diesen zwei RFCs sind im enthalten.

Die Texte von Kapitel 2 beziehen sich des weiteren auf folgende RFCs:

Das klassische Paper Congestion Avoidance and Control [ftp://ftp.ee.lbl.gov/papers/congavoid.ps.Z] von Van Jacobson und Michael J. Karels beschreibt mehrere wichtige Algorithmen für TCP, u.a. Slow-Start sowie Congestion Avoidance.

Richard Stevens dokumentiert im RFC 2001 die vier Algorithmen Slow-Start, Congestion Avoidance, Fast Retransmit und Fast Recovery, die Bestandteil moderner TCP-Implementierungen sind und in der Regel durch einen einzigen, kombinierten Algorithmus realisiert werden.

Details zu Karn's Algorithm finden sich im Paper Improving Round-Trip Time Estimates in Reliable Transport Protocols [ftp://ftp.sics.se/users/craig/karn-partridge.ps] von Phil Karn und Craig Partridge.

Denjenigen, die sich speziell für die Protokoll-Implementierungen interessieren, seien die C-Quelltexte der vielen frei verfügbaren Systeme (z.B. Linux und FreeBSD) bzw. Software-Pakete (z.B. ping, traceroute und tcpdump) empfohlen. Dokumentierte C-Quellen der Basis-Protokolle finden sich in den Büchern

Speziell für Entwickler von TCP/IP-basierten Anwendungen, die primär die weit verbreitete Socket-API unter einem UNIX-artigen Betriebssystem verwenden wollen, können folgende Bücher hilfreich sein:


© Holger Trapp, 8.2.1999