华清远见嵌入式学习——网络编程——作业3

目录

作业要求:基于UDP的TFTP文件传输

代码

下载功能效果图​编辑

上传功能效果图

思维导图

模拟面试题和答案(定期更新)


作业要求:基于UDP的TFTP文件传输

完成文件的上传和下载功能

代码

#include<myhead.h>

//实现下载功能
int do_download(int cfd, struct sockaddr_in sin)
{
	//定义变量存储下载请求包
	char buf[516] = "";
	//定义变量存储文件名
	char fileName[40] = "";

	printf("请输入文件名:");
	scanf("%s", fileName);
	getchar();

	//组装请求包
	short *p1 = (short *)buf;
	*p1 = htons(1);                 //写1表明要下载

	char *p2 = buf+2;           //文件名段
	strcpy(p2, fileName);

	char *p3 = p2+strlen(p2)+1;    //模式段
	strcpy(p3, "octet");

	int size = 4 + strlen(p2) + strlen(p3);      //要发送的请求包的大小

	//向服务器发送下载请求
	if(sendto(cfd, buf, size, 0, (struct sockaddr*)&sin, sizeof(sin)) == -1)
	{
		perror("sendto error");
		return -1;
	}

	printf("请求成功\n");

	socklen_t socklen = sizeof(sin);
 
	//打开一文件接受下载文件
	int fd = open(fileName,O_RDWR|O_TRUNC|O_CREAT,0666);
	if(fd<0)
	{
		perror("open error");
		return -1;
	}
	int  res;
	while(1){
		//接受数据包
		bzero(buf,sizeof(buf));
		res = recvfrom(cfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,&socklen);
		if(res<0)
		{
			perror("recvfrom error");
			return -1;
		}
 
		if(buf[1]==3)
		{
			//写入文件
			if(write(fd,buf+4,res-4)<0)
			{
				perror("write");
				return -1;
			}
 
			//构造ACK
			buf[1] = 4;
			//发送ACK
			if(sendto(cfd,buf,4,0,(struct sockaddr*)&sin,sizeof(sin))<0)
			{
				perror("sendto");
				return -1;
			}
 
			//判断数据包中的数据大小
			if(res-4<512)
			{
				printf("%s 下载完毕\n",fileName);
				break;
			}
		}else if(buf[1]==5)
		{
			printf("%d %s\n",ntohs(*(short*)(buf+2)),buf+4);
			break;
		}
	}
	close(fd);	
	return 0;
}

//实现上传功能
int do_upload(int cfd,struct sockaddr_in sin)
{
	//定义变量存储上传请求包
	char buf[516] = "";
	//定义变量存储文件名
	char fileName[40] = "";

	printf("请输入文件名:");
	scanf("%s", fileName);
	getchar();

	//组装请求包
	short *p1 = (short *)buf;
	*p1 = htons(2);                 //写2表明要上传

	char *p2 = buf+2;           //文件名段
	strcpy(p2, fileName);

	char *p3 = p2+strlen(p2)+1;    //模式段
	strcpy(p3, "octet");

	int size = 4 + strlen(p2) + strlen(p3);      //要发送的请求包的大小

	//向服务器发送上传请求
	if(sendto(cfd, buf, size, 0, (struct sockaddr*)&sin, sizeof(sin)) == -1)
	{
		perror("sendto error");
		return -1;
	}

	printf("请求成功\n");

	socklen_t socklen = sizeof(sin);
 
	//打开准备上传的文件
	int fd = open(fileName,O_RDONLY);
	if(fd<0)
	{
		perror("open error");
		return -1;
	}
	int res1,res2;
	int kbh = 1;
	while(1)
	{
		//接受数据包
		bzero(buf,sizeof(buf));
		res1 = recvfrom(cfd,buf,4,0,(struct sockaddr*)&sin,&socklen);
		if(res1 < 0)
		{
			perror("recvfrom error");
			return -1;
		}
 
		//判断是否接收到服务器发来的ACK
		if(buf[1]==4)
		{
			//填充发送的数据包
			buf[1] = 3;
			buf[3] = kbh;
			
			res2 = read(fd,buf+4,512);
			if(res2 < 0)
			{
				perror("read error");
				return -1;
			}					

			//向服务器发送数据包
			if(sendto(cfd,buf,sizeof(buf),0,(struct sockaddr*)&sin,sizeof(sin)) == -1)
			{
				perror("sendto error");
				return -1;
			}
	
			//发一次块编号加一一次
			kbh++;
			
			//循环退出条件
			if(res2 < 512)
			{
				close(fd);
				printf("文件上传完毕\n");
				break;
			}
		}else if(buf[1]==5)
		{
			printf("%d %s\n",ntohs(*(short*)(buf+2)),buf+4);
			break;
		}
	}
	return 0;
}
int main(int argc, const char *argv[])
{
	if(argc != 2)
	{
		printf("input error\n");
		printf("usage:./a.out ip\n");
		return -1;
	}

	//1、创建套接字
	int cfd = socket(AF_INET, SOCK_DGRAM, 0);
	if(cfd == -1)
	{
		perror("socket error");
		return -1;
	}

	//2、填充服务器地址信息结构体
	struct sockaddr_in sin;
	sin.sin_family = AF_INET;
	sin.sin_port = htons(69);
	sin.sin_addr.s_addr = inet_addr(argv[1]);

	int menu = -1;
	while(1)
	{
		system("clear");                     //清屏
		printf("\t\t======1、下载=======\n");
		printf("\t\t======2、上传=======\n");
		printf("\t\t======0、退出=======\n");

		printf("请输入功能:");
		scanf("%d", &menu);
		getchar();

		//多分支选择
		switch(menu)
		{
			case 1:
				{
					do_download(cfd, sin);
				}
				break;

			case 2:
				{
					do_upload(cfd,sin);
				}
				break;
			case 0:
				goto POS;
			default:printf("输入功能有误,请重新输入\n");
		}

		//阻塞
		printf("输入任意键,按回车清空:");
		while(getchar() != '\n');
	}

POS:
	//关闭套接字
	close(cfd);


	return 0;
}

下载功能效果图

上传功能效果图

思维导图

(从第二章到第五章)

模拟面试题和答案(定期更新)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/180004.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

一站式解决Mac音视频转换需求——Xilisoft Video Converter Ultimate for Mac

在数字化时代&#xff0c;音视频的应用越来越广泛&#xff0c;不同的设备和平台对音视频格式的要求也不尽相同。因此&#xff0c;如何找到一款功能强大、易于操作的音视频转换软件成为了Mac用户的迫切需求。而Xilisoft Video Converter Ultimate for Mac&#xff08;曦力音视频…

亚马逊智能机器人Astro新升级!可为中小企业提供巡逻服务

原创 | 文 BFT机器人 Astro是Amzon近年来推出的一种新型的家用机器人&#xff0c;由智能助手Alexa驱动&#xff0c;主要用于家庭监控&#xff0c;如检查炉子、水龙头是否开着&#xff0c;以及其他任务。它将人工智能、计算机视觉、传感器技术以及语音和边缘计算方面的新进展汇…

linux -系统通用命令查询

有时候内网环境下&#xff0c;系统有些命令没有安装因此掌握一些通用的linux 命令也可以帮助我们解决一些问题查看 1.查看系统内核版本 uname -r2.查看系统版本 cat /etc/os-release3. 查看cpu 配置 lscpu4.查看内存信息 free [参数] 中各个数值的解释如下表 数值解释t…

宿主Linux——KVM安装Windows7系统

KVM虚拟技术 KVM(Kernel-based Virtual Machine) 是基于Linux内核的开源虚拟化技术&#xff0c;在一台物理机上可同时运行多个虚拟系统。KVM使用硬件虚拟化扩展&#xff0c;例如Intel的VT和AMD的AMD-V&#xff0c;在性能方面更加高效&#xff0c;可提供更好的计算能力和响应速…

启发式搜索算法-人工智能

第1关:评估函数和启发信息 第2关:A*搜索算法 class Array2D:"""说明:1.构造方法需要两个参数,即二维数组的 宽和高2.成员变量w和h是二维数组的宽和高3.使用:‘对象[x][y]’可以直接取到相应的值4.数组的默认值都是0"""def __init__(s…

Python语言创建爬虫代理ip池详细步骤和代码示例

作为长期游弋于代码世界中的程序猿来说&#xff0c;拥有自己的服务器以及代理池能够让自己网络爬虫更得心应手。那么新手如何创建自己的私有IP池呢&#xff1f;它的步骤又有哪些&#xff1f;带着这些问题我们意义探讨。 以我多年的爬虫经验创建一个IP池的大体上可以分为以下几个…

可上手 JVM 调优实战指南

文章目录 为什么要学 JVM一、JVM 整体布局二、Class 文件规范三、类加载模块四、执行引擎五、GC 垃圾回收1 、JVM内存布局2 、 JVM 有哪些主要的垃圾回收器&#xff1f;3 、分代垃圾回收工作机制 六、对 JVM 进行调优的基础思路七、 GC 情况分析实例八、最后总结 全程可上手JVM…

又下一城!文心中国行入厦,大模型助推区域产业智能化提速

11月22日&#xff0c;“文心中国行”落地厦门。活动现场&#xff0c;厦门火炬高技术产业开发区管委会、厦门市思明区政府授予百度飞桨“人工智能公共技术服务平台”并举行授牌仪式。来自当地政产学研各界的领导、专家、企业嘉宾分享了AI大模型的最新技术趋势、产教融合开源共创…

React16中打印事件对象取不到值的现象及其原因分析

React16中打印事件对象取不到值的现象及其原因分析 一、背景 在最近的开发过程中&#xff0c;遇到了一个看起来匪夷所思的问题❓&#xff1a; <Inputplaceholder"请输入"onChange{(e) > {console.log(e:, e)}}onKeyDown{handleKeyDown} />此时按理来说我…

畅谈Linux在小型微型企业中的应用

在这篇文章里我们讨论和畅谈一下linux系统在小微型企业中的应用&#xff0c;为什么会写这篇文章呢&#xff1f;因为在平时的工作中&#xff0c;认识的一些做小微型企业的朋友&#xff0c;他们经常找我咨询或是去解决一些平时工作中的IT相关的问题&#xff0c;那么小微型企业中的…

人物血条的制作_unity基础开发教程

人物血条的制作 场景创建导入素材血条制作血量控制代码部分 场景创建 随便创建一个地板、一个胶囊体&#xff0c;搭建一个简易的场景&#xff0c;我这里就继续使用前面文章创建的场景 导入素材 在unity编辑器中选择Window&#xff0c;点击Asset Store 点击Search online 在搜…

Course1-Week1:机器学习简介

Course1-Week1&#xff1a;机器学习简介 文章目录 Course1-Week1&#xff1a;机器学习简介1. 课程简介1.1 课程大纲1.2 Optional Lab的使用 (Jupyter Notebooks)1.3 欢迎参加《机器学习》课程 2. 机器学习简介2.1 机器学习定义2.2 有监督学习2.3 无监督学习 3. 线性回归模型3.1…

垂直领域生成式AI模型的矿业应用

快速发展的人工智能 (AI) 领域正在出现一种新范式&#xff1a;更小的、垂直的生成式 AI 模型。 这种方法不同于旨在解决许多问题的传统横向模型。 相反&#xff0c;它开发专门的人工智能模型来解决特定行业或垂直领域的问题。 垂直导向的生成式AI模型迎合特定行业&#xff0c;提…

【nlp】3.2 Transformer论文复现:1. 输入部分(文本嵌入层和位置编码器)

Transformer论文复现:输入部分(文本嵌入层和位置编码器) 1 输入复现1.1 文本嵌入层1.1.1 文本嵌入层的作用1.1.2 文本嵌入层的代码实现1.1.3 文本嵌入层中的注意事项1.2 位置编码器1.2.1 位置编码器的作用1.2.2 位置编码器的代码实现1.2.3 位置编码器中的注意事项1 输入复现…

上海 · 得物技术沙龙-「项目管理」专场报名开启!

随着业务的快速发展以及资源规模的增长&#xff0c;项目管理也需要根据团队规模及不同阶段的特点及时做好调整及应对。PMO/项目经理承担着资源使用、项目进度、团队协作等相关管理工作&#xff0c;过程的成功与否也决定着团队交付目标是否达成&#xff0c;结果是否符合预期。本…

应用带通滤波器进行划痕检测

案例要求&#xff1a; 图为HALCON中的例图“surface_scratch”&#xff0c;请提取出图中的划痕。 案例分析&#xff1a; 图中明亮程度不一&#xff0c;划痕颜色较淡&#xff0c;因此不能用灰度BLOB分析的方法提取出目标区域。因此&#xff0c;先构造一个带通滤波器&#xff0…

企业计算机服务器中了locked勒索病毒怎么办,勒索病毒解密恢复

计算机网络为企业的生产生活提供了极大帮助&#xff0c;让企业逐步走向数字化办公&#xff0c;但随之而来的网络安全威胁也不断增多&#xff0c;网络勒索病毒病毒攻击企业计算机的事件频发&#xff0c;并且攻击加密手段也在不断提升。近期&#xff0c;云天数据恢复中心再次接到…

抖音商城小程序源码系统 附带完整的搭建教程

大家好啊&#xff0c;今天小编来给大家分享一款抖音商城小程序源码系统。这可是当下最热门的的项目之一。。抖音作为国内最大的短视频平台之一&#xff0c;拥有庞大的用户群体和丰富的社交功能。为了满足用户在抖音上购物和交易的需求&#xff0c;抖音商城小程序应运而生。 以…

编程世界中的不可思议任务

在这个以代码为生命的职场里&#xff0c;遇到过形形色色的人物。让我印象最深的&#xff0c;当属那位对技术一窍不通&#xff0c;却对代码指手画脚的“极客”领导。他将编程的艺术视为一种神秘的巫术&#xff0c;经常提出些看似高大上&#xff0c;实则荒诞不经的要求。 那是一个…