簡體   English   中英

使用C將文件從服務器發送到Linux上的客戶端

[英]Send file from Server to Client on Linux in C

我對此代碼有疑問。 問題是我必須用這種期貨開發一個客戶端-服務器模型:

  1. 客戶端類型:“ GETfile_name.txt”;
  2. 服務器接收請求並發送文件的大小;
  3. 服務器發送文件;

問題在於服務器不將文件發送到客戶端。 感謝大家的幫助。

代碼是這樣的:

服務器:

f = fopen(file_name,"r");

/* file's size */
fseek(f,0L,SEEK_END);
size = ftell(f);
fseek(f,0L,SEEK_SET);

/* convert int to string */
sprintf(file_size,"%d",size); 

/* send file's size to the client */
Send(s,file_size,sizeof(file_size)); 

/* send file to the client */
buffer = (char *) malloc(sizeof(char)*size);  
bzero(buffer,sizeof(char)*size);
x = fread(binoltro,sizeof(char),sizeof(char)*dimensione,f);
Send(s,binoltro,x);

客戶:

/* wait file's size */
recv(s,buffer,MAX,0); 
printf("Remote server will send: %s Bytes\n",buffer);
size = atoi(buffer);

/* execute malloc */
buffer = (char *) malloc(sizeof(char)*size);
bzero(buffer,size*sizeof(char));

Recv(s,buffer,size*sizeof(char));
fwrite(buffer,sizeof(char),size*sizeof(char),f);
printf("File: %s",buffer);

/* clean the buffer */
bzero(buffer,MAX);

/* do free */
free(buffer);
fclose(f);

帶有:

int Recv (int s, char *ptr, size_t maxlen){
size_t n;
ssize_t nread;
char c;

for (n=1; n<maxlen; n++)
{
    nread=recv(s, &c, 1, 0);
    if (nread == 1)
    {
        *ptr++ = c;
        if (c == '\n')
            break;
    }
    else if (nread == 0)    
    {
        *ptr = 0;
        return (n-1); 
    }
    else
        return (-1); 
}
*ptr = 0;
return (n);
}

和:

int Send(int s, char *ptr, size_t nbytes){
size_t  nleft;
ssize_t nwritten;

for (nleft=nbytes; nleft > 0; )
{
    nwritten = send(s, ptr, nleft, 0);
    if (nwritten <=0)
        return (nwritten);
    else
    {
        nleft -= nwritten;
        ptr += nwritten;
    }
}
return (nbytes - nleft); 
}

我看到的問題是,當您的Recv()函數接收到'\\ n'或沒有更多數據或達到maxlen時,它就會中斷。 在您的客戶端收到文件長度的最后一個字節后,這些條件均不匹配,因此它將繼續讀取並且文件數據丟失。

我建議您使用來將文件長度填充為固定位數(例如10)

sprintf( file_size, "%010s", size );

並使用經過修改的Recv()函數,如下所示:

int Recv (int s, char *ptr, size_t nbytes ){
    size_t n;
    ssize_t nread;


    while( nbytes > 0 ) {
        if( (nread = recv( s, ptr, nbytes, 0 )) <= 0 )
            return -1; /* Error */

        ptr += nread;
        nbytes -= nread;
    }
    +ptr = '\0';
    return 0; /* OK */
}

然后,您的客戶端可以首先使用讀取文件大小

Recv( s, buffer, 10 )

然后使用

Recv( s, ..., atoi( buffer ) )

由於Recv()添加了'\\ 0',因此請確保分配文件大小+ 1

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM