This is a experimental approach for using micro-ROS with embeddedRTPS as middleware. This instructions are an approach to a STMCubeIDE v1.7.0 + FreeRTOS + LwIP configuration and has been tested with Nucleo F746ZG board against ROS 2 Galactic with Fast-DDS as default middleware.
IT IS HIGHLY RECOMMENDED TO HAVE THE BOARD AND THE ROS 2 COMPUTER IN AN ISOLATED ETHERNET NETWORK
-
Create a a new STM32 project based on C++
-
In the
.ioc
file enable:- Middleware -> FreeRTOS: with CMSIS_V2
- Middleware -> LwIP
- Connectivity -> ETH
-
Make sure that your HAL timebase is not Systick (FreeRTOS requeriment) and
USE_NEWLIB_REENTRANT
is enabled (FreeRTOS -> Advanced settings). -
Make sure that FreeRTOS has the following configuration:
- FreeRTOS -> Config parameters -> Memory management settings -> TOTAL_HEAP_SIZE -> 100000 Bytes
- FreeRTOS -> Config parameters -> Kernel settings -> MAX_TASK_NAME_LEN -> 30
- FreeRTOS -> Tasks and Queues -> defaultTask -> Stack Size -> 8000 Words
- FreeRTOS -> Tasks and Queues -> defaultTask -> Priority -> Belownormal3
-
Make sure that LwIP has the following configuration:
- LwIP -> Key Options (Show advanced parameters) -> Multicast Options -> LWIP_MULTICAST_TX_OPTIONS -> Enabled
- LwIP -> General Settings -> LWIP IGMP -> Enabled
- LwIP -> General Settings -> LWIP_DHCP -> Disabled
- LwIP -> General Settings -> IP Address Settings (Set here the board address and mask)
- LwIP -> General Settings -> Procols Options -> MEMP_NUM_UDP_PCB -> 15
- LwIP -> Key Options (Show advanced parameters) -> Infraestructure - Heap and Memory Pools Options -> MEM_SIZE -> 30000 Bytes
- LwIP -> Key Options (Show advanced parameters) -> Infraestructure - Threading options -> TCPIP_THREAD_STACKSIZE -> 10000 Words
- LwIP -> Key Options (Show advanced parameters) -> Infraestructure - Threading options -> TCPIP_THREAD_PRIO -> 20
- LwIP -> Key Options (Show advanced parameters) -> Infraestructure - Pbuf Options -> PBUF_POOL_SIZE -> 20
-
Save the file and generate the code.
-
In file
LWIP/Target/ethernetif.c
add the following line in blockUSER CODE BEGIN MACADDRESS
insidelow_level_init()
function:netif->flags |= NETIF_FLAG_IGMP;
-
Make sure that
macinit.MulticastFramesFilter
is set toETH_MULTICASTFRAMESFILTER_NONE
. Usually this configuration is set inDrivers/STM32F7xx_HAL_Driver/Src/stm32f7xx_hal_eth.c:1878
and by default its value isETH_MULTICASTFRAMESFILTER_PERFECT
. Probably this is modified automatically every time code is generated. -
Clone this repository in your STM32CubeIDE project folder.
-
Go to
Project -> Settings -> C/C++ Build -> Settings -> Build Steps Tab
and inPre-build steps
add:
docker pull microros/micro_ros_static_library_builder:galactic && docker run --rm -v ${workspace_loc:/${ProjName}}:/project --env MICROROS_USE_EMBEDDEDRTPS=ON --env MICROROS_LIBRARY_FOLDER=micro_ros_stm32cubemx_utils/microros_static_library_ide microros/micro_ros_static_library_builder:galactic
- Add the following source code files to your project, dragging them to source folder:
extra_sources/microros_time.c
extra_sources/microros_allocators.c
extra_sources/custom_memory_manager.c
- Add micro-ROS include directory:
- In
Project -> Settings -> C/C++ Build -> Settings -> Tool Settings Tab -> MCU GCC Compiler -> Include paths
add../micro_ros_stm32cubemx_utils/microros_static_library_ide/libmicroros/include
- In
Project -> Settings -> C/C++ Build -> Settings -> Tool Settings Tab -> MCU G++ Compiler -> Include paths
add../micro_ros_stm32cubemx_utils/microros_static_library_ide/libmicroros/include
- Add the micro-ROS precompiled library. In
Project -> Settings -> C/C++ Build -> Settings -> MCU GCC Linker -> Libraries
- add
../micro_ros_stm32cubemx_utils/microros_static_library_ide/libmicroros
inLibrary search path (-L)
- add
microros
inLibraries (-l)
-
Use
sample_main_embeddedrtps.c
as reference for writing you application code. -
In
Core/Inc/FreeRTOSConfig.h
. Explanation here
// FROM THIS:
// #define configASSERT( x ) if ((x) == 0) {taskDISABLE_INTERRUPTS(); for( ;; );}
// TO THIS:
#define configASSERT( x )