前言
组播通信的特点是报文从一个源发出,被转发到一组特定的接收者。但在组播通信模型中,发送者不关注接收者的位置信息,只是将数据发送到约定的目的组播地址。要使组播报文最终能够到达接收者,需要某种机制使连接接收者网段的组播路由器能够了解到该网段存在哪些组播接收者,同时保证接收者可以加入相应的组播组中。IGMP就是用来在接收者主机和与其所在网段直接相邻的组播路由器之间建立、维护组播组成员关系的协议。
本文将给大家演示一下基本 stm32 以太网接口+LWIP实现IGMP组播通信功能。
示例详解
基于硬件平台: MCU 的型号是 STM32F407VGT6, 使用stm32cubemx 工具自动产生的配置工程,使用KEIL5编译代码。本示例所用的最小系统板原理图:
-
- 关于CUBEMX工具及KEIL工具的操作将不再细讲,如果还有不熟悉的可以查看之前的教程文档。下面直接介绍工程配置:
-
-
- 系统时钟树
-
-
-
- 网口配置(这里参数保持默认即可)
-
-
-
- RCC配置
-
-
-
- SYS配置
-
-
-
- Lwip配置(参数可保持默认)
-
-
-
- 引脚配置
-
-
-
- 中断配置(保持默认即可)
-
-
- 工程代码
- 在main.c 中加入如下图所示代码:
- 工程代码
同时给工程加入我们事先准备好的 multicast.c文件并指定multicast.h路径
要在cube 中实现IGMP功能,直接要CUBEMX工具的配置界面无法使能IGMP(不知道具体原因,好几个版本的都是一样不行,可能是cubemx的bug或不完善之处),本示例我们直接从代码中更改,首先是在Lwipopts.h头文件中把宏MEMP_NUM_SYS_TIMEOUT屏蔽(使用lwip/opt.h中的定义),并在文件末端定义 LWIP_IGMP 宏为1 :
要实现IGMP的接收,还要去hal库中网络接口文件,如本例中修改stm32f4xx_hal_eth.c源文件,将第1640行的参数macinit.MulticastFramesFilter值修改成ETH_MULTICASTFRAMESFILTER_NONE:
最后也是最关键一步在工程ethernetif.c文件中low_level_init函数中下图所示位置处加入红框处代码(注,如果你的ethernetif.c文件中有变量EthInitStatus的定义,可以把红框中屏蔽的代码 // EthInitStatus = hal_eth_init_status; 取消屏蔽 ):
编译工程,下载代码, ip为路由器自动分配,如果设备网口及LWIP成功运行,在路由器列表中同样也应该可以看到我们的设备,同时也应该是可以PING通的。
用TCP,UDP测试工具来测试一下UDP收发功能(本例是一个数据回显功能),相应的工具会在资料包中提供,打开软件,按下图所示步骤操作:
程序烧录后,上电可以出现如下图所示操作结—在接收区打印出我们程序中的测试输出:
本示例还是一个回显示例,在发送区发送数据,接收可以接收到同样的数据,注意因为是IGMP组播且发送端口与接收端口号一致,上位机自身发送的数据其自已也能接收到,故会出现下图中发送一次数据能接收到两次数据的现象:
上面的实验过程在Wireshark工具中能看到具体的数据包信息如下:
OK,本期实验完成!下期见!同时如果大家有什么疑问或是有想了解的其它内容,也欢迎大家留言!!最后喜欢这个公众号的同学们记得加关注了,会有不定期技术干货推出!!
文中资料下载,在公众号里给十三发消息:
下载|STM32基础系列教程37
关注十三公众号