IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 嵌入式 -> 关于NUCLEO-F207ZG开发板通过STM32CubeMx配置(五)配置FreeRTOS+Lwip使用socketAPI进行tcp连接测试 -> 正文阅读

[嵌入式]关于NUCLEO-F207ZG开发板通过STM32CubeMx配置(五)配置FreeRTOS+Lwip使用socketAPI进行tcp连接测试

目录

前言

一、详细步骤

1.配置UART打印调试信息

? ? ? ? 1.1.配置UART5

? ? ? ? 1.2.查看串口的引脚配置

? ? ? ? 1.3.? UART5 NVIC Settings

? ? ? ? 1.4.配置完成进行PING测试

2.写程序代码前的准备工作

? ? ? ? ?2.1.?在usart.c这个文件中重定向一下printf()这个函数的输出。

? ? ? ? ?2.2.在usart.c加上头文件”stdio.h”

? ? ? ? ?2.3.在main.h在头文件处加上”stdio.h”

? ? ? ? ? ?2.4.测试一下串口输出效果

3.在FreeRTOS任务1(Task1)中编写客户端代码,运行连接程序

? ? ? ? 3.1.代码编写

? ? ? ? 3.2.测试连接

3.在FreeRTOS任务2(Task2)中编写服务器端代码,运行连接程序

? ? ? ? 3.1.代码编写

? ? ? ? 3.2.测试连接

?

4.结束

总结



前言

????????因为工作关系需要用到STM32F207ZGTx的芯片,所以公司购买了基于STM32F207ZGT6U芯片的ST开发板NUCLEO-F207ZG。而且要求使用FeeRTOS+Lwip的环境,来进行软件开发,主要目的是通过此环境,运行一个软件下载程序,此程序用到了lwip库封装的socket套接字函数库,通过Tcp请求服务器下载文件包。因为我自己第一次正式做一个关于STM32的程序项目,之前只是在学校学习和了解一些基础,认识比较浅显,所以写下本文来加深自己的学习和了解,并且总计经验分享出来,有问题可以共同探讨。

????????本文内容:使用STM32CubeMx配置FreeRTOS和Lwip的例子在上一章已经讲过了就不重复列出来了,这里这里主要讲配置UART串口打印调试信息和使用Lwip库中socket套接字做tcp连接测试的例子和流程。

????????配置软件:STM32CubeMx 6.2.1

????????开发板:NUCLEO-F207ZG

????????配置环境:FreeRTOS+Lwip

????????编译软件:keil ?5.27


一、详细步骤

1.配置UART打印调试信息

? ? ? ? 1.1.配置UART5

????????????????配置UART5作为打印信息的串口,默认波特率115200/bps,其他也是默认配置,如果有需要其他波特率可以根据自己需求修改。

? ? ? ? 1.2.查看串口的引脚配置

????????????????可以看到选择UART5后,CubeMx软件已经将串口的引脚配置完成了,我们只需要根据引脚进行接线即可。????

? ? ? ? 1.3.? UART5 NVIC Settings

????????????????NVIC Settings这里我没有开启中断,当然可以根据自己的需要开启。

? ? ? ? 1.4.配置完成进行PING测试

????????????????串口配置已经完成,生成后续时钟配置按照上一章的进行即可,接下来写代码。在写代码之前注意ping一下自己配置的ip,保证网卡驱动配置正确。

2.写程序代码前的准备工作

? ? ? ? ?2.1.?在usart.c这个文件中重定向一下printf()这个函数的输出。

?????????????????代码:

/* USER CODE BEGIN 1 */
//这个变量是其他.c文件定义的
 //extern UART_HandleTypeDef huart1;
 uint8_t ch;
 uint8_t ch_r;
 //重写这个函数,重定向printf函数到串口,意思就是说printf直接输出到串口,其默认输出到控制台的
 /*fputc*/
int fputc(int c, FILE * f)
{
    ch=c;
     HAL_UART_Transmit(&huart5,&ch,1,1000);//发送串口
     return c;
 }
 
 //重定向scanf函数到串口 意思就是说接受串口发过来的数据,其默认是接受控制台的数据
 /*fgetc*/
 int fgetc(FILE * F)    
 {
     HAL_UART_Receive(&huart5,&ch_r,1,0xffff);//接收
     return ch_r;
 }
/* USER CODE END 1 */

? ? ? ? ?2.2.在usart.c加上头文件”stdio.h”

? ? ? ? ?2.3.在main.h在头文件处加上”stdio.h”

????????????????????????找到main.h在头文件处加上”stdio.h”,这样其他包含main.h的源文件都能够使用printf()打印调试信息,不然你使用printf()就需要在使用的源文件中声明stdio.h。

? ? ? ? ? ?2.4.测试一下串口输出效果

? ? ? ? ? ? ? ? ? ? ? ? 重定义准备完成,测试一下串口输出效果。在freertos.c的任务1函数,StartTask1(void const * argument)的for循环中运行调试信息,下载到开发板中,运行程序,打开串口调试软件,这里我的端口为COM7,所以选择com7,波特率115200bps,打开串口可以看到输出的信息,说明整个流程是成功的。

????????????????????????代码:

void StartTask1(void const * argument)
{
  /* init code for LWIP */
  MX_LWIP_Init();
  /* USER CODE BEGIN StartTask1 */
  /* Infinite loop */
  for(;;)
  {
	printf("这是task1 打印调试信息!\r\n");
    osDelay(1000); //1s循环一次
  }
  /* USER CODE END StartTask1 */
}

3.在FreeRTOS任务1(Task1)中编写客户端代码,运行连接程序

? ? ? ? 3.1.代码编写

????????????????前期准备工作完成,接下来就是进行tcp编程了,先进行客户端代码的编写。

????????????????代码:

void StartTask1(void const * argument)
{
  /* init code for LWIP */
  MX_LWIP_Init();
  /* USER CODE BEGIN StartTask1 */
  /* Infinite loop */
  //tcp client 连接测试
	int iResult = 0;
	
	struct sockaddr_in conn_addr;				//连接地址
	int conn_fd;								//服务器的 socked 
//	int sock_conn;								// 请求的 socked 
//	socklen_t addr_len;							// 地址长度 
//	int err;
	printf("come StartTask1\r\n");
	


	conn_fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
	conn_addr.sin_family = AF_INET;
	conn_addr.sin_port = htons(28884);
	conn_addr.sin_addr.s_addr = inet_addr("192.168.0.64");

	if( connect(conn_fd, (struct sockaddr *)&conn_addr, sizeof(struct sockaddr_in)) == -1)
	{
			printf("connect error\n");
	}
	printf("connect successful!conn_fd=%d\r\n",conn_fd);
	
	unsigned char bTmpSendBuf[]="hello server!This is NUCLEO-F207ZGT6U connect!";
	  for(;;)
	  {
			write(conn_fd,bTmpSendBuf,sizeof(bTmpSendBuf));
			if(iResult>0)
			{
				printf("write successful Size=%d\r\n",iResult);
			}
		osDelay(1000);
	  }
  /* USER CODE END StartTask1 */
}

? ? ? ? 3.2.测试连接

????????????????创建一个tcp服务器端,接收NUCLEO-F207ZG开发板客户端的连接,我这里服务器端配置的ip是”192.168.0.64”,端口28884,可以看到客户端成功连接上服务器端

3.在FreeRTOS任务2(Task2)中编写服务器端代码,运行连接程序

? ? ? ? 3.1.代码编写

????????????????代码:

/* USER CODE END Header_StartTask2 */
void StartTask2(void const * argument)
{
  /* USER CODE BEGIN StartTask2 */
  /* Infinite loop */
 char data_buffer[512];
  /* Infinite loop */
	struct sockaddr_in server_addr;				//服务器地址
	struct sockaddr_in conn_addr;				//连接地址
	int sock_fd;								//服务器的 socked 
	int sock_conn;								// 请求的 socked 
	socklen_t addr_len;							// 地址长度 
	int err;
	printf("come StartTask2\r\n");
	sock_fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);		//建立一个新的socket连接	
	if(sock_fd<0)
	{
		printf("create sock_fd failed! sock_fd=%d\r\n",sock_fd);
	}
	printf("create sock_fd successful! sock_fd=%d\r\n",sock_fd);
	memset(&server_addr, 0, sizeof(server_addr));				//将服务器地址清空
	server_addr.sin_family = AF_INET;							//地址家族
	server_addr.sin_addr.s_addr =htonl(INADDR_ANY);				//注意转化为网络字节序
	server_addr.sin_port = htons(18885);					//使用指定端口号
	err = bind(sock_fd, (struct sockaddr *)&server_addr, sizeof(server_addr));	//建立绑定
	if (err < 0)															    //如果绑定失败则关闭套接字
	{
		printf("bind socket failed!\r\n");
		closesocket(sock_fd); 												//关闭套接字
	}
	while(1)
	{		
		err = listen(sock_fd, 1);									//监听连接请求    1:ACCEPT队列的大小
		if (err < 0) 												//如果监听失败则关闭套接字
		{
			printf("listen socketFd failed!socketFd=%d\r\n",sock_fd);
			closesocket(sock_fd); 								//关闭套接字
		}
		addr_len = sizeof(struct sockaddr_in);		//将链接地址赋值给addr_len
		sock_conn = accept(sock_fd, (struct sockaddr *)&conn_addr, &addr_len);	//等待连接,状态赋值给sock_conn
		if(sock_conn < 0)											//状态小于0代表连接故障,此时关闭套接字
		{
			printf("accept socketFd failed!socketFd=%d\r\n",sock_fd);
			closesocket(sock_fd);
		}
		while (1) 
		{
			memset(data_buffer, 0, sizeof(data_buffer));			//清空接收Buff
			int length = recv(sock_conn, (unsigned int *)data_buffer, 100, 0);	//将收到的数据放到接收Buff 100为可以接收的数据长度
			if(length > 0)
			{
				printf("recv buf data! size=%d\r\n",length);
				send(sock_conn, data_buffer,length, 1);	//回复客户端
				printf("[StartTask2] Send bufSize=%d\r\n",length);
			}
			else
			{
				printf("Recv error Data!\r\n");
				closesocket(sock_conn);
				break;
			}
			osDelay(1);
		}
		osDelay(1);
	}
  /* USER CODE END StartTask2 */
}

? ? ? ? 3.2.测试连接

????????????????(一)、创建客户端,这里目的服务器ip是开发板的ip192.168.0.179,端口:18885,ping一下测试是否能够连接,如果能够ping通,说明可以连接

????????????????(二)、选择打开tcp,发送数据,可以看到串口打印了调试信息,NUCLEO-F207ZG服务器端接收到数据后完整返回给了客户端。这里表示整个流程成功。

4.结束



总结

  1. 通过以上测试我们就能够完整的掌握整个NUCLEO-F207ZG开发板配置FreeRTOS+LWIP然后进行tcp连接的一个完整流程了。
  2. 注意串口软件的波特率需要与配置串口的波特率一致。
  3. 在连接是需要多注意一下是否能够ping通,在运行程序连接。
  嵌入式 最新文章
基于高精度单片机开发红外测温仪方案
89C51单片机与DAC0832
基于51单片机宠物自动投料喂食器控制系统仿
《痞子衡嵌入式半月刊》 第 68 期
多思计组实验实验七 简单模型机实验
CSC7720
启明智显分享| ESP32学习笔记参考--PWM(脉冲
STM32初探
STM32 总结
【STM32】CubeMX例程四---定时器中断(附工
上一篇文章      下一篇文章      查看所有文章
加:2021-11-30 15:46:40  更:2021-11-30 15:48:06 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 10:47:28-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码