cancel
Showing results for 
Search instead for 
Did you mean: 

FreeRTOS + LWIP + MDNS

i2pi
Associate II

I have an STM32H735 Discovery Kit and am running the example LWIP code from STM32H7-LwIP-Examples/STM32H735_Disco_ETH. This works great. But, when I add MDNS, I get a very curious crash.

I enabled MDNS in CubeMX, and then created a new thread to wait for an address to be assigned by DHCP before initializing MDNS:

void mdns_thread(void *argument) { mdns_resp_init(); while(!dhcp_supplied_address(&gnetif)) { vTaskDelay(1000/ portTICK_PERIOD_MS); } LOCK_TCPIP_CORE(); mdns_resp_add_netif(&gnetif, "scion", 60); /* mdns_resp_add_service(&gnetif, "_scion", "_scion", DNSSD_PROTO_UDP, 9000, 3600, srv_txt, NULL); mdns_resp_announce(&gnetif); */ UNLOCK_TCPIP_CORE(); while (1) { vTaskDelay(500/ portTICK_PERIOD_MS); } }

 With the thread created as:

osThreadAttr_t attributes; memset(&attributes, 0x0, sizeof(osThreadAttr_t)); attributes.name = "MDNS"; attributes.stack_size = 512; attributes.priority = osPriorityNormal; osThreadNew(mdns_thread, &gnetif, &attributes);

The issue occurs when I uncomment mdns_resp_add_netif(), as per the code snippet above. 

 

Enabling mdns_resp_add_netif(&gnetif, "scion", 60); causes the program to hang on:
 
configASSERT( pxQueue->uxItemSize == 0 );
Inside xQueueSemaphoreTake:
Thread #1 [main] 1 [core: 0] (Suspended : Signal : SIGINT:Interrupt) xQueueSemaphoreTake() at queue.c:1,433 0x8005210 osMutexAcquire() at cmsis_os2.c:1,416 0x8004586 sys_mutex_lock() at sys_arch.c:435 0x8011f9e mem_trim() at mem.c:751 0x80089de pbuf_realloc() at pbuf.c:444 0x800973e mdns_send_outpacket() at mdns.c:1,485 0x80078c4 mdns_send_probe() at mdns.c:2,005 0x8007abe mdns_probe() at mdns.c:2,035 0x800833c sys_check_timeouts() at timeouts.c:390 0x800e276 tcpip_timeouts_mbox_fetch() at tcpip.c:98 0x8006b02 <...more frames...>
This pxQueue is supposed to be a semaphore, but the data inside it has been corrupt. 
p &pxQueue->uxItemSize $3 = (UBaseType_t *) 0x24002e90 <ucHeap+3088>
So, let's set a watch on that in GBD and restart:
watch *(uint32_t *)0x24002e90 Hardware watchpoint 6: *(uint32_t *)0x24002e90
It first breaks in prvInitialiseNewQueue, which is totally kosher. Continuing execution and it breaks here:
Program received signal SIGTRAP, Trace/breakpoint trap. 0x08006d06 in mdns_readname_loop (p=p@entry=0x30000470, offset=offset@entry=12, domain=domain@entry=0x24002ec4 <ucHeap+3140>, depth=depth@entry=0) Thread #1 [main] 1 [core: 0] (Suspended : Signal : SIGTRAP:Trace/breakpoint trap) mdns_readname_loop() at mdns.c:360 0x8006d06 mdns_readname() at mdns.c:424 0x8006e12 mdns_compress_domain() at mdns.c:798 0x8006e12 mdns_compress_domain() at mdns.c:842 0x8006ee4 mdns_write_domain() at mdns.c:849 0x8006ee4 mdns_add_question() at mdns.c:923 0x8006fb4 mdns_add_answer() at mdns.c:1,001 0x8007086 mdns_add_a_answer() at mdns.c:1,176 0x80073fa mdns_send_outpacket() at mdns.c:1,320 0x80079e8 mdns_send_probe() at mdns.c:2,005 0x8007abe <...more frames...>
 
 
Look at the psp:
 
info registers r0 0x30000470 805307504 r1 0xc 12 r2 0x24002ec4 603991748 r3 0x0 0 r4 0x30000470 805307504 r5 0xc 12 r6 0x2400307c 603992188 r7 0xd 13 r8 0x0 0 r9 0x24003204 603992580 r10 0xa5a5a5a5 2779096485 r11 0x2400307c 603992188 r12 0x2e 46 sp 0x24002e90 0x24002e90 <ucHeap+3088> lr 0x8006e13 134245907 pc 0x8006d06 0x8006d06 <mdns_readname_loop+6> xpsr 0x81000000 -2130706432 fpscr 0x0 0 msp 0x2404ffe0 0x2404ffe0 psp 0x24002e90 0x24002e90 <ucHeap+3088> <== SHOULD BE &pxQueue->uxItemSize!!! primask 0x0 0 basepri 0x0 0 faultmask 0x0 0 control 0x2 2
 
So, psp is now pointing to an address inside a mutex. This shouldn't happen :)
 
and for reference we're in the "tcpip_thread", with
 
p pxCurrentTCB->pxTopOfStack $3 = (volatile StackType_t *) 0x240032bc <ucHeap+4156> p pxCurrentTCB->pxStack $4 = (StackType_t *) 0x24002f70 <ucHeap+3312>

 

So psp is below pxStack. I'm at a loss as to what I should be changing in terms of memory settings, linker files, etc., to get this to work. Suggestion would be greatly appreciated!

 

My full source is attached.

 

2 REPLIES 2
i2pi
Associate II

Ok. So increasing TCPIP_THREAD_STACKSIZE from 1024 to 2048 words seems to have fixed it. Now I just need to work out why I can't see the MDNS messages. Looking into wireshark and I don't see any UDP packets being sent.

Tracing the code, I see that memp_malloc(MEMP_UDP_PCB) (inside mdsn_resp_init(), udp_new()) fails as memp_pools[MEMP_UDP_PCB]->tab = 0x0.

 

I've enabled semihosting and I see a stream of:

 

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem overflow in pool UDP_PCB" failed at line 109 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem underflow in pool UDP_PCB" failed at line 120 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem underflow in pool UDP_PCB" failed at line 120 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem underflow in pool UDP_PCB" failed at line 120 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem underflow in pool UDP_PCB" failed at line 120 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

Assertion "detected mem underflow in pool UDP_PCB" failed at line 120 in ../Middlewares/Third_Party/LwIP/src/core/mem.c

i2pi
Associate II

The issue was that my mdns_thread was starting before memp_init() ran, so the pools were not set up. It also turns out that CubeMX dropped Driver_PHY, so I set that back to LAN8742, and now the issue I'm seeing is:

 

 
Assertion "pbuf_free: p->ref > 0" failed at line 753 in ../Middlewares/Third_Party/LwIP/src/core/pbuf.c Assertion "pbuf_free: p->ref > 0" failed at line 753 in ../Middlewares/Third_Party/LwIP/src/core/pbuf.c Assertion "pbuf_free: p->ref > 0" failed at line 753 in ../Middlewares/Third_Party/LwIP/src/core/pbuf.c Assertion "pbuf_free: p->ref > 0" failed at line 753 in ../Middlewares/Third_Party/LwIP/src/core/pbuf.c Assertion "pc->custom_free_function != NULL" failed at line 767 in ../Middlewares/Third_Party/LwIP/src/core/pbuf.c

Which is happening here:

Thread #1 (Suspended : Signal : SIGTRAP:Trace/breakpoint trap) HardFault_Handler() at stm32h7xx_it.c:91 0x800174a <signal handler called>() at 0xfffffffd 0x0 pbuf_free() at pbuf.c:768 0x8008490 icmp_input() at icmp.c:193 0x800f642 ip4_input() at ip4.c:715 0x800fcce ethernet_input() at ethernet.c:186 0x801083e tcpip_thread_handle_msg() at tcpip.c:174 0x8006f70 tcpip_thread() at tcpip.c:148 0x8006fd6 0x8006940

I reduced the size of MEMP_NUM_ARP and _DNS, and that kinda fixed it? I'm able to ping it (although i get ~20% packet loss). My wireshark shows MDNS being announced, but its not appearing in mDNS-Explorer and my client application can't find it.