Datei einlesen und uebertragen(Binär)



  • Hallo,
    ich möchte gerne eine Datei versenden und habe dies auch schon mit folgendem Code geschafft:

    std::ifstream thefile("Bla.dat", std::ios::in | std::ios::binary);
    //...
    std::string buffer;
    while (std::getline(thefile, buffer)) {
    	sendStr(connectedSocket, buffer + "\n");
    }
    thefile.close();
    

    Das Problem ist, dass dieser Code zu langsam ist, da die Datei viele Zeilen enthält die nicht sehr lang sind! Ich habe also folgendes ausprobiert:

    std::ifstream thefile("Bla.dat", std::ios::in | std::ios::binary);
    //...
    char buffer[512];
    while (true) {
    	thefile.read(buffer, sizeof(buffer));
    	sendStr(connectedSocket, buffer);
    	if (screenshot.eof()) { break; }
    }
    thefile.close();
    

    Die Datei wird leider nicht komplett übertragen... Wo liegt der Fehler? 😞

    Vielen Dank im Voraus!!! 🙂

    HilfeNoetig



  • #include <winsock2.h>
    #include <windows.h>
    #include <stdio.h>
    #include <conio.h>
    #include <string.h>
    
    #pragma comment( lib, "ws2_32.lib" )
    
    typedef struct _NETFILEHEADER
    {
        unsigned long FileSize;
        char pFileName[256];
    } NETFILEHEADER;
    
    long SendFileToNet(const char *pFileName,
                       const char *pIP,
                       unsigned short Port)
    {
        FILE *pFile;
        unsigned long FileSize;
        char buffer[4096];
        NETFILEHEADER FileHeader;
        SOCKET sender;
        WSADATA wsa;
        SOCKADDR_IN addr;
        int addrlen = sizeof(SOCKADDR_IN);
    
        pFile = fopen(pFileName, "rb");
    
        if(!pFile) return 0;
    
        fseek(pFile, 0, SEEK_END);
        FileSize = ftell(pFile);
        fseek(pFile, 0, SEEK_SET);
    
        FileHeader.FileSize = FileSize;
        memset(FileHeader.pFileName, 0, 256);
        memcpy(FileHeader.pFileName, pFileName, strlen(pFileName));
    
        WSAStartup(MAKEWORD(2,0),&wsa);
    
        sender = socket(AF_INET, SOCK_STREAM, 0);
    
        memset(&addr, 0, sizeof(SOCKADDR_IN));
        addr.sin_family = AF_INET;
        addr.sin_port = htons(Port);
        addr.sin_addr.s_addr = inet_addr(pIP);
    
        connect(sender, (SOCKADDR*)&addr, addrlen);
    
        send(sender, (char*)&FileHeader, sizeof(NETFILEHEADER), 0);
    
        while(FileSize >= 4096)
        {
            fread(buffer, 4096, 1, pFile);
            send(sender, buffer, 4096, 0);
    
            FileSize -= 4096;
        }
    
        if(FileSize)
        {
            fread(buffer, FileSize, 0, pFile);
            send(sender, buffer, FileSize, 0);
        }
    
        closesocket(sender);
    
        fclose(pFile);
    
        WSACleanup();
    
        return FileSize;
    }
    
    long GetFileFromNet(unsigned short Port)
    {
        SOCKET server;
        SOCKET client;
        WSADATA wsa;
        SOCKADDR_IN addr;
        char buffer[4096];
        long rval;
        FILE *pFile;
        NETFILEHEADER FileHeader;
        long FileSize;
    
        int addrlen = sizeof(SOCKADDR_IN);
    
        WSAStartup(MAKEWORD(2,0),&wsa);
    
        server = socket(AF_INET, SOCK_STREAM, 0);
    
        memset(&addr, 0, sizeof(SOCKADDR_IN));
        addr.sin_family = AF_INET;
        addr.sin_port = htons(Port);
        addr.sin_addr.s_addr = INADDR_ANY;
        bind(server, (SOCKADDR*)&addr, sizeof(SOCKADDR_IN));
    
        listen(server, 10);
    
        client = accept(server, (SOCKADDR*)&addr, &addrlen);
    
        recv(client, (char*)&FileHeader, sizeof(NETFILEHEADER), 0);
    
        FileSize = FileHeader.FileSize;
    
        pFile = fopen(FileHeader.pFileName, "wb");
    
        while(FileSize > 0)
        {
            rval = recv(client, buffer, 4096, 0);
            fwrite(buffer, rval, 1, pFile);
    
            FileSize -= rval;
        }
    
        fclose(pFile);
    
        closesocket(client);
        closesocket(server);
    
        WSACleanup();
    
        return FileHeader.FileSize;
    }
    
    void main(void)
    {
        //SendFileToNet("net.cpp", "127.0.0.1", 2007);
        GetFileFromNet(2007);
    }
    

    Das sind mal 2 Funktionen zum versenden und empfangen von Dateien. Um ehrlich zu sein war ich zu faul bei deinem Code auf Fehlersuche zu gehen.



  • Und dein Code hilft mir rein gar nicht weiter...

    Wir sind hier übrigens im C++ Forum...

    Trotzdem Danke!



  • Oh oh, jetzt wirste patzig. Einen geschenkten Gaul guckt man nicht ins Maul.
    Du überprüfst in deinem Mist nichteinmal wie groß die Datei ist, so dass auch zu viel bzw. zu wenig gesendet werden könnte. Aber das kann man aus meinem Beispiel ja nicht sehen, besonders nicht wenn man es sich nichteinmal anguckt.


  • Mod

    HilfeNoetig schrieb:

    Wo liegt der Fehler?

    Ich kenne deine sendStr-Funktion nicht, würde aber darauf tippen, dass deinem String der Terminator fehlt bzw. du keine Länge angibst. Da eine Binärdatei auch eingebettete Nullen enthalten kann, ist es sowieso schlecht, mit terminierten Strings zu arbeiten.

    char buffer[512];
    while (true) {
        if (int x = thefile.readsome(buffer, sizeof buffer))
            sendStr( connectedSocket, std::string(buffer,x));
        else
            break;
    }
    thefile.close();
    


  • @camper:

    void sendStr(SOCKET socket, const std::string& str) {
    	send(socket, str.c_str(), (int)str.length(), 0);
    }
    

    Dein Code erzeugt bei mir leider eine leere Datei...


  • Mod

    char buffer[512];
    while (thefile.good()) {
        thefile.read(buffer, sizeof buffer))
        if ( thefile.gcount() )
            sendStr( connectedSocket, std::string(buffer,thefile.gcount()));
    }
    

    oder so ähnlich.



  • Danke! Klappt perfekt 🙂

    for (;;) {
      std::cout << "Vielen Dank!\n";
    }
    

    Viele Gruesse,
    HilfeNoetig


Anmelden zum Antworten