FAQ zum Internet-Praktikum im WS02/03

Verantwortlich: Prof. Anja Feldmann, Nils Kammenhuber, Olaf Maennel, Arne L. Wichmann


Erläuterung

Wir bemühen uns, in dieser FAQ folgende Kennzeichnung zu verwenden (nur in graphischen Browsern sichtbar):
Rotes List-Bullet Punkt ist vor kurzem neu hinzugekommen
Gelbes List-Bullet Punkt wurde vor kurzem wesentlich geändert
Blaues List-Bullet Punkt ist schon eine Zeitlang in der FAQ und wurde nicht mehr geändert (...oder einer von uns hat mal wieder vergessen, den Punkt als neu oder geändert zu markieren... ;-) )


Allgemeines


Erstes Blatt


Zweites Blatt


Drittes Blatt


Viertes Blatt

Erste Aufgabe (tcpdump)

Zweite Aufgabe (RDT 2.2)


Fünftes Blatt


Achtes Blatt


Neuntes Blatt


Zehntes Blatt


Elftes Blatt


Antworten


Ich will an den Praktikumsrechnern arbeiten, aber der Raum ist zu.

Geh' in den Flur des Lehrstuhl Feldmann und frag irgendjemanden der Anwesenden, ob er/sie Dir mit seinem/ihrem Transponder den Praktikumsraum öffnen kann.

Sollte keiner mehr dort sein, bleibt Dir wohl nichts anderes übrig, als z.B. in die "Sunhalle" zugehen und Dich von dort aus remote einzuloggen.

Übrigens soll in den nächsten Tagen das Schloss ausgetauscht werden und dann zumindest tagsüber problemlosen Zugang ermöglichen.

(Die momentanen Schlösser brennen anscheinend durch, wenn die Tür längere Zeit offensteht.)


Ich will lieber an einem anderen Rechner arbeiten. Wie greife ich auf die Rechner im Praktikumsraum zu?

Einfach mit ssh auf irgendeinen der folgenden Rechner einloggen:

viper.net.informatik.tu-muenchen.de
slowworm.net.informatik.tu-muenchen.de
housesnake.net.informatik.tu-muenchen.de
seasnake.net.informatik.tu-muenchen.de
adder.net.informatik.tu-muenchen.de
cobra.net.informatik.tu-muenchen.de
boa.net.informatik.tu-muenchen.de
copperhead.net.informatik.tu-muenchen.de
[python.net.informatik.tu-muenchen.de]

Bis der password:-Prompt kommt, kann es u.U. eine Zeitlang dauern, also nicht die Geduld verlieren.


Ich will mit meinem Laptop im Praktikumsraum arbeiten.

Wenn Du einen Laptop hast, kannst Du ihn einfach an eines der freien Ethernetkabel anschließen, die an den Switches auf den Praktikumstischen dranhängen und dann mit Deinem Laptop arbeiten. (Außerdem soll wohl in absehbarer Zeit das Funk-LAN im Gebäude funktionieren.)

Siehe auch Wie greife ich auf die Rechner im Praktikumsraum zu?


Wie ändere ich mein Paßwort auf den Praktikumsrechnern?

Bitte auf prakt-server einloggen und dort mit 'passwd' ändern. Bis das neue Paßwort auf allen Rechnern gültig ist, kann es unter Umständen einige Zeit dauern, also das alte Paßwort nicht sofort vergessen.


Welche Anforderungen werden an die Lösungen gestellt?

Die Lösungen müssen...


Wie gebe ich meine praktischen Aufgaben ab?

Beispiel

Angenommen, mein eigenes Login lautete meinLogin und das meines Teampartners partnerLogin. Die Uhrzeit sei 15:00h (und 27 Sekunden). Dann gebe ich meine Lösung für die 1. Übung folgendermaßen ab:

meinLogin@viper> mkdir meinLogin_partnerLogin
meinLogin@viper> cp loesungsfile1 loesungsfile2 loesungsfile3 usw meinLogin_partnerLogin/
meinLogin@viper> date +%H%M%S
150027
meinLogin@viper> tar -czf meinLogin_partnerLogin_150027.tgz meinLogin_partnerLogin/
meinLogin@viper> cp meinLogin_partnerLogin_150027.tgz ~inetprak/abgabe/1.uebung/
meinLogin@viper> chmod g+r ~inetprak/abgabe/1.uebung/meinLogin_partnerLogin_150027.tgz
meinLogin@viper>

Hinweise

Schon abgegebene Lösungen können bis zur Abgabedeadline upgedatet werden (d.h., man kann z.B. sicherheitshalber z.B. ein paar Tage vor der Deadline schonmal eine halbfertige Lösung abgeben, ohne Nachteile zu erwarten.) Dazu gibt man einfach nochmal eine komplette Lösung wie oben beschrieben mit aktuellem Datum ab.

Siehe auch Welche Sprachen sind erlaubt?


Bis wann kann ich meine praktischen Aufgaben abgeben?


Infos zum Thema Zweiergruppen


Was soll ich machen, wenn ich noch Fragen habe?

  1. Zuallererst: Lies Dir bitte diese FAQ durch (was Du ja gerade tust ;-) )
  2. Wenn das Deine Frage nicht oder nur unzureichend beantwortet, dann schreib eine E-Mail an: inetprak@net.in.tum.de.
    Wir können keine HTML-Mails, keine Word-Dokumente oder sonstwie seltsam kodierten Mails berücksichtigen, sondern nur plain ASCII (also ISO-8859-1 oder ISO-8859-15, 8bit oder auch quoted-printable).
    Also bitte keine Mails in irgendwelchen Schweinkram-Formaten schicken, gell? :-)
  3. Außerdem wird's wöchentlich noch eine Fragestunde im Rechnerraum geben. (Termin wird noch bekanntgegeben.)

Wo finde ich Infos zu Perl?


Welche Sprachen sind erlaubt?

Sofern nicht genauer spezifiziert, sind folgende Sprachen erlaubt:

Grundsätzlich gilt: Deine Programme müssen ohne Änderungen, Umkonfigurationen und sonstige vorbereitenden Arbeiten auf den Schlangen-Rechnern lauffähig sein.
Falls Dein Programm dennoch solche vorbereitenden Arbeiten erfordert (z.B. Setzen von $CLASSPATH bei Java-Programmen, oder Umleiten der Ausgabe Deines Programmes in einen Shellbefehl wie z.B. sort, usw.), dann schreibe einfach ein kurzes Shellskript, das diese Aufgaben automatisch erledigt.

Für das dritte Aufgabenblatt (und die weiteren Blätter) sind Java und das Perl-Modul IO::Socket wieder erlaubt.


Wo finde ich die RFCs?

Beim RFC-Editor.


Wie generiere ich ein tar-File eines Verzeichnisses inklusive aller darin enthaltenen Dateien, Unterverzeichnisse etc.?

Angenommen, das Verzeichnis heiße dir. Dann:

Anmerkung für Leute, die die Übungen an einem anderen Rechner (z.B. zuhause oder sunhalle) erstellen: Es gibt verschiedene Versionen von tar -- verwende daher unbedingt eine Version, die zu der auf den Praktikumsrechnern defaultmäßig installierten kompatibel ist!


Was ist ein File der Form name.gz?

Es ist ein mit dem Befehl gzip komprimiertes File. Zum Ausgeben auf Standardausgabe benutze entweder

In Perl kannst Du es recht trickreich auslesen mit
open(DATEIHANDLE, "zcat dateiname|")
so dass das File also beim Auslesen gleich automatisch dekomprimiert wird.


Und wie verarbeite ich dann so ein File, das auf der Standardausgabe ausgegeben wird?

Du brauchst nicht immer ein Programm zu schreiben; Du kannst manchmal wichtige Informationen durch eine einzige Zeile in der Shell herausbekommen.

Benutze hierzu die sogenannten Pipes. Wenn z.B. der Inhalt der Datei zu groß ist, kannst Du die Ausgabe des Dekompressionskommandos in den Pager less pipen, und zwar mit zcat dateiname.gz | less.

Du kannst diese Pipes sogar schachteln, was sie sehr, sehr mächtig macht. Ein Beispiel:
 zcat name.gz | grep "http" | sort -n -r | uniq | head >ausgabe.txt

Wohlgemerkt: Das ist eine einzige Zeile, die man in die Shell eintippt. Diese recht komplexe Aufgabe wurde also komplett ohne irgendein Programm oder Skript gelöst.


Wie verarbeite ich eines dieser Datenfiles mit Perl?

Das folgende kombinierte Shell-/Perlskript gibt aus, wie oft welcher HTTP-Returncode im Logfile logfile.gz vorkommt:

zcat logfile.gz | perl -e 'while(<>){s/\s+/ /g;@l=split;@f=split("/",$l[3]);$p{$f[1]}++;}foreach $i (sort keys %p) {print "$i:$p{$i}\n";}'

Natürlich ist dieser Einzeiler schrecklich unübersichtlich und somit quasi unlesbar. Daher nochmal in kommentierter Form:

zcat logfile.gz Ausgabe des Logfiles auf die Standardausgabe (vgl. oben)
| Umleiten von Standardausgabe auf Standardeingabe
perl -e Aufruf von Perl mit der restlichen Kommandozeile als auszuführendes Skript
while() {} While-Schleife
<> Zeilenweises Lesen der Standardeingabe (in Variable $_)
while(<>) {} Durchlaufen aller Zeilen der Standardeingabe
s/\s+/ /g; globales Ersetzen von mehreren Spaces durch ein Space
@l=split; Aufspalten einer Zeile in ein Array namens l mit dem Space als Trennzeichen
@f=split ("/", $l[3]); Aufspalten des 4ten Wortes (Trennzeichen ist "/")
$p{$f[1]}; Benutzt 2ten Eintrag von f als Hash in Hashtabelle p
$p{$f[1]}++; Automatisches Erhöhen des Wertes in der Hashtabelle
keys %p Liste aller Hashes der Hashtabelle p
Hash := Hashkey
sort keys %p Sortiere die obige Liste von Hashes
foreach $i (sort keys %p) {} Für jeden Eintrag (der dann bei jedem Durchlauf jeweils in der Variable i gespeichert wird) in der sortierten Liste von Hashes
print "$i:$p{$i}\n"; Gib den Wert von i und den Wert des Hashes aus

Und wie Du siehst, kann man Perl also auch "on-the-fly" benutzen, also ohne eine extra Skriptdatei anzulegen. Das ist natürlich recht unübersichtlich, also muss man solche "Einzeiler" dann gut dokumentieren.

Mehr Infos, wie man Perl trickreich aufrufen kann und sich dadurch eine Menge Schreibarbeit sparen kann, findest Du übrigens auf der Manpage man perlrun.


Was ist mit "in eine logarithmische Skala konvertiert" gemeint?

Damit ist gemeint, daß alle Werte durch ihren Logarithmus ersetzt werden sollen.


Warum ist das Logfile nur so groß??

Für Netzwerkverhältnisse ist das ein kleines Logfile. Ihr werdet im Praktikum daher auch lernen, wie man mit solch großen Datenmengen umgeht (z.B. was man tut, wenn das zu analysierende File gar nicht komplett ins RAM reinpasst...).

Es ist also nicht bloße Schikane, sondern durchaus Praxisorientierung.


Warum darf ich kein Java oder kein IO::Socket verwenden??

Wer ein Internet-Praktikum macht, der sollte auch einmal "von Hand" mit Sockets umgegangen sein, d.h. die entsprechenden Systemaufrufe verwendet haben. Java oder auch das Perl-Modul IO::Socket abstrahieren den Umgang mit Sockets aber zu stark von der Systemebene. Daher sind sie für das zweite Aufgabenblatt ausnahmsweise nicht erlaubt.


Warum soll ich überhaupt Perl lernen?

Du musst nicht, wir empfehlen es Dir nur. Einer der zahlreichen positiven Aspekte von Perl ist dabei auch der, dass man schon mit nur wenigen Kenntnissen der Sprache sehr weit kommt. Perls Motto ist there's more than one way to do it, was man auch so interpretieren kann, dass man auch schon als Anfänger in Perl "alles" machen kann, nur dass eben ein Perl-Profi die Sachen z.T. schneller und eleganter hinbekommt.

In diesem Praktikum wirst Du Perl insbesondere gebrauchen können für:

Auch im Alltag wird Dir Perl später gute Dienste leisten. Übrigens sind viele sog. CGI-Skripte im WWW-Bereich in Perl geschrieben.


Irgendwie bekomme ich seltsame Fehler, wenn ich versuche, Sockets aufzumachen

Lies' Dir unsere "Schnellinfo-Seite" über TCP und/oder die Folien des Vortrags über Socketprogrammierung durch.

Vermutlich lässt im Moment gerade ein anderer Praktikumsteilnehmer ein Programm auf dem gleichen Port laufen. => Versuch' Dein Glück auf einem anderen Rechner, oder nimm eine andere Portnummer.

Wenn Du die Portnummer aus diesem Grund änderst, dann schreibe dies ins README-File hinein.


Ich kann java oder javac nicht aufrufen.

Stelle bitte zunächst sicher, dass in der Shellvariable $PATH auch das Verzeichnis /usr/local/bin (oder alternativ /usr/local/java oder /usr/local/j2sdk1.3.1) enthalten ist. Ansonsten kann die Shell java natürlich nicht ausführen.

Sollte das der Fall sein und Java aber trotzdem nicht ausführbar sein, dann schreib uns bitte eine Mail, damit wir es auf dem entsprechenden Rechner nachinstallieren können. (Mail Spamschutz)

Solange wir uns nicht gerührt haben, kannst Du Dich (z.B. mit dem Kommando ssh) auf einem anderen der Schlangenrechner einloggen, auf dem Java installiert ist.


Warum kommen die Daten, die ich sende, nie auf meinem Server an?

Das TO_SERVER-Filehandle des Sockets wird nicht automatisch geflusht, wenn man mit print() hineinschreibt. Verwende daher einfach send() statt print(), dann brauchst Du Dich gar nicht um das Flushing zu kümmern.

Du kannst zwar das Autoflush mit $|=1 (möglichst zu Beginn des Programms) einschalten, aber das löst die Probleme nicht immer.


Mein Programm läft anscheinend durch, gibt aber offensichtlich nicht alle meine print-Anweisungen aus.

Dieses Problem hat die gleichen Ursachen wie das Problem, dass die Daten nicht beim Server ankommen und kann daher auch genauso umgangen werden, nämlich mit $| = 1; am Programmanfang.


Soll der Server die auf dem Blatt spezifizierten Meldungen auf seiner Standardausgabe ausgeben oder zum Client übermitteln?

Der Server soll die auf dem Blatt spezifizierten Meldungen (wie z.B. 200 1298798612 Bytes oder 551 Current directory only) an den Client senden. (Logisch -- der Client muss ja irgendwie wissen, woran er ist.)

Es wäre sinnvoll, wenn der Client diese Meldung nicht einfach nur schweigend entgegennehmen, sondern daraus eine für den menschlichen Benutzer verständliche Fehlermeldung generieren würde.

Siehe auch die nächste Frage.


Was ist mit diesem get-Befehl des Clients?

Der get-Befehl des Clients ist logischerweise ein String, den der Client zum Server schickt, um ihn anzuweisen, dass der Server dem Client das angegebene File schicken soll.

Siehe auch die vorige Frage.


Mein Perlskript hängt irgendwie beim Auslesen von Daten aus dem Socket oder einer Datei fest

Bedenke, dass beim Auslesen via <FILEHANDLE> immer eine ganze Zeile gelesen wird. Aber solange kein \n kommt...


Mein Perlskript hängt aber immer noch beim Auslesen von Daten aus dem Socket fest!!

Anscheinend gibt es Probleme bei der Verwendung von receive() auf den Schlangenrechnern: Beim Auslesen von Daten aus einem Socket mit mit receive() kommen einfach keine Daten an, obwohl der Code auf anderen (Debian-Linux-) Rechnern einwandfrei funktioniert.

Die Ursache dieses wirklich sehr seltsamen Phänomens ist uns leider auch nicht bekannt. Die einzige Abhilfe scheint zu sein, stattdessen read() oder <SOCKET> zu verwenden. :-(


Wird die Datei dann direkt vom letzten Glied in der Kette empfangen, oder durchläuft sie die gesamte Kette der angegebenen Server?

Die Antwort hierauf folgt unmittelbar aus dem vierten Aufzählungspunkt auf dem Aufgabenblatt... (und zwar insbesondere aus dem zweiten Teilsatz)

In der Vorlesung wurde gesagt, wie die Sache bei anderen Filesharing-Diensten läuft (nämlich häufig so, dass die Enden der Kette die Datei dann mit einer direkten TCP-Verbindung zwischen sich übertragen). Das verursacht zwar weniger Traffic, ist andererseits aber nicht so gut anonymisierbar.


Nach dem Einlesen und Ausführen des ersten Kommandos tut der Client nichts mehr.

Wenn Du fork() verwendest, dann sollte der Prozess, der von STDIN (sprich: aus der Tastatur) einliest, immer der Vater sein.

Normalerweise wird zwar STDIN an den Kindprozess weitervererbt; allerdings kann es sein, dass Du beim Auslesen von STDIN von verschiedenen Kindprozessen mit seltsamen Signalen wie z.B. SIGTTYIN o.ä. hantieren musst, was ziemlich eklig ist. (Und wenn Du es nicht tust, wird der entsprechende Kindprozess einfach blockieren.) Daher ist es einfacher, den Vaterprozess für STDIN (also Tastatureingaben) verantwortlich zu machen.


Wo kriege ich Infos zu tcpdump-patched her?


Ich will dump.gz zuerst entpacken und dann durch diverse Programme schicken -- aber wie verhindere ich dabei, dass da zusätzliche Files angelegt werden?


Wie sortiere ich dieses riesige File? In den Speicher kann ich es ja nicht komplett einlesen.

Falls Du das File irgendwie sortieren willst, dann kannst Du das auch dem (recht schnellen) Unixbefehl sort überlassen. Vermutlich wirst Du etwas wie

... |  sort -n -t '|' +4711  |...
in irgendeine Kommando-Pipeline einbauen.
Beachte, dass '|' das Argument zu -t ist und daher mit ' gequotet wird. Ansonsten würde es ja von der Shell als Pipe-Operator interpretiert.


Hey, dieses externe sort kann ja richtig Zeit sparen. Gibt's noch mehr solche Tricks?

Klassische Unix-Befehle, die immer mal wieder in langen Pipes auftauchen, sind z.B.

Weitere Infos zu diesen Befehlen findet man auf ihren Manpages oder z.B. auch in den Büchern Linux in a Nutshell oder Unix in a Nutshell.


SYN, ACK und FIN kennen wir, aber was sind z.B. PUSH, RST usw.?


Ich verstehe dieses Java-Template nicht so ganz...

In Java ist es schwierig, non-blocking I/O (also wie z.B. mit select() in Perl/C/C++) zu realisieren. Das hat zur Folge, dass das Java-Template sozusagen zwei voneinander unabhängige lines of execution hat, was die Implementierung der Zustandsübergangsmaschine deutlich anders als in Perl/C/C++ gestaltet:

Die Timeout-Routinen kannst Du ignorieren, da sie erst für das nächste Übungsblatt (auf dem RDT 3.0 implementiert werden soll) relevant sind. Außerdem bist Du nicht dazu verpflichtet, unser Template zu übernehmen; Du kannst auch gerne einen eigenen, völlig anderen Ansatz wählen. Und außerdem haben wir mittlerweile die etwas verwirrende Bemerkung über die Green Threads angepasst.


Wie kann ich in Perl den Binärwert einer Zahl (also nicht als String) bekommen?

Verwende die pack()-Funktion. (Siehe z.B. man perlfunc oder perldoc -f pack)

Am einfachsten ist es vermutlich, die Daten iterativ zu pack()en; beginne also zuerst mit dem ersten Headerelement und hänge dann die anderen an:

$data .= pack(...bla...);
$data .= pack(...blubb...);
...
$data .= pack(...body...);

Zum Empfang kannst Du dann entsprechend unpack() verwenden.


Ohje! So ein großes File! Wie soll ich das bloß in endlicher Zeit analysiert kriegen?

Hierzu ein paar Tips:


Sollen wir jetzt 16bit- oder 1bit- Sequenznummern (und ACK-Nummern) verwenden?

Damit der RDT-Header einigermaßen einfach zu lesen ist, sind die Sequenzummern/ACK-Nummern 16 Bit groß. Allerdings nehmen sie, wie im Buch spezifiziert, nur die Werte 0 und 1 an.


Die Checksumme verwirrt mich...


Was ist network byte order?

Kaum zu glauben, aber wahr: Für das uralte Problem, wie man einen 16-bit-Wert (oder einen 32-bit-Wert) in zwei Bytes (bzw. vier Bytes) hintereinander im Speicher ablegt, existieren zwei verschiedene Standards, nämlich big endian und little endian.

Mehr Infos über endianness findest Du z.B. hier:


Euer Empfänger tut nicht das, was angegeben ist.

Das sollte jetzt gefixt sein. Großes Sorry!


Muss ich verschiedene Programme für die RDT 2.2- und die RDT 3.0-Aufgabe abgeben?

Nein. RDT 3.0 hat ja das gleiche Paketformat, nur dass hier noch zusätzlich Packet Losses auftreten können. D.h., wenn Du RDT 3.0 korrekt implementiert hast, dann hast Du damit schon automatisch RDT 2.2 erschlagen.


Was soll ich tun, wenn sich Pakete gegenseitig überholen (z.B. wenn ein früher abgeschicktes Paket wegen des Zufallsdelays später ankommt)?

Gar nichts, denn das sollte bei RDT nicht vorkommen. :-) (Steht auch irgendwo relativ versteckt im Buch drin.)

In der Realität kommt sowas natürlich durchaus vor (wenn auch recht selten). Du kannst Dir ja mal kurz überlegen...


Wie kann ich die Ausgabe meines Empfängers sonst noch debuggen?

Du kannst dafür z.B. die Tools netcat und hexdump verwenden, z.B. so:

netcat -u -l -p 4812 | hexdump -...
(Die Option -u bringt netcat dazu, standardmäßig UDP statt TCP zu verwenden.)


Wie sorge ich dafür, dass meine verschiedenen Prozesse, die ich mit fork() angelegt habe, miteinander Daten austauschen können?

Da fork() verschiedene Prozesse anlegt und unter Unix Prozesse getrennte Speicherbereiche haben, können sie nicht einfach auf die gleichen Variablen zugreifen.
Für dieses Problem gibt es mehrere Herangehensweisen:


Auf welchem {TCP|UDP}-Serverport läuft normalerweise Protokoll XYZ?

Das kriegst Du auf Unixrechnern normalerweise ganz einfach durch Anschauen der Datei /etc/services heraus. Allerdings haben manche Protokolle seltsame Namen; z.B. taucht DNS nicht etwa als dns, sondern als domain auf.


Irgendwie kriege ich nicht raus, welche Daten mein Programm falsch übermittelt. Kann ich den Netzverkehr von anderen Programmen als Referenz anschauen?

Wir haben jetzt sowohl /usr/sbin/tcpdump als auch /usr/local/bin/tcpdump-patched mit einem s-Bit versehen. Das heißt im Klartext:

Ab sofort kann jeder Benutzer eines Schlangenrechners sämtlichen Traffic, der über die Ethernetkarte geht, mit Hilfe von tcpdump mithören!

Sofern man an der Konsole sitzt, braucht man einfach nur /usr/sbin/tcpdump ohne Parameter einzugeben. (Ist man allerdings per ssh eingeloggt, dann würde beim ersten gesnifften Netzwerkpaket von tcpdump eine Ausgabezeile generiert und per ssh als mindestens ein weiteres Ethernetpaket zum Anwender geschickt, was nat&uum;rlich dazu führt, dass tcpdump ein dieses zweite Paket ebenfalls snifft und ausgibt, usw. usw. -- also Vorsicht)

Bitte benutzt tcpdump nicht zur Spionage anderer Leute, zum Hacken von Passwörtern oder zu ähnlichen Dingen, sondern lediglich zu Test, Debugging und Untersuchung von Programmen und Protokollen!


Wieviele TCP-Verbindungen darf es in Aufgabenteil f) und g) geben?

  1. Der Proxy darf gleichzeitig mehrere TCP-Verbindungen zu den Clients haben.
  2. Aber pro Client darf er nur eine (oder auch gar keine) TCP-Verbindung offenhaben.
    Umgekehrt formuliert: Jeder Client darf maximal eine TCP-Verbindung zum Proxy aufgebaut haben.
Das gleiche gilt genauso für die Kommunikation zwischen Proxy und Servern, d.h., der Proxy darf gleichzeitig mehrere Verbindungen zu den Servern geöffnet haben, darf aber pro Server jeweils (maximal) nur eine TCP-Verbindung haben.


Was soll ich in Aufgabenteil f) und g) tun, wenn schon eine TCP-Verbindung besteht und ich laut Trace nun eine zweite Anfrage stellen müsste?

Simulation

Du musst Dir in diesem Fall merken, dass der Client noch eine weitere Anfrage stellen muss. Sobald die schon bestehende TCP-Verbindung abgebaut ist (Aufgabenteil f) bzw. sobald in der bestehenden TCP-Verbindung alle Daten übertragen wurden (Aufgabenteil g), baust Du eine neue TCP-Verbindung auf (Aufgabenteil f) bzw. stellst gleich die neue GET-Anfrage (Teil g).

Auszugebende Daten

Die Dauer, bis die Nutzdaten am Client angekommen sind, bestimmt sich hier sinnvollerweise als das Zeitintervall


Was kann ich als Grundlage für mein kryptografisches Protokoll verwenden?

Einige kryptografische Protokolle und Dokumentation dazu:

ssh

PGP

SSL

IPsec


Sollen die verschiedenen Nachrichtentypen als Textstring gesendet werden oder mit den Headern, wie sie in RFC 1654 spezifiert sind?

Einfach nur als Text senden; also genauso, wie es auf dem Aufgabenblatt steht. Keine komplizierten Header aus irgendwelchen RFCs verwenden.


Wir haben folgendes Problem: uns ist klar, dass wir beim BGP-Handshake als allererstes die AS-IDs austauschen müssen; dazu muss allerdings schon eine TCP-Verbindung bestehen. Zu welchem Rechner/Port soll ich die denn aufbauen?

Der Router hat eine Konfiguration und anhand dieser Konfiguration weiß er, von welchen Peers (Router/Port) er Nachrichten empfangen kann und von welchen nicht. Um Fehler, Missbrauch, etc. zu reduzieren wird beim BGP-Handshake als erstes die AS-ID ausgetauscht.

Sprich: ihr braucht für Euren "Software-Router" auch so eine Konfigurationsmöglichkeit... die könnte z.B. so aussehen:

router bgp 65111
 bgp router-id 131.159.14.22
 neighbor 131.159.14.23 remote-as 65111
 neighbor 131.159.14.24 remote-as 65112

Dann baut Router 131.159.14.22 mit Router 131.159.14.23 und 131.159.14.24 eine BGP-Verbindung auf. Bei BGP ist der Port normalerweise immer 179. Ihr solltet natürlich wegen Aufgabenteil (c) die remote-Ports irgendwo in der Konfiguration mit spezifizieren.
Vermutlich ist es zu Anfang am Einfachsten, die Konfiguration erstmal hart in den Code reinzuhacken.

Was in der Aufgabenstellung spezifiziert ist, ist wie die Router Nachrichten ausstauschen...