TCP Echo Server, Daten in Datei schreiben

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • TCP Echo Server, Daten in Datei schreiben

    Hi, ich habe folgendes vor und komme nicht weiter:

    Ich will von meinem PC über ein eingerichteten netzwerk-Drucker drucken...
    An sich nicht all zu schwer, nur dass der Drucker keiner ist, sondern ein weiterer PC im netzwerk.

    ich habe also ersteinmal mit netcat gestet ( auf dem 'druck-pc' gestartet und von da alles ankommende in eine datei geschrieben). ging hervorragend.

    Einziges Problem, nachdem netcat einen druckauftrag erhalten hat, schreibt er es in eine datei und beendet die sitzung...

    Ausserdem war das mit netcat ja nur zu testzwecken.

    Ich habe mir also einen TCP-Echo-Server gebaut/geholt und schreibe dort nun die empfangenen daten in eine datei.
    leider jedoch nicht die richtigen... wenn der server läuft und einen druckauftrag bekommt, merkt er es zwar, aber er schreibt nur den namen des senders in die datei...

    wie kann ich es lösen, dass der inhalt des dokuments (drucker ist als postscript drucker eingerichtet) in die datei schreibt?

    anbei mal mein code für den server...


    Quellcode

    1. #include<sys/types.h>
    2. #include<sys/socket.h>
    3. #include<stdio.h>
    4. #include<unistd.h>
    5. #include<string.h>
    6. #include<netinet/in.h>
    7. #define SERVER_PORT 515 /* Ein Port der auch von 'gewöhnlichen' Benutzern verwendet werden darf */
    8. #define MSG_SIZE 10000 /* Die maximale Anzahl an Zeichen, die 'msg' enhalten darf */
    9. FILE *fp;
    10. char pfad[100];
    11. char hilfe[50];
    12. int main(int argc, char **argv){
    13. strcpy(pfad, "/home/xdavid/TCP/empfangen.ps");
    14. int fromsocket; /* Socket, der auf ankommende Anfragen wartet */
    15. int client; /* Socket für die Kommunikation mit einem Client */
    16. struct sockaddr_in fromaddr; /* Adresse die 'belauscht' werden soll */
    17. char msg[MSG_SIZE]; /* der Buffer für die Nachrichten */
    18. int bytes; /* hier wird die Anzahl der gelesenen Bytes gespeichert */
    19. printf("%s: server is up and running ...\n", argv[0]);
    20. /* Socket erzeugen; verbindungsorientiert mit TCP */
    21. fromsocket = socket(PF_INET,SOCK_STREAM,0);
    22. if(fromsocket == -1){
    23. fprintf(stderr, "%s: cannot open socket\n", argv[0]);
    24. exit(1);
    25. }
    26. /* Adresse zum 'Lauschen' definieren */
    27. fromaddr.sin_family = PF_INET;
    28. fromaddr.sin_addr.s_addr = htonl(INADDR_ANY); /* eine Anfrage kann von jeder IPAdresse kommen */
    29. fromaddr.sin_port = htons(SERVER_PORT);
    30. /* Socket an die Adresse und den Port binden */
    31. if(bind(fromsocket, (struct sockaddr *)&fromaddr, sizeof(fromaddr)) == -1){
    32. fprintf(stderr, "%s: cannot bind socket\n", argv[0]);
    33. exit(1);
    34. }
    35. /* Socket 'horchen' lassen; die maximale Länge der Warteschlange wird auf 3 gesetzt */
    36. if(listen(fromsocket, 3) == -1){
    37. fprintf(stderr, "%s: unable to listen\n", argv[0]);
    38. exit(1);
    39. }
    40. /* Auf Anfragen warten */
    41. for(; ; ){ /* Endlosschleife; "forever" */
    42. /* Socket für ankommende Anfrage erzeugen */
    43. if((client = accept(fromsocket, NULL, NULL)) == -1){
    44. fprintf(stderr, "%s: error while receiving request\n", argv[0]);
    45. exit(1);
    46. }
    47. /* Nachricht vom Client lesen */
    48. if((bytes = recv(client, msg, sizeof(msg), 0)) == -1){
    49. fprintf(stderr, "%s: error while receiving reply\n", argv[0]); exit(1);
    50. }
    51. if ((fp = fopen(pfad,"w"))==NULL)
    52. {printf("\n Fehler beim Öffnen der Datei\n"); }
    53. /* es handelt sich um einen String, also darf man das abschließende '\0'
    54. nicht vergessen */
    55. msg[bytes] = '\0';
    56. printf("%f\n", fp);
    57. fprintf(fp,"%s\n",msg);
    58. fclose(fp);
    59. printf("%s: received request from '%s'\n", argv[0], msg);
    60. /* den Client-Socket freigeben */
    61. close(client);
    62. }
    63. return 0;
    64. }
    Alles anzeigen



    ich hoffe jemand kann mir bei meinem problem weiter helfen...

    vielen dank schonma
    mfg
    meneke
  • Hi,

    ich nehme nicht an, dass die ganze Datei in ein TCP Paket passt. Und nach jedem Schleifendurchlauf/Verbindungsaufbau erstellst du ja in deinem Code eine neue Datei. Es ist also nicht vorgesehen, dass du mehrere Pakete in eine Datei schreibst.

    Du wirst die recv Funktion also auf jeden Fall in eine Schleife packen müssen. Damit er nicht nach jedem Verbindungsaufbau durchrattert, einen Teil schreibt und dann auf neue Verbindungsversuche wartet. In C bin ich nicht so fit. In Python ginge das so:

    Quellcode

    1. while True:
    2. data = socketverbindung.recv(1024)
    3. file('bla.txt','a').write(data)
    4. if not data:
    5. reporting("Datei fertig empfangen")
    6. break


    Schau mal ob dir das weiterhilft, ansonsten meld dich nochmal:
    zotteljedi.de/doc/socket-tipps/

    Einfacherheitshalber appendest du die eine Datei immer.
  • Mahlzeit,

    ich würde die allgemein die select Funktion empfehlen.

    Beim Empfangen von Daten musst du - wie d0nUt bereits erwähnte - mit einer Schleife arbeiten.
    TCP ist streamorientiert. Heißt also: Du sendest deine Daten solange, bis der Socket einen Fehler zurückgibt (EWOULDBLOCK unter Windows WSAEWOULDBLOCK). Wenn genau das passiert, musst du solange warten (Auch hier ist die select Funktion sehr vorteilhaft!), bis das Socket nicht mehr blockiert. Dann halt die restlichen Daten schicken und das Spielchen geht von vorne los.
    (Send gibt die Anzahl Bytes zurück, die versendet wurden).
    Bei der Serverapplication musst du dementsprechend aufpassen. Am besten sendest du ein terminator (oder einen eindeutigen String) mit, damit du genau weißt, wann die Datei vollständig angekommen ist.

    Hier noch ein paar Infos zu non-blocking Sockets: www.kegel.com

    Gruß,
    Blue