> 文章列表 > 基于UDP的文件传输程序代码

基于UDP的文件传输程序代码

基于UDP的文件传输程序代码

1、基于UDP的TFTP文件传输

#include<stdio.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>
#include<netinet/ip.h>
#include<string.h>
#include<arpa/inet.h>
#include<unistd.h>
#include<sys/stat.h>
#include<fcntl.h>
#define ERR_MSG(msg) do{\\fprintf(stderr,"%d",__LINE__);\\perror("msg");\\
}while(0)#define SER_IP "192.168.2.131"
#define SER_PORT 69#define CLI_IP "192.168.0.111"
#define CLI_PORT 7777void Download();void Upload();int main(int argc, const char *argv[])
{int option =-1;while(1){printf("************************\\n");printf("********1、下载*********\\n");printf("********2、上传*********\\n");printf("********3、退出*********\\n");printf("************************\\n");printf("************************\\n");scanf("%d",&option);while(getchar() != 10);if(1 == option)Download();else if(2 == option)Upload();else if(3 == option)break;}//关闭return 0;
}void Download()
{//创建报式套接字int cfd = socket(AF_INET,SOCK_DGRAM,0);if(cfd < 0){ERR_MSG("socket");return;}char buf[516]={0};//创建填充服务器地址信息结构体struct sockaddr_in sin;sin.sin_family      = AF_INET;sin.sin_port        = htons(SER_PORT);sin.sin_addr.s_addr = inet_addr(SER_IP);socklen_t addrlen = sizeof(sin);//设置读请求*(short*)buf = htons(1);//printf("%hd\\t__%d__\\n",ntohs(*(short*)buf),__LINE__);//将文件名写入到buf中printf("请输入要下载的文件名>>>>>>\\n");scanf("%s",buf+2);while(getchar() != 10);char pathname[128]="";strcpy(pathname,buf+2);strcpy(buf+2+strlen(buf+2)+1,"octet");//printf("%hd %s %s\\n",ntohs(*(short*)buf),buf+2,buf+2+strlen(buf+2)+1);     char *p1 = buf+2+strlen(buf+2)+1;int size = 4 + strlen(buf+2)+strlen(p1)+1;//发送数据if(sendto(cfd,buf,size,0,(struct sockaddr*)&sin,sizeof(sin)) < 0){ERR_MSG("sendto");return;}printf("发送成功   size=%d\\n",size);ssize_t res = 0,num = -1;short count=1;int fd = -1;;while(1){//接收数据bzero(buf,sizeof(buf));res = recvfrom(cfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,&addrlen);if(res < 0){ERR_MSG("recvfrom");return;}//  printf("[%s:%d]: %s\\n",inet_ntoa(rcvaddr.sin_addr),ntohs(rcvaddr.sin_port),buf);//  printf("%d : %d\\t%s\\n",ntohs(*(short*)buf),ntohs(*(short*)(buf+2)),buf+4);if(ntohs(*(short*)buf) == 3){if(1 == ntohs(*(short*)(buf+2))){//创建文件fd = open(pathname,O_WRONLY|O_CREAT|O_TRUNC,0664);if(fd < 0){ERR_MSG("open");return;}}if(ntohs(*(short*)(buf+2)) == count){num = write(fd,buf+4,res-4);if(num < 0){ERR_MSG("read");break;}else if(num < 512){printf("Download sucess\\n");break;}//发送数据bzero(buf,sizeof(buf));*(short *)buf = htons(4);*((short *)(buf+2))=htons(count++);if(sendto(cfd,buf,4,0,(struct sockaddr*)&sin,sizeof(sin)) < 0){ERR_MSG("sendto");return ;}}}else if(ntohs(*(short *)buf) == 5){printf("%s  __%d__\\n",buf+4,__LINE__);break;}//  printf("发送成功\\n");}close(fd);close(cfd);}
void Upload()
{//创建报式套接字int cfd = socket(AF_INET,SOCK_DGRAM,0);if(cfd < 0){ERR_MSG("socket");return;}char buf[516]={0};//创建填充服务器地址信息结构体struct sockaddr_in sin;sin.sin_family      = AF_INET;sin.sin_port        = htons(SER_PORT);sin.sin_addr.s_addr = inet_addr(SER_IP);socklen_t addrlen = sizeof(sin);//设置写请求*(short*)buf = htons(2);//printf("%hd\\t__%d__\\n",ntohs(*(short*)buf),__LINE__);//将文件名写入到buf中printf("请输入要上传的文件名>>>>>>\\n");scanf("%s",buf+2);while(getchar() != 10);char pathname[128]="";strcpy(pathname,buf+2);strcpy(buf+2+strlen(buf+2)+1,"octet");//  printf("%hd %s %s\\n",ntohs(*(short*)buf),buf+2,buf+2+strlen(buf+2)+1);     char *p1 = buf+2+strlen(buf+2)+1;int size = 4 + strlen(buf+2)+strlen(p1)+1;//发送数据if(sendto(cfd,buf,size,0,(struct sockaddr*)&sin,sizeof(sin)) < 0){ERR_MSG("sendto");return;}printf("发送成功   size=%d\\n",size);ssize_t res = 0,num = -1;short count=0;int flag = 1;int fd = -1;;while(1){//接收数据bzero(buf,sizeof(buf));res = recvfrom(cfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,&addrlen);if(res < 0){ERR_MSG("recvfrom");return;}//  printf("*****%d*****%d*****\\n",ntohs(*(short*)buf),ntohs(*(short*)(buf+2)));if(ntohs(*(short *)buf) == 5){printf("*******************%d  __%d__\\n",ntohs(*(short*)(buf+2)),__LINE__);break;}//  printf("[%s:%d]: %s\\n",inet_ntoa(rcvaddr.sin_addr),ntohs(rcvaddr.sin_port),buf);else if(ntohs(*(short*)buf) == 4){if(flag == 1){//创建文件fd = open(pathname,O_RDONLY);if(fd < 0){ERR_MSG("open");return;}flag = 0;}if(ntohs(*(short*)(buf+2)) != count){lseek(fd,512*(ntohs(*(short*)(buf+2))),SEEK_SET);count = ntohs(*(short*)(buf+2));}if(ntohs(*(short*)(buf+2)) == count){//      printf("%s",buf+4);bzero(buf,sizeof(buf));//发送数据*(short *)buf = htons(3);*((short *)(buf+2))=htons(++count);res = read(fd,buf+4,512);if(res < 0){ERR_MSG("read");break;}///if(count ==5)count++;        //手动产生错误包,修改文件偏移量后读取数据并发送/////      printf("%d : %d\\t%s\\n",ntohs(*(short*)buf),ntohs(*(short*)(buf+2)),buf+4);if(res == 0){printf("Update sucess\\n");break;}if(sendto(cfd,buf,res+4,0,(struct sockaddr*)&sin,sizeof(sin)) < 0){ERR_MSG("sendto");return ;}}}//  printf("发送成功\\n");}close(fd);close(cfd);}                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      

ubuntu@ubuntu:TFTP$ gcc 02_udpCli_TFTP.c 
ubuntu@ubuntu:TFTP$ ./a.out 
************************
********1、下载*********
********2、上传*********
********3、退出*********
************************
1
请输入要下载的文件名>>>>>>
5.png
1 5.png octet
发送成功   size=15
Download sucess
************************
********1、下载*********
********2、上传*********
********3、退出*********
************************
^C
ubuntu@ubuntu:TFTP$ ls
02_udpCli_TFTP.c  2       5      a.out  asd.c     d         huahua.c
1.png             2octet  5.png  asd    asdoctet  dict.txt
ubuntu@ubuntu:TFTP$ eog 5.png
ubuntu@ubuntu:TFTP$