需求:

创建UDP客户端实现利用TFTP协议从服务器上下载文件与上传文件。

代码实现过程:

#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <unistd.h>
#include <string.h>
#include <sys/socket.h>
#include <pthread.h>#define ERR_MSG(msg) do{\fprintf(stderr,"line : %d\n",__LINE__);\perror("msg");\
}while(0)#define IP "192.168.8.130" //填本機ubantuIP ifconfig查看
#define PORT 69             //1024~49151#define FIL "download.png"char buf[600] = "";
ssize_t res = 0;
int sfd = 0;
socklen_t addrlen = 0;
short num = 0;
unsigned short numS = 1;void* funcS(void* arg){struct sockaddr_in sein = *((struct sockaddr_in*)arg);int fdS = open("upload.c",O_RDONLY);if(fdS < 0){ERR_MSG(open);return NULL;}while(1){bzero(buf,sizeof(buf));if(recvfrom(sfd,buf,sizeof(buf),0,(struct sockaddr*)&sein,&addrlen) < 0){ERR_MSG(recvfrom);return NULL;}bzero(buf,sizeof(buf));sprintf(buf,"%c%c",0,3);*(short*)(buf+2) = htons(numS);// *(short*)(buf+2) = htons(numS);res = read(fdS,buf+4,512);printf("numS = %d htons(numS) = %d num = %d res = %ld\n",numS,htons(numS),num,res);if(res < 0){ERR_MSG(read);return NULL;}//  printf("buf = %s\n",buf+4);if(sendto(sfd,buf,res+4,0,(struct sockaddr*)&sein,sizeof(sein)) < 0){ERR_MSG(sendto);return NULL;}if(res != 512){printf("文件上传完毕\n");break;}numS++;}
}void* funcR(void* arg){struct sockaddr_in sein = *((struct sockaddr_in*)arg);int flag = 0;int fdR = -1;unsigned short numC = 0;while(1){//接受if(0 == flag){fdR = open(FIL,O_RDWR|O_CREAT|O_TRUNC,0664);if(fdR < 0){ERR_MSG(open);return NULL;}    flag=1;}//UDP是无连接不可靠的,数据包可能会重复接收到的通信//可以在本地记录每次收到的包的编号//如果本地记录的包的编号与数据包发送回来的块编号不一致,则不处理//if(htons(numC+1) == *(unsigned short*)(buf+2)){bzero(buf,sizeof(buf));res = recvfrom(sfd,buf,sizeof(buf),0,(struct sockaddr*)&sein,&addrlen);short *p1 = (short*)(buf+2);num = ntohs(*p1);printf("num = %d res = %ld\n",num,res);if(res < 0){ERR_MSG(recv);return NULL;}if(write(fdR,buf+4,res-4) < 0){ERR_MSG(write);return NULL;}bzero(buf,sizeof(buf));short *p2 = (short*)buf;*p2 = htons(4);short *p3 = p2+1;*p3 = htons(num);if(sendto(sfd,buf,4,0,(struct sockaddr*)&sein,sizeof(sein)) < 0){ERR_MSG(sendto);return NULL;}if(res!=516){fprintf(stderr,"文件下载完毕\n");close(fdR);break;}numC++;//}}
}int main(int argc, const char *argv[])
{//創建报式套接字sfd = socket(AF_INET,SOCK_DGRAM,0);if(sfd < 0){ERR_MSG(socket);return -1;}//填充地址信息結構體//根據地址族的不同,地址信息結構體不一致,AF_INET:man 7 ipstruct sockaddr_in sein;sein.sin_family      = AF_INET;         //必須填AF_INETsein.sin_port       = htons(PORT);     //端口號的網絡字節序,1024~49151sein.sin_addr.s_addr = inet_addr(IP);    //本機IP地址的網絡字節序,ifconfigaddrlen = sizeof(sein);char choose = 0;int size = 0;pthread_t tidS,tidR;while(1){printf("-------------------------\n");printf("---------1.download------\n");printf("---------2.upload--------\n");printf("---------3.exit----------\n");printf("-------------------------\n");printf("请输入>>>");choose = getchar();getchar();switch(choose){case '1'://do_download//发送下载请求    bzero(buf,sizeof(buf));size = sprintf(buf,"%c%c%s%c%s%c",0,1,"5.png",0,"octet",0);printf("buf = %s size = %d \n",buf+1,size);if(sendto(sfd,buf,size,0,(struct sockaddr*)&sein,sizeof(sein)) < 0){ERR_MSG(send);return 0;}printf("send success\n");if( pthread_create(&tidR,NULL,funcR,&sein) != 0){ERR_MSG(pthread_create);return -1;}pthread_join(tidR,NULL);break;case '2'://do_upload发送上传请求bzero(buf,sizeof(buf));size = sprintf(buf,"%c%c%s%c%s%c",0,2,"upload.c",0,"octet",0);if(sendto(sfd,buf,size,0,(struct sockaddr*)&sein,sizeof(sein)) < 0){ERR_MSG(send);return 0;}printf("send success\n");if( pthread_create(&tidS,NULL,funcS,&sein) != 0){ERR_MSG(pthread_create);return -1;}pthread_join(tidS,NULL);break;case '3':printf("程序退出\n");return 0;}}close(sfd);return 0;
}

代码实现结果:

基于UDP的TFTP文件下载与上传相关推荐

  1. 基于华为云obs实现文件上传下载(技术栈mysql+springboot+Maven+jsp+java)的技术分享

    基于华为云obs实现文件上传下载(技术栈mysql+springboot+jsp+java)的技术分享 obs实现文件上传下载 前言 一.OBS是什么? 二.使用步骤 1.1 前期准备 2 工具的内容 ...

  2. tftp在put上传的时候显示File not found的解决办法

    tftp在put上传的时候显示File not found的解决办法 在linux下,不管使用的是哪一种super-server,inetd或者xinetd,默认情况下TFTP服务是禁用的,所以要修改 ...

  3. ASP.NET Web API实现简单的文件下载与上传

    ASP.NET Web API实现简单的文件下载与上传.首先创建一个ASP.NET Web API项目,然后在项目下创建FileRoot目录并在该目录下创建ReportTemplate.xlsx文件, ...

  4. antd的联级选择器异步调用编辑回显_react-uplod-img 是一个基于 React antd组件的图片上传组件...

    react-uplod-img 是一个基于 React antd组件的图片上传组件 支持oss qiniu等服务端自定义获取签名,批量上传, 预览, 删除, 图片精确的尺寸限制 排序等功能 需要 re ...

  5. 前端基于element组件的语音文件上传

    前端基于element组件的语音文件上传 原理 项目采用的是element组件的UI库,基于标签,实现基本的文件上传功能,并基于标签内置的触发事件,实现了对语音文件大小,格式,上传前确认,上传后显示已 ...

  6. 学习日志day41(2021-09-03)(1、文件的上传 2、文件的查看 3、文件的下载 4、使用工具类上传文件 5、基于servlet3.0以上的文件上传 )

    学习内容:学习JavaWeb(Day41) 1.文件的上传 2.文件的查看 3.文件的下载 4.使用工具类上传文件 5.基于servlet3.0以上的文件上传 1.文件的上传 (1)实现文件的上传需要 ...

  7. 基于element-ui的图片转码上传服务器

      毕业后回公司搬砖了,今天记录一下基于element-ui的图片转码上传问题.先说一下页面逻辑,上传图片到服务器,先把图片和图片信息转码成字符串,然后传给后台. 先看看页面实现的效果:   这里用的 ...

  8. 基于fastDFS和elementUI的文件上传(只要后端有数据,一通百通。)

    基于elementUI和fastDFS的文件上传 只要数据传到后端,啥都好说,进不去白瞎,所以不管是fastDFS还是别的,一通百通(只是时间问题) 准备 <dependency>< ...

  9. [C# 网络编程系列]专题十一:实现一个基于FTP协议的程序——文件上传下载器...

    引言: 在这个专题将为大家揭开下FTP这个协议的面纱,其实学习知识和生活中的例子都是很相通的,就拿这个专题来说,要了解FTP协议然后根据FTP协议实现一个文件下载器,就和和追MM是差不多的过程的,相信 ...

最新文章

  1. python【蓝桥杯vip练习题库】BASIC-11 十六进制转十进制
  2. nema0183 java解析_NEMA 0183 语句解析
  3. C#操作Access数据库
  4. Atom React或前端插件推荐
  5. js中 switch 注意事项
  6. 中职学校计算机教学参考文献,学生计算机论文,关于中职学校计算机专业教学现状相关参考文献资料-免费论文范文...
  7. Atitit 开发效率的提升艺术 艾提拉著 目录 1. 主要几个层次上简化开发 2 1.1. 管理创新 2 1.2. 开发体系方法使用简单方法 2 1.3. 技术选型使用简单框架模式 2 1.4.
  8. allergo 命令
  9. 彻底删除浏览器毒霸首页
  10. “不学数学就去当厨子”,兰大校友入选全球竞赛最强10人,决赛最后几小时才想起做题...
  11. C# async / await 任务超时处理
  12. 我的RUST学习 ——【第九章 9-2】Result 与 可恢复的错误
  13. 小程序快递单号查询接口物流助手对接指南
  14. 成为人生的赢家都有哪些书_那么,我们是否有代码挑战#1的赢家?
  15. POJ-3426-0-1背包Charm Bracelet
  16. OpenStack T版服务组件--Keyston身份服务
  17. 龙芯版UOS 自带浏览器无法使用flash在线播放视频
  18. AAL模板及脑区功能介绍
  19. MFC程序最小化到托盘
  20. 文件IO中read()函数读取输出字符串有乱码

热门文章

  1. python获取字典长度_Python中的字典
  2. galaxy buds耳机一只耳机断开连接
  3. C++水电管理信息系统
  4. Elasticsearch 分片管理解析
  5. ATM跨行查询也开始收费了
  6. 对一个windows2000注册表项的粗略分析(转)
  7. 图解如何修改github个人空间地址
  8. Linux文件系统概览
  9. Flex 弹性布局教程以及对主轴 交叉轴的理解 :语法篇
  10. Nginx+Lua 实现灰度发布详细步骤