基于RT-Thread在STM32H7上移植LWIP(二)

本文主要讲述将基于FreeRTOS的STM32H7工程源码移植LWIP到RT-Thread的过程。包括修改报错文件,将工程与LWIP关联,完成初始化和配置。同时分享了移植中遇到的问题,如发送函数缓存设置、PHY硬复位等,还指出参考代码存在的不足。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一,写在前面

上一节已经把所需要的工程源码全部准备好了,前面做的只是基础工作,现在去编译工程会出现非常多的错误以及警告,这一节就是去解决这些错误和警告。

二,修改报错文件

因为是源码是基于FREERTOS的,所以错误的代码不是找不到头文件,就是找不到API,按照这两个思路去解决这些错误就行了。

  1. 修改头文件报错
    删除FREERTOS相关头文件,比如 “FreeRTOS.h” “task.h”,调用这些头文件出现在源码的很多地方,只要替换为RT-Thread相关即可。

  2. 修改LWIP依赖的OS内核函数
    修改sys_arch.c 中关于OS内核函数
    例如源码

err_t sys_sem_new(sys_sem_t *sem, u8_t count)
{
  osSemaphoreDef(SEM);

  *sem = osSemaphoreCreate (osSemaphore(SEM), 1);
	
  if(*sem == NULL)
  {
#if SYS_STATS
      ++lwip_stats.sys.sem.err;
#endif /* SYS_STATS */	
		return ERR_MEM;
  }
	
  if(count == 0)	// Means it can't be taken
  {
    osSemaphoreWait(*sem,0);
  }

#if SYS_STATS
	++lwip_stats.sys.sem.used;
 	if (lwip_stats.sys.sem.max < lwip_stats.sys.sem.used) {
		lwip_stats.sys.sem.max = lwip_stats.sys.sem.used;
	}
#endif /* SYS_STATS */
		
	return ERR_OK;
}

替换成

err_t sys_sem_new( sys_sem_t *sem, u8_t count )
{
    static unsigned short counter = 0;
    char tname[RT_NAME_MAX];
    sys_sem_t tmpsem;

    RT_DEBUG_NOT_IN_INTERRUPT;

    rt_snprintf(tname, RT_NAME_MAX, "%s%d", SYS_LWIP_SEM_NAME, counter);
    counter ++;

    tmpsem = rt_sem_create(tname, count, RT_IPC_FLAG_FIFO);
    if (tmpsem == RT_NULL)
        return ERR_MEM;
    else
    {
        *sem = tmpsem;

        return ERR_OK;
    }
}

替换参考RT_Thread的LWIP软件包

完成修改操作

三,工程和LWIP关联起来

  1. 启动LWIP
    在main 调用tcpip_init(NULL, NULL) 来完成LWIP的初始化

  2. 配置LWIP
    调用Netif_Config();完成对LWIP的配置

static void Netif_Config(void)
{
    ip_addr_t ipaddr;
    ip_addr_t netmask;
    ip_addr_t gw;

    IP_ADDR4(&ipaddr,192,168,1,30);
    IP_ADDR4(&netmask,255,255,255,0);
    IP_ADDR4(&gw,192,168,1,1);

    /* add the network interface */
    netif_add(&gnetif, &ipaddr, &netmask, &gw, NULL, &ethernetif_init, &tcpip_input);

    /*  Registers the default network interface. */
    netif_set_default(&gnetif);

    netif_set_link_callback(&gnetif, eth_link_callback);


#if LWIP_DHCP
    /* Start DHCPClient */
    tid = rt_thread_create("eth_dhcp", DHCP_Thread, &gnetif, 1024, 30, 20);
    rt_thread_startup(tid);
#endif
}
  1. 修改low_level_init
    在配置ETH之前增加PHY硬复位
phy_reset();

把FREERTOS创建任务函数替换为RT-Thread

  /* create the task that handles the ETH_MAC */
  xTaskCreate( ethernetif_input, "eth_if", 
               INTERFACE_THREAD_STACK_SIZE, netif, INTERFACE_TASK_PRIORITY,NULL);

  /* create the task that handles the eth_link */
  xTaskCreate( ethernet_link_thread, "eth_link", 
               INTERFACE_THREAD_STACK_SIZE, netif,INTERFACE_TASK_PRIORITY,NULL);
  rt_thread_t tid = rt_thread_create("eth_rx", ethernetif_input, netif, 2048, 2, 10);
  rt_thread_startup(tid);
  rt_thread_t tid = rt_thread_create("eth_link", ethernet_link_thread, &gnetif, 1024, 20, 10);
  rt_thread_startup(tid);
  1. 修改low_level_output
    在发送函数前要增加一句SCB_CleanInvalidateDCache();
  TxConfig.Length = framelen;
  TxConfig.TxBuffer = Txbuffer;
  
  SCB_CleanInvalidateDCache();
  HAL_ETH_Transmit(&EthHandle, &TxConfig, 0);
  1. 修改收发函数的信号量API
    原来的API都是基于FREERTOS的,修改为RT-Thread
    如:
    if (osSemaphoreWait( RxPktSemaphore, TIME_WAITING_FOR_INPUT)==osOK)

修改为:

    if(rt_sem_take(&eth_rxin, RT_WAITING_FOREVER) == RT_EOK)
  1. 把开发板和电脑连接起来
    在这里插入图片描述
    能看到开发板和电脑的已经通讯了。至此移植全部完成。

四,我移植过程中遇到的问题

  1. 发送函数增加SCB_CleanInvalidateDCache();
    这个和cache策略配置有关,这个CACHE还需要多少研究。不加这一句会导致发送失败。

  2. PHY硬复位
    如果不复位可能导致ETH配置失败。

  3. lwipopts.h修改
    这里使用LWIP的动态内存,所以要把这个宏定义为1。

#define MEMP_MEM_MALLOC             1
  1. LWIP的RAM设置
    这里的设置一定要是
#define LWIP_RAM_HEAP_POINTER    (0x30044000)
  1. 设置pbuf_size
#define PBUF_POOL_BUFSIZE       1536
  1. 注意2个宏定义
#define ETH_RX_BUFFER_SIZE                     (1536UL)
#define ETH_MAX_PACKET_SIZE      ((uint32_t)1528) 

这两个宏定义只能使用其中一个,因为大小不一样,会导致内存出现问题。

五,我参考GITHUB上的代码中存在的问题

  1. 发送函数没有增加SCB_CleanInvalidateDCache();
  2. 在配置PHY之前没有给一个硬复位;
  3. LWIP提供了3中内存分配机制,但是全部定义为0,既都没使用;
  4. pbuf_size通过宏定义来实现,我直接手动到设置为1536;

六,参考链接

  1. 言简意赅的介绍M7内核的Cache工作流程,摸爬滚打半年的经验总结
  2. stm32h7_freertos
  3. 终于搞定STM32H743网络了,分享调试经验及注意事项
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值