FreeRTOS + TCP is crashing in prvEMACHandlerTask()

Sounds like somehow it isn’t installing the Interrupt Vector for the Ethernet IRQ.

Are there differences between using stm32f4xx_hal and stm32f4xx libraries?
For example, between stm32f4xx_dma.h and stm32f4_hal_dma.h?
Currently I’m using header files from both libraries.
Could it create problems ?

Hi Richard, I’m trying to debug my project by tracing it and step through fnPhyRead() function, but couldn’t find any definition on it in my TCPIP library. Also in the line 198 of phyHandling.c there is statement:
pxPhyObject->fnPhyRead( xPhyAddress, phyREG_03_PHYSID2, &ulLowerID );
which includes uninitialized local variable: ulLowerID, passed as argument of fnPhyRead() function. Could you clarify for me, what I may missed?

fnPhyRead is a function pointer pointing to the actual platform PHY read routine you have to provide.
It’s initialized along with the fnPhyWrite pointer by calling vPhyInitialise. contains xSTM32_PhyRead/Write example implementations.

Thanks Hartmut, I may missed some info, that FreeRTOS + TCP
requires some customer adjustments based on real hardware.
Which other low level functions need to fill voids by customers?

@stshvarts1 wrote:

Are there differences between using stm32f4xx_hal and stm32f4xx libraries?
For example, between stm32f4xx_dma.h and stm32f4_hal_dma.h?

I think that stm32f4xx_dma.h is part of the older standard peripheral library, which was in use before the HAL version. Some developers claim that it was simpler and more stable.

Which other low level functions need to fill voids by customers?

The PHY handler only needs a read and a write function to talk with the PHY. The way in which this happens is universal.

The Network Interface needs to implement two things:

  1. The function xNetworkInterfaceOutput(), which passes network packets to DMA, so it will be sent o the LAN.
  2. A function prvNetworkInterfaceInput(), which calls xSendEventStructToIPTask() to forward network packets to the IP-task for processing.

The first function is called by the IP-task, the second function is normally called from a driver function called prvEMACHandlerTask(), which wakes up after a DMA event.

Hello Richard,

Thanks for responding. This is my second gmail account, which I don’t use very often. Sorry, only now noticed your email.

I’m getting a crash which manifests itself by jumping to the infinite loop located in startup_stm32.s file at line 102
I traced the function, from which the program jumps to the infinite loop. It is vIPNetworkUpCalls() in FreeRTOS_IP.c (line 1660).

One symptom I have, that during initialization in HAL_ETH_MSPInit(heth) where STM32F407 pins connected to
Phy DP83848 initialized I also initialise ETH_IRQn interrupt.
The simptom is that, if I commented interrupt out, the software will stop crashing, but still will respond to the ping
with a “request time out” message.

Also we have an old working version of FreeRTOS with LWIP drivers, but our company decided for new
products to use the latest FreeRTOS + TCP. So, initialization implemented in HAL_ETH_MSPInit(heth)
is the same as in LWIP.

Steven Shvarts.

Do you enable ETH_IRQn after initializing the network stack by FreeRTOS_IPInit ?

Steven, have you already looked at my STM32F407 project here?

I have HAL_ETH_MspInit() defined in Src/main.c.


Maybe it helps to compare your and my project.

When main() is called, it starts with the general stack space as defined in your linker file. Now if I am not mistaken, once the scheduler is running, this stack space is being user for the ISR’s (I am not sure if this is true for the STM32F4x ports).
But if it is true, can you tell if there are still references to stack earlier used by main()? Does it have local variables that are used?

STM32F4x are Cortex-M4 MCUs. So yes - the Cortex-M port restriction regarding (not using) main stack applies.

Hartmut, thanks for confirming this.
@stshvarts1 can you make sure that you stop accessing any objects declared on-stack in main()?

Hein and Hartmut, thanks for responding to my problems.
First, let me answer Hartmut question.
I initialize ETH_IRQn in the HAL_ETH_MspInit( heth ) in stm32fxx_hal_eth.c (line 226).
It looks like this:

NVIC_InitStructure.NVIC_IRQChannel = ETH_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 13;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;

Hein, I built my project (it is based on XCore407I “WaveShare” dev board) the following way:

  1. Downloaded the latest FreeRTOS, created and ran 2 simple tasks, which through the serial COM port output data to the Tera Term terminal. Everything worked perfectly well.
  2. Used FreeRTOS “TCP Networking” tutorial to add to current project networking capability.
  • downloaded from FreeRTOS repository recommended freertos_plus_projects from which selected …/plus/Framework/FreeRTOS-Plus-TCP/… and added it to my project. I did this because according to tutorial FreeRTOS-Plus-TCP folder has the same source code organization.
  1. The things I adjusted for my XCore407I board hardware was:
  • in the HAL_ETH_MspInit() settings very similar to your HAL_ETH_MspInit()
  • set SystemCoreClock = 120000000
  • my ETH_IRQn interrupt priority was 13, I will try 0 as you suggested.

Note that Hein didn’t propose ETH_IRQn prio 0:

OK, Sorry, thanks for correcting.

Currently in the main() I’m using only 2 functions: FreeRTOS_IPInit(…) and vTaskStartScheduler()

Found software crashing source. In startup_stm32.s file Ethernet interrupt handle ETH_IRQHandler was absent. After placing this handler on its place in the startup file the software stopped crashing.
Now I have another hurdle in the stm32f4xx_hal_dma.h file. It shows “expected identifier or ‘(’ before typedef” problem at the beginning of “DMA_InitTypeDef” structure (line 49) although there are no reason for this error. It is standard structure definition.
In stm32f4xx_hal.c (line 77) error: “SYSCFG_CMPCR_CMP_PD_Pos undeclared”