2

我必须使用 UDP 进行服务器-客户端文件传输。我创建了一个接收客户端发送的消息的基本服务器。就这样。现在是主要部分:-

1. The message sent by client is the name of file .
2. Now the server checks whether there exists this file or not .
3. If there exists it sends the file to the client and it also keeps the count of the     number of requests of file made by the client .

我是新手,我不知道如何进一步进行。

这是服务器代码

#include<sys/socket.h>
#include<arpa/inet.h>
#include<stdio.h>
#include<unistd.h>
#include<fcntl.h>
#include<sys/types.h>
#include<string.h>




int main()
{

  char buff[2000];
  char file_buffer[2000];
  int sd,connfd,len;

  struct sockaddr_in servaddr,cliaddr;

  sd = socket(AF_INET, SOCK_DGRAM, 0);

  if(sd==-1)
    {
      printf(" socket not created in server\n");
      exit(0);
    }
  else
    {
      printf("socket created in  server\n");
    }

  bzero(&servaddr, sizeof(servaddr));

  servaddr.sin_family = AF_INET;
  servaddr.sin_addr.s_addr = INADDR_ANY;
  servaddr.sin_port = htons(7802);

  if ( bind(sd, (struct sockaddr *)&servaddr, sizeof(servaddr)) != 0 )
    printf("Not binded\n");
  else
    printf("Binded\n");



  len=sizeof(cliaddr);

  recvfrom(sd,buff,1024,0,
   (struct sockaddr *)&cliaddr, &len);

  printf("%s\n",buff);
  /* */
  FILE *fp;
  fp=fopen(buff,"r");
  if(fp==NULL)
    {
      printf("file does not exist\n");
    }

  fseek(fp,0,SEEK_END);
  size_t file_size=ftell(fp);
  fseek(fp,0,SEEK_SET);
  if(fread(file_buffer,file_size,1,fp)<=0)
    {
      printf("unable to copy file into buffer\n");
      exit(1);
    }
  if(sendto(sd,file_buffer,strlen(file_buffer),0,  (struct sockaddr *)&cliaddr, &len)<0)    {
    printf("error in sending the file\n");
    exit(1);
  }
  bzero(file_buffer,sizeof(file_buffer));


  /* */
  close(sd);

  return(0);
}

这是客户端代码

#include <stdio.h>
#include <errno.h>
#include <sys/socket.h>
#include <resolv.h>
#include<netinet/in.h>
#include<sys/types.h>



int main()
{
    char buff[2000];
    int sockfd,connfd,len;

struct sockaddr_in servaddr,cliaddr;

// create socket in client side
sockfd = socket(AF_INET, SOCK_DGRAM, 0);

if(sockfd==-1)
{
    printf(" socket not created in client\n");
    exit(0);
}
else
{
    printf("socket created in  client\n");
}


bzero(&servaddr, sizeof(servaddr));

servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = INADDR_ANY; // ANY address or use specific address
servaddr.sin_port = htons(7802);  // Port address


    printf("Type ur  UDP client message\n");
    scanf("%s",buff);

// send  msg to server

sendto(sockfd, buff, strlen(buff), 0,
          (struct sockaddr *)&servaddr, sizeof(struct sockaddr));
      char file_buffer[2000];

    if (recvfrom(sockfd,file_buffer,2000,0,  (struct sockaddr *)&servaddr, sizeof(struct sockaddr))<0)
    {
      printf("error in recieving the file\n");
      exit(1);
    }

  char new_file[]="copied";
  strcat(new_file,buff);
  FILE *fp;
  fp=fopen(new_file,"w+");
  if(fwrite(file_buffer,1,sizeof(file_buffer),fp)<0)
    {
      printf("error writting file\n");
      exit(1);
    }


  //close client side connection
    close(sockfd);

return(0);
}

我已经编辑了程序并创建了一个新的缓冲区 file_buffer ,服务器从文件中读取数据并将其写入并发送到客户端,另一端客户端接收数据并复制该文件并写入其中。但是在编译时它会在写入文件时出错:(

4

3 回答 3

1

您将不得不在这两个地方扩展逻辑。基本上对于服务器代码,您可以使用 buff 作为文件名并检查它是否存在。您可以使用 "fopen (buff, "r" )" -- 如果返回 NULL,则该文件不存在,在这种情况下,您可能希望向客户端发送一条说明该文件不存在的说明。像这样的东西:

FILE *istream;
strncpy(fileName, buff, ret_len + 1);
if ( (istream = fopen(fileName, "r" ) ) == NULL ){
    printf ( "file non-existant!\n" );
    strncpy(buff, "Does not Exist", strlen("Does Not Exist"));
} else {
    printf ( "file exists!\n" );
    strncpy(buff, "Does Exist", strlen("Does Exist"));
    fclose (istream );
}

ret_len = sendto(sd, buff, strlen(buff), 0, (struct sockaddr *)&cliaddr, sizeof(struct sockaddr));
if (ret_len < 0) {
fprintf(stderr, "sendto() failed [ret value: %d]\n", ret_len);
return -1;
}

如果文件存在,则读取文件并将内容发送到文件。

客户端在将缓冲区发送到服务器后,必须从服务器执行 recvfrom() !像这样的东西。请注意,您可以使用数值(-1 或 0)来指示文件是否存在。如果文件存在,您可能可以在初始消息中传递文件长度——这样,客户端就会知道它需要读取多少数据。

// send  msg to server
sendto(sockfd, buff, strlen(buff) + 1, 0, (struct sockaddr *)&servaddr, sizeof(struct sockaddr));

// recveive from server
ret_len = recvfrom(sockfd, buff, 1024, 0, NULL, 0);
printf("Received from server: %s \n",buff);

if (strncmp(buff, "Does not Exist", strlen("Does not Exist")) == 0)
    printf("File does not exist\n");
else if (strncmp(buff, "Does Exist", strlen("Does Exist")) == 0)
    printf("File does exist\n");
else
    printf("Unknown message\n");

顺便说一句,在上面的代码中,我们需要加 1 来说明 NUL 字符。此外,一旦完成此步骤,客户端代码应在循环中调用 recvfrom() 以从服务器接收数据,如前面步骤中所述。

请注意,如果文件太大,那么您可能只想像要发送的消息一样读取它——使用 UDP,您最多可以发送 64K,但理想情况下您应该只发送最多 1 个 MUT(大约 1500 个字节)。

于 2013-09-01T07:40:00.583 回答
1

我不确定您是否必须开发自己的客户端/服务器,或者您是否可以使用其他人?还有其他一些基于 UDP 的开源文件传输系统,例如UDTUFTPTsunami-UDP,甚至是 Google 的QUIC

于 2015-07-15T14:56:30.330 回答
0

您希望服务器表现得像 FTP 服务器吗?

从客户端收到文件名后,检查它是否存在。请参阅检查文件是否存在于 C 中的最佳方法是什么?(跨平台)。然后打开文件并将它的缓冲区(例如一次200字节)发送给客户端。同时,客户端收到它并写入一个名为filename的新文件。

于 2013-09-01T07:47:08.990 回答