思维导图
使用tftp实现简单文件的上传
#include <head.h>
#define SER_PORT 69
#define SER_IP "192.168.125.223"
int link_file()
{int sfd=socket(AF_INET,SOCK_DGRAM,0);if(sfd==-1){perror("socket error");return -1;}return sfd;
}
int filedownload()
{//创建文件描述符用于下载传输过来的数据包int wfd=-1;if((wfd=open("./copy_file",O_WRONLY|O_CREAT|O_TRUNC,0664))==-1){perror("open error:");return -1;}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 socklen=sizeof(sin);int sfd=-1;if((sfd=link_file())==-1){printf("链接失败\n");return -1;}//封装请求下载数据包//第一块char buf[516]="";short *p1=(short*)buf;*p1=htons(1);//第二模块printf("请输入你要下载的文件:");char file[50];scanf("%s",file);char *p2=buf+2;strcpy(p2,file);//第三模块char *p3=p2+strlen(p2)+1;strcpy(p3,"octet");int len=4+strlen(p2)+strlen(p3);sendto(sfd,buf,len,0,(struct sockaddr*)&sin,sizeof(sin));while(1){int res=0;if((res=recvfrom(sfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,&socklen))<0){perror("recvfrom error:");return -1;}char *data_point=buf+4;short *cmd_point=(short*)buf;short *block_point=(short*)(buf+2);if(res<516){write(wfd,data_point,res-4);printf("文件拷贝完成!\n");break;}write(wfd,data_point,512); //完成了一次拷贝要向客户端发送ACK包char ack[4];short *p1=(short*)ack;short *p2=(short*)(ack+2);*p1=htons(4);*p2=*block_point;sendto(sfd,ack,4,0,(struct sockaddr*)&sin,sizeof(sin));}
}
int fileonload()
{int sfd=link_file();system("ls");printf("请问你要上传的文件是:");char file[50];scanf("%s",file);//打开文件用于读取上传文件的数据int send_fd=-1;if((send_fd=open(file,O_RDONLY))==-1){perror("open error:");return -1;}//填充信息结构体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 socklen=sizeof(sin);//封装请求下载数据包//第一块char buf[516]="";short *p1=(short*)buf;*p1=htons(2);//第二模块char *p2=buf+2;strcpy(p2,file);//第三模块 int broadcast_permission=1;char *p3=p2+strlen(p2)+1;strcpy(p3,"octet");int len=4+strlen(p2)+strlen(p3);sendto(sfd,buf,len,0,(struct sockaddr*)&sin,sizeof(sin));char *data_point=buf+4;short *cmd_point=(short*)buf;*cmd_point=htons(3);short *block_point=(short*)(buf+2);*block_point=htons(1);int i=1;while(1){recvfrom(sfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,&socklen);if(*cmd_point==htons(4)){int res=read(send_fd,buf+4,512);if(res==0){printf("拷贝完成,按任意键退出\n");break;}*cmd_point=htons(3);sendto(sfd,buf,res+4,0,(struct sockaddr*)&sin,socklen);}}
}
int main(int argc, const char *argv[])
{while(1){printf("==========欢迎使用文件下载客户端==========\n");printf("1、下载文件\t2、上传文件\t0、退出\n");printf("请输入你要执行的操作:");int cmd;scanf("%d",&cmd);switch(cmd){case 1:{filedownload();break;}case 2:{fileonload();break;}case 0:{system("clear");return 0;}default:{printf("输入有误\n");}}while(getchar()=='\n');system("clear");}return 0;
}