套接字发送客户端服务器文件

sazearte

我编写了一个应用程序,其中客户端使用使用tcp协议的套接字将文件发送到服务器。

我的服务器是多线程的(带有Pthread)。

仅有一个问题,将文件复制到服务器的文件比原始文件小(丢失约2ko)。为什么?

这是我的客户代码,该代码开始输入./client filename filenamecopy

#include <netdb.h>
#include <netinet/in.h>
#include <string.h>
#include <stdio.h>
 
 
int fileSEND(char *server, int PORT, char *lfile, char *rfile){
 
    int socketDESC;
    struct sockaddr_in serverADDRESS;
    struct hostent *hostINFO;
    FILE * file_to_send;
    int ch;
    char toSEND[1];
    char remoteFILE[4096];
    int count1=1,count2=1, percent;
 
    hostINFO = gethostbyname(server);
    if (hostINFO == NULL) {
        printf("L'adresse ip du serveur n'est pas accesible\n");
        return 1;
    }
 
    socketDESC = socket(AF_INET, SOCK_STREAM, 0);
    if (socketDESC < 0) {
        printf("Erreur création socket\n");
        return 1;
    }
 
    serverADDRESS.sin_family = hostINFO->h_addrtype;
    memcpy((char *) &serverADDRESS.sin_addr.s_addr, hostINFO->h_addr_list[0], hostINFO->h_length);
    serverADDRESS.sin_port = htons(PORT);
 
    if (connect(socketDESC, (struct sockaddr *) &serverADDRESS, sizeof(serverADDRESS)) < 0) {
        printf("Erreur de connection\n");
        return 1;
    }
 
 
    file_to_send = fopen (lfile,"r");
    if(!file_to_send) {
        printf("Erreur de lecture du fichier\n");
        close(socketDESC);
        return 0;
    } else {
    long fileSIZE;
    fseek (file_to_send, 0, SEEK_END); fileSIZE =ftell (file_to_send);
    rewind(file_to_send);
 
    sprintf(remoteFILE,"FBEGIN:%s:%i\r\n", rfile, fileSIZE);
    send(socketDESC, remoteFILE, sizeof(remoteFILE), 0);
 
    percent = fileSIZE / 100;
    while((ch=getc(file_to_send))!=EOF){
        toSEND[0] = ch;
        send(socketDESC, toSEND, 1, 0);
        if( count1 == count2 ) {
            printf("33[0;0H");
            printf( "\33[2J");
            printf("Nom du fichier: %s\n", lfile);
            printf("Taille du fichier: %i Kb\n", fileSIZE / 1024);
            printf("Poucentage : %d%% ( %d Kb)\n",count1 / percent ,count1 / 1024);
            count1+=percent;
        }
        count2++;
 
    }
    }
    fclose(file_to_send);
    close(socketDESC);
return 0;
}
 
int main(int argc, char* argv[])
{
    fileSEND("127.0.0.1", 31338, argv[1], argv[2]);
    return 0;
}

和服务器,仅由./server启动

#include <arpa/inet.h>
#include <netdb.h>
#include <netinet/in.h>
#include <string.h>
#include <stdio.h>
#include <pthread.h>
 
#define PORT 31338
 
int parseARGS(char **args, char *line){
    int tmp=0;
    args[tmp] = strtok( line, ":" );
    while ( (args[++tmp] = strtok(NULL, ":" ) ) != NULL );
    return tmp - 1;
}
 
int client(void *ptr){
    int  connectSOCKET;
    connectSOCKET = (int ) ptr;
    char recvBUFF[4096];
    char *filename, *filesize;
    FILE * recvFILE;
    int received = 0;
    char tempstr[4096];
    char *header[4096];
 
    /*int i=0;
    while(i<993199) {
    i++;*/
    while(1){
        if( recv(connectSOCKET, recvBUFF, sizeof(recvBUFF), 0) ){
            if(!strncmp(recvBUFF,"FBEGIN",6)) {
                recvBUFF[strlen(recvBUFF) - 2] = 0;
                parseARGS(header, recvBUFF);
                filename = header[1];
                filesize = header[2];
                printf("Fichier: %s\n", filename);
                printf("Taille: %d Kb\n", atoi(filesize) / 1024);
        }
        recvBUFF[0] = 0;
        recvFILE = fopen ( filename,"w" );
        while(1){
            if( recv(connectSOCKET, recvBUFF, 1, 0) != 0 ) {
                fwrite (recvBUFF , sizeof(recvBUFF[0]) , 1 , recvFILE );
                received++;
                recvBUFF[0] = 0;
                } else {
                printf("Progression: %s [ %d of %s bytes]\n", filename, received , filesize);
                return 0;
                }
            }
            return 0;
        } else {
        printf("Client déconnecté\n");
        }
    return 0;
    }
}
 
 
int main()
{
    int socketINDEX = 0;
    int listenSOCKET, connectSOCKET[4096];
    socklen_t clientADDRESSLENGTH[4096];
    struct sockaddr_in clientADDRESS[4096], serverADDRESS;
    pthread_t threads[4096];
 
    listenSOCKET = socket(AF_INET, SOCK_STREAM, 0);
    if (listenSOCKET < 0) {
        printf("Peut pas crée socket\n");
        close(listenSOCKET);
        return 1;
    }
 
    serverADDRESS.sin_family = AF_INET;
    serverADDRESS.sin_addr.s_addr = htonl(INADDR_ANY);
    serverADDRESS.sin_port = htons(PORT);
 
    if (bind(listenSOCKET, (struct sockaddr *) &serverADDRESS, sizeof(serverADDRESS)) < 0) {
        printf("Peut pas trouver la socket\n");
        close(listenSOCKET);
        return 1;
    }
 
    listen(listenSOCKET, 5);
    clientADDRESSLENGTH[socketINDEX] = sizeof(clientADDRESS[socketINDEX]);
    int i=0;
    /*while(i<993199) {
    i++;*/
    while(1){
        connectSOCKET[socketINDEX] = accept(listenSOCKET, (struct sockaddr *) &clientADDRESS[socketINDEX], &clientADDRESSLENGTH[socketINDEX]);
        if (connectSOCKET[socketINDEX] < 0) {
            printf("Connection refusé\n");
            close(listenSOCKET);
            return 1;
        }
 
        pthread_create( &threads[socketINDEX], NULL, client, connectSOCKET[socketINDEX]);
        if(socketINDEX=4096) {
            socketINDEX = 0;
        } else {
        socketINDEX++;
        }
    }
    close(listenSOCKET);
}
基思莫

两个问题:

  1. 您的客户端发送带有FBEGIN:filename:size标头的4K块。服务器尝试在一个4K块中读取它。recv()可以返回的缓冲区少于完整的缓冲区(最少1个字节)。

  2. 您的服务器在读取文件后没有关闭文件。这可能导致文件大小差异(关闭文件时,缓冲的数据将被刷新)。

本身不是错误,而是性能问题:一次读/写/发送/接收一个字节是SLOW您应该在更大的块中进行所有操作(即使仅1K的性能也会大幅度提高)。只要记住recv()上面提到的“可能会部分完成”的问题即可。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

使用套接字从服务器向客户端发送静态文件

来自分类Dev

通过python中的TCP套接字在客户端-服务器之间发送文件?

来自分类Dev

使用C中的套接字将文件从客户端发送到服务器

来自分类Dev

使用python套接字将Txt文件从客户端发送到服务器

来自分类Dev

使用套接字C#客户端/服务器发送文件

来自分类Dev

通过python中的TCP套接字在客户端-服务器之间发送文件?

来自分类Dev

在套接字客户端服务器中发送多个文件

来自分类Dev

TCP套接字,发送文件,客户端服务器,服务器不保存整个文件,C语言

来自分类Dev

套接字io,节点js,从服务器向客户端发送图像/文件的简单示例

来自分类Dev

客户端套接字未完全收到服务器端套接字发送的内容

来自分类Dev

使用套接字将值从服务器发送到客户端

来自分类Dev

如何将数据从Web套接字服务器发送到客户端?

来自分类Dev

Spring Integration和TCP服务器套接字-如何向客户端发送消息?

来自分类Dev

套接字服务器无法接收客户端发送的消息

来自分类Dev

通过ActionScript服务器和Java客户端之间的套接字发送对象

来自分类Dev

Java套接字-将数据从服务器发送到客户端

来自分类Dev

服务器无法通过C中的套接字向客户端发送消息

来自分类Dev

Java多线程套接字客户端/服务器:发送和接收Enummap对象

来自分类Dev

Java套接字-将数据从客户端发送到服务器

来自分类Dev

从Node JS Socket客户端向MINA套接字服务器发送消息

来自分类Dev

C posix套接字,无法从客户端向服务器发送数据

来自分类Dev

Python套接字服务器/客户端编程

来自分类Dev

C客户端/服务器套接字错误

来自分类Dev

服务器/客户端套接字连接

来自分类Dev

套接字编程-简单的客户端/服务器

来自分类Dev

客户端js上的套接字服务器?

来自分类Dev

Java客户端/服务器套接字问题

来自分类Dev

Java TCP 客户端/服务器套接字

来自分类Dev

在客户端服务器套接字连接中正确传输文件

Related 相关文章

  1. 1

    使用套接字从服务器向客户端发送静态文件

  2. 2

    通过python中的TCP套接字在客户端-服务器之间发送文件?

  3. 3

    使用C中的套接字将文件从客户端发送到服务器

  4. 4

    使用python套接字将Txt文件从客户端发送到服务器

  5. 5

    使用套接字C#客户端/服务器发送文件

  6. 6

    通过python中的TCP套接字在客户端-服务器之间发送文件?

  7. 7

    在套接字客户端服务器中发送多个文件

  8. 8

    TCP套接字,发送文件,客户端服务器,服务器不保存整个文件,C语言

  9. 9

    套接字io,节点js,从服务器向客户端发送图像/文件的简单示例

  10. 10

    客户端套接字未完全收到服务器端套接字发送的内容

  11. 11

    使用套接字将值从服务器发送到客户端

  12. 12

    如何将数据从Web套接字服务器发送到客户端?

  13. 13

    Spring Integration和TCP服务器套接字-如何向客户端发送消息?

  14. 14

    套接字服务器无法接收客户端发送的消息

  15. 15

    通过ActionScript服务器和Java客户端之间的套接字发送对象

  16. 16

    Java套接字-将数据从服务器发送到客户端

  17. 17

    服务器无法通过C中的套接字向客户端发送消息

  18. 18

    Java多线程套接字客户端/服务器:发送和接收Enummap对象

  19. 19

    Java套接字-将数据从客户端发送到服务器

  20. 20

    从Node JS Socket客户端向MINA套接字服务器发送消息

  21. 21

    C posix套接字,无法从客户端向服务器发送数据

  22. 22

    Python套接字服务器/客户端编程

  23. 23

    C客户端/服务器套接字错误

  24. 24

    服务器/客户端套接字连接

  25. 25

    套接字编程-简单的客户端/服务器

  26. 26

    客户端js上的套接字服务器?

  27. 27

    Java客户端/服务器套接字问题

  28. 28

    Java TCP 客户端/服务器套接字

  29. 29

    在客户端服务器套接字连接中正确传输文件

热门标签

归档