Writing peripheral initialization code is probably the most tedious work in embedded development. It always successfully stops me from starting a new project. I believe engineers at STMicroelectronics share the same pain. Therefore they created STM32Cube firmware and STM32CubeMX graphical configuration tool, which turns numerous key strokes and page flips into just a few mouse clicks. STM32CubeMX is free software, but the initialization code it generates require compiler tools carrying hefty price tags, IARARM, Keil ARM-MDK, and Atollic TrueSTUDIO, to name the few. Fair enough these compilers do offer free editions with limited functionality. But I still prefer unrestricted, free tool that is easily scale-able for my current and future projects. Just like the GNU Make and ARM GCC toolchain I described in Opensource STM32 development.

UPDATE

Always get update from https://github.com/baoshi/CubeMX2Makefile The code is now based on SW4STM32 project output. Thanks various contributors to make this possible.

Deprived off electronics lab back in Singapore, a Chinese new year holiday here in Shanghai home is perfect for some software projects. I have little exposure with Python but after two days of Googling (through VPN) and copy/paste, a crude CubeMX2Makefile utility is ready, available at https://github.com/baoshi/CubeMX2Makefile (OOP aficionados please forgive my spaghetti styled code. It works is it?)

As the name suggests, the program converts STM32CubeMX project into a GNU Makefile. Here is a mini-HOWTO:

    1. Create a STM32CubeMX project, configure pins, peripherals and MiddleWare, then edit project settings as follows: (choose SW4STM32 instead of TrueStudio in the picture below)
      STM32CubeMX project settings
      STM32CubeMX project settings

      Make sure the Tool/IDE selection is TrueSTUDIO 4.3.1 (as of STM32CubeMX 4.6.0), and note down the “Toolchain Folder Location”. I found it necessary to empty the old “Toolchain Folder” before each code generation, otherwise the project file just keep growing regardless of settings (this could be a bug in STM32CubeMX). See update below.

    2. Download the project from the Github repo below, extract files to a folder, say “C:CubeMX2Makefile”. Install Python 2.7 Win32 from www.python.org
      c:CubeMX2Makefile>dir /b
      .gitattributes
      .gitignore
      CubeMX2Makefile.py
      CubeMX2Makefile.tpl
      readme.md
      
    3. From command prompt, execute CubeMX2Makefile.py, e.g,
      c:CubeMX2Makefile>CubeMX2Makefile.py R:\411ProjTestF4
      File created: R:\411ProjTestF4Makefile
      
    4. Cd into “Toolchain Folder Locaiton”, make project, i.e.,
      R:\411ProjTestF4\>make
      ...
      arm-none-eabi-size build/TestF4.elf
       text data bss dec hex filename
       5876 12 1056 6944 1b20 build/TestF4.elf
      arm-none-eabi-objcopy -O ihex build/TestF4.elf build/TestF4.hex
      

      Refer to blog and below links for ARM GCC and make utility installation. It will be much easier to import the Makefile project into Eclipse CDT for code editing and debugging.

Useful links

CubeMX2Makefile: https://github.com/baoshi/CubeMX2Makefile

STM32Cube: http://www.st.com/stm32cube

ARM GCC: https://launchpad.net/gcc-arm-embedded

My packaged GNU Make for Win32: http://www.ba0sh1.com/wp-content/uploads/2013/05/make.zip

 

36 thoughts on “STM32CubeMX GCC Makefile project

  1. “Writing peripheral initialization code is probably the most tedious work in embedded development. It always successfully stops me from starting a new project”: Amen, brother! I’ve been switching between IDEs and microcontrollers, trying to find one that bootstraps a project well. I looked at CooCox and Rowley (not free, but only $150) and they are possibilities. Currently, I use Microchip PIC16s and PIC32s: the IDE is free and there are Code Configurators that get a project up and running. I’ve just started playing with Cypress PSoCs, and they seem to do a great job of configuring peripherals for you. My main concern about PSoC is there are very few DIP/SOIC/large pitch QFP packages (i.e. packages I can solder by hand).

    Reply
    • CooCox is not bad too. But their 1.7 series does not support STM32Cube, and their 2.0beta hasn’t even have 1.7 repositories ported over yet.

      Reply
  2. Excellent! I literally just started banging my head against STM32CubeMX (after having done a few significant projects with StdPeriphLib) and I’d started writing something very similar to this. Now I don’t have to!

    Reply
  3. Awesome and thank for the all the work. To automate the process you can create a shortcut to the *.py file and store that with your projects. Then all you have to do is drag the project folder on top and it runs the script.
    Matt

    Reply
  4. Awesome job. This saved me a lot of pain. But it seems that the FreeRTOS option from CubeMX is not supported yet. I get the following error when executing make:

    arm-none-eabi-gcc -c -mthumb -mcpu=cortex-m4 -DUSE_HAL_DRIVER -DSTM32F303xC -IInc -IDrivers/STM32F3xx_HAL_Driver/Inc -IMiddlewares/Third_Party/FreeRTOS/Source/portable/GCC/ARM_CM4F -IMiddlewares/ST/STM32_USB_Device_Library/Core/Inc -IMiddlewares/ST/STM32_USB_Device_Library/Class/AUDIO/Inc -IMiddlewares/Third_Party/FreeRTOS/Source/include -IMiddlewares/Third_Party/FreeRTOS/Source/CMSIS_RTOS -IDrivers/CMSIS/Include -IDrivers/CMSIS/Device/ST/STM32F3xx/Include -O0 -Wall -fdata-sections -ffunction-sections -g -gdwarf-2 -MD -MP -MF .dep/port.o.d -Wa,-a,-ad,-alms=build/port.lst Middlewares/Third_Party/FreeRTOS/Source/portable/GCC/ARM_CM4F/port.c -o build/port.o
    /tmp/cccgY0kB.s: Assembler messages:
    /tmp/cccgY0kB.s:632: Error: selected processor does not support Thumb mode `vstmdbeq r0!,{s16-s31}’
    /tmp/cccgY0kB.s:634: Error: instruction not allowed in IT block — `stmdb r0!,{r4-r11,r14}’
    /tmp/cccgY0kB.s:653: Error: selected processor does not support Thumb mode `vldmiaeq r0!,{s16-s31}’
    /tmp/cccgY0kB.s:655: Error: instruction not allowed in IT block — `msr psp,r0′
    Makefile:135: die Regel für Ziel „build/port.o“ scheiterte
    make: *** [build/port.o] Fehler 1

    Anyways you helped me a lot. And getting FreeRTOS in this project by hand shouldnt be that hard :).

    Reply
    • Ok I solved the Problem and can also use the freeRTOS option in CubeMX and generate the makeproject with your pythonscript.

      I had to add the -mfpu=fpv4-sp-d16 -mfloat-abi=softfp flags to the CFLAGS and AFLAGS in the Makefile and change the objcopy from hex to bin.

      Reply
      • Thanks! I do not have a F4 board so the previous code is based on assumption. Now I can integrate your code into the python script.

        Reply
        • I dont use it with an F4 Board. I made a custom board with an STM32F303VCT7 microcontroller. But this is also an M4-architecture with an FPU. For Programming I use an stlink/v2 with JTAG.

          Reply
  5. Thanks for this project – it’s surprising that ST doesn’t support the GCC toolchain in a more “direct” manner. I wonder if they’re doing so because of pressure from Keil, IARARM, and Attolic. In any case, this makes development that much more straight forward!

    One note – it seems that the newest CubeMX has changed the default output path for the TrueSTUDIO directory structure. There is an added “Projects” folder. I just changed the path in your python script and it now works:

    “toolchain_dirProjectsTrueSTUDIOproj_name Configuration”

    Reply
  6. Pingback: TrueSTUDIO STM32 project to GCC Makefile converter - Digital Me

  7. Hi, thank you for the script.
    I try to run it under windows but get some errors:
    —————————
    D:STM32F407_CubeMX_ExampleTest03>make
    Das System kann den angegebenen Pfad nicht finden.
    arm-none-eabi-gcc -c -mthumb -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=softfp -DUSE_HAL_DRIVER -DSTM32F407xx -IInc -IDriversSTM32F4xx_HAL_DriverInc -IDriversSTM32F4xx_HAL_DriverIncLegacy -IDriversCMSISInclude -IDriversCMSISDevi
    ceSTSTM32F4xxInclude -O0 -Wall -fdata-sections -ffunction-sections -g -gdwarf-2 -MD -MP -MF .dep/system_stm32f4xx.o.d -Wa,-a,-ad,-alms=build/system_stm32f4xx.lst Drivers/CMSIS/Device/ST/STM32F4xx/Source/Templates/system_stm32f4xx.c -o bu
    ild/system_stm32f4xx.o
    Drivers/CMSIS/Device/ST/STM32F4xx/Source/Templates/system_stm32f4xx.c:287:1: fatal error: opening dependency file .dep/system_stm32f4xx.o.d: No such file or directory
    compilation terminated.
    make: *** [build/system_stm32f4xx.o] Fehler 1
    —————————

    First of all, it seems to stumble over the mkdir -p .. ” command. At least I will get a folder called “-p”, how ever the folder build still gets generated.
    But then I get this odd error:
    Drivers/CMSIS/Device/ST/STM32F4xx/Source/Templates/system_stm32f4xx.c:287:1: fatal error: opening dependency file .dep/system_stm32f4xx.o.d: No such file or directory

    Reply
      • Couldn’t find your email address, so here it is:
        —————————————
        #MicroXplorer Configuration settings – do not modify
        #Wed Jun 10 16:51:00 CEST 2015
        File.Version=5
        KeepUserPlacement=false
        Mcu.Family=STM32F4
        Mcu.IP0=NVIC
        Mcu.IP1=RCC
        Mcu.IP2=SYS
        Mcu.IPNb=3
        Mcu.Name=STM32F407Z(E-G)Tx
        Mcu.Package=LQFP144
        Mcu.Pin0=PH0-OSC_IN
        Mcu.Pin1=PH1-OSC_OUT
        Mcu.Pin2=PA13
        Mcu.Pin3=PA14
        Mcu.Pin4=PA15
        Mcu.Pin5=PB3
        Mcu.Pin6=PB4
        Mcu.PinsNb=7
        Mcu.UserName=STM32F407ZGTx
        MxCube.Version=4.6.0
        MxDb.Version=DB.4.0.60
        NVIC.PriorityGroup=NVIC_PRIORITYGROUP_4
        NVIC.SysTick_IRQn=true:0:0:true
        PA13.Mode=JTAG(5-pin)
        PA13.Signal=SYS_JTMS-SWDIO
        PA14.Mode=JTAG(5-pin)
        PA14.Signal=SYS_JTCK-SWCLK
        PA15.Mode=JTAG(5-pin)
        PA15.Signal=SYS_JTDI
        PB3.Mode=JTAG(5-pin)
        PB3.Signal=SYS_JTDO-SWO
        PB4.Mode=JTAG(5-pin)
        PB4.Signal=SYS_JTRST
        PCC.Family=STM32F4
        PCC.MCU=STM32F407Z(E-G)Tx
        PCC.MXVersion=4.6.0
        PCC.PartNumber=STM32F407ZGTx
        PCC.Seq0=0
        PCC.SubFamily=STM32F407/417
        PCC.Temperature=25
        PCC.Vdd=3.3
        PH0-OSC_IN.Mode=HSE-External-Oscillator
        PH0-OSC_IN.Signal=RCC_OSC_IN
        PH1-OSC_OUT.Mode=HSE-External-Oscillator
        PH1-OSC_OUT.Signal=RCC_OSC_OUT
        ProjectManager.AskForMigrate=true
        ProjectManager.BackupPrevious=false
        ProjectManager.CompilerOptimize=2
        ProjectManager.ComputerToolchain=false
        ProjectManager.CoupleFile=true
        ProjectManager.DeletePrevious=true
        ProjectManager.DeviceId=STM32F407ZGTx
        ProjectManager.FirmwarePackage=STM32Cube FW_F4 V1.4.0
        ProjectManager.FreePins=false
        ProjectManager.HalAssertFull=false
        ProjectManager.KeepUserCode=false
        ProjectManager.LastFirmware=true
        ProjectManager.LibraryCopy=0
        ProjectManager.ProjectBuild=false
        ProjectManager.ProjectFileName=Test03.ioc
        ProjectManager.ProjectName=Test03
        ProjectManager.TargetToolchain=TrueSTUDIO 4.3.1
        ProjectManager.ToolChainLocation=
        RCC.48MHZClocksFreq_Value=84000000
        RCC.AHBFreq_Value=168000000
        RCC.APB1CLKDivider=RCC_HCLK_DIV4
        RCC.APB1Freq_Value=42000000
        RCC.APB1TimFreq_Value=84000000
        RCC.APB2CLKDivider=RCC_HCLK_DIV2
        RCC.APB2Freq_Value=84000000
        RCC.APB2TimFreq_Value=168000000
        RCC.CortexFreq_Value=21000000
        RCC.EthernetFreq_Value=168000000
        RCC.FCLKCortexFreq_Value=168000000
        RCC.FamilyName=M
        RCC.HCLKFreq_Value=168000000
        RCC.HSE_VALUE=25000000
        RCC.HSI_VALUE=16000000
        RCC.I2SClocksFreq_Value=96000000
        RCC.IPParameters=LSI_VALUE,APB1TimFreq_Value,APB2Freq_Value,MCO2PinFreq_Value,APB1CLKDivider,FCLKCortexFreq_Value,AHBFreq_Value,48MHZClocksFreq_Value,VCOInputFreq_Value,I2SClocksFreq_Value,PLLSourceVirtual,SYSCLKFreq_VALUE,SYSCLKSource,LSE_VALUE,HSE_VALUE,HSI_VALUE,VCOI2SOutputFreq_Value,PLLCLKFreq_Value,RTCFreq_Value,FamilyName,HCLKFreq_Value,EthernetFreq_Value,APB2CLKDivider,PLLM,PLLN,VCOOutputFreq_Value,VcooutputI2S,CortexFreq_Value,APB1Freq_Value,RTCHSEDivFreq_Value,APB2TimFreq_Value
        RCC.LSE_VALUE=32768
        RCC.LSI_VALUE=32000
        RCC.MCO2PinFreq_Value=168000000
        RCC.PLLCLKFreq_Value=168000000
        RCC.PLLM=25
        RCC.PLLN=336
        RCC.PLLSourceVirtual=RCC_PLLSOURCE_HSE
        RCC.RTCFreq_Value=32000
        RCC.RTCHSEDivFreq_Value=12500000
        RCC.SYSCLKFreq_VALUE=168000000
        RCC.SYSCLKSource=RCC_SYSCLKSOURCE_PLLCLK
        RCC.VCOI2SOutputFreq_Value=192000000
        RCC.VCOInputFreq_Value=1000000
        RCC.VCOOutputFreq_Value=336000000
        RCC.VcooutputI2S=96000000

        Reply
  8. Great utility. I had to make some slight modifications to the generated Makefile to use it with the cmd.exe terminal on windows that comes with GNU make. The mkdir implementation doesn’t support command line options like -p. Also, there is no /dev/null mapping. Otherwise it worked flawlessly.

    Reply
  9. Thanks for a very useful tool!

    Few changes were needed, but I got a makefile and a successful build, so I call that success!

    1) Here:

    C_DEFS = -D__weak=__attribute__((weak)) -D__packed=__attribute__((__packed__)) -DUSE_HAL_DRIVER -DSTM32F303xC

    Bash complained about “unexpected token (” – it needed quotes around it, as follows:

    C_DEFS = -D__weak=”__attribute__((weak))” -D__packed=”__attribute__((__packed__))” -DUSE_HAL_DRIVER -DSTM32F303xC

    The ld file in TrueStudio was empty, so I generated a WS4 project and copied the LD script from there. I hope that’ll work.

    Reply
  10. This works very well, and is a most welcome addition to my toolset. A couple of comments though: first, it seems to want the project saved as SW4 rather than TrueStudio (not a problem, but has it changed? and when?), and second that the linker command includes -specs=nano.specs and the build fails until I remove that switch.

    Reply
    • Yes it has been changed to SW4STM32. This is in the history.txt file. -specs=nano.specs uses nanolib from GCC which reduces binary size. Maybe you can try update your ARM-GCC toolchain to have this recognized.

      Reply
  11. A little suggestion, having used this excellent tool a few times. It would suit Eclipse better if the c_defs were written as #defines in a .h file rather than as -D command line arguments, as the right sections would then get greyed out in the editor. I’d do it myself except I don’t speak Python!

    Reply
    • Hi Paul,
      I assume you’re using Eclipse CDT. Under Project Properties, find “C/C++ Generals”, “Preprocessor Include Paths, Macros”, etc, check “CDT GCC Output Parser”, then change the “Command Pattern” below to (arm-none-eabi-gcc), this will enable eclipse to discover -D defineds from the gcc command line.
      I hope this will help your editing.

      Reply
  12. ST has modified the path locations for the CubeMX SW4STM32 outputs. There is no longer a configuration label added to the folder and the python checks fail.

    Reply
  13. I’m unable to compile .cpp files this way, am I doing something wrong or the generated makefile is not supposed to deal with cpp files?

    Reply
  14. This seems very nice!
    Though im running into some problems, first it stops because it says it cant find any file named disc.map, and if i remove the part looking for that i get no rule for hex required by all.

    Any Idea?

    Reply
  15. Thanks for this great tool.
    I just downloaded STM32CubeMx but it is now version 4.14.0. I am running it with SW4STM32 Outputs and it seems some changes happened as I had to modify the script to pick up the project Files and library directly from the Tool chain folder. However, even with these changes, it seems that the script no longer picks up the source files. C_SOURCES and ASM_SOURCES are empty. Could it be possible that the sources now need to be taken from .mxproject? I am willing to hack but as I haven’t worked with STM32CubeMx before, I would appreciate some pointers.

    Thank you

    Reply
  16. Not sure where I’m going wrong. I’m running this on OS X

    ~/CubeMX2Makefile/CubeMX2Makefile.py ~/tmp/CubeTest
    Unable to find target MCU node. Error: ‘NoneType’ object has no attribute ‘attrib’

    In the python code, there’s a references to other stuff —

    mcu_node = root.find(‘.//toolChain[@superClass=”fr.ac6.managedbuild.toolchain.gnu.cross.exe.debug”]/option[@name=”Mcu”]’)

    Which would indicate a code dependence. Does this require eclipse to be installed ?

    Reply
    • Me too, it seems that .cproject syntax generated by latest STM32CubeMX-4.18.0 has changed and the script cannot find necessary values – need an update. BTW latest STM32CubeMX has not any option for Truestudio version, only one choice

      Reply

Leave a Reply