Use Arduino framework for a custom STM32 board


I’m upgrading from an Arduino mega 2560 to a custom designed board, based on an STM32F407VG processor, and would like to remain in an Arduino framework. However, when creating the project I’m requested to choose from the existing boards, which obviously have completely different pinout than what my board has.

Is there a quick way to configure my project to support a new board, without resorting to ST’s cubeMX framework?


Are you really sure you can’t use preset boards like Black STM32F407VG — PlatformIO latest documentation and the associated BLACK_F407XX/variant.h default pins and clock init? In code you can always use explicit pin names for initializing stuff (peripherals etc).

So if I understand you correctly, you want to create your own Arduino-STM32 variant which has the default pins for Serial, I2C, SPI, LEDs, Timers and clocks (HSE/HSI, LSI/LSE) setup?

Yes, I’m developing a robot, based on a custom designed board which incorporates the STM32 and wanted to customize an Arduino-STM variant to control the required resources

I have actually tried using the black_f407vg, but unfortunately, after uploading a very simple FW toggling a GPIO, the board just did not respond. Using genericSTM32F407VGT6 with the below settings gave better results, however the settings seem much more “tailored” to the original board, than the variant.h you’ve suggested, hence we found it very hard to work out PWMs, serial port etc.

platform = ststm32
board = genericSTM32F407VGT6
framework = arduino

If you want to create a new STM32Duino core variant, this is the general procedure:

  1. Create a custom board JSON file docs. You can basically copy and adapt black_f407vg since it’s the same chip and target framework – however change the variant field to some other name and the -DARDUINO_BLACK_F407VG accordingly to the new variant name. I’ll just demonstrate it with MY_ROBOT as the variant name here. Save this JSON file under some name in the boards/ directory of the project, e.g. boards/my_robot.json.
  2. Setup the platformio.ini to point to your newly created board.
platform = ststm32
board = my_robot ; json file without extension
framework = arduino
  1. Configure extra configuration flags for STM32Duino as needed.
  2. Create a new variant folder in the STM32Duino framework. Go to C:\Users\<users>\.platformio\packages\framework-arduinoststm32\variants. Duplicate the BLACK_F407XX under the name MY_ROBOT. This must match the variant field in the JSON file. You can also duplicate Generic_F4x7Vx if you like and it’s closer to a working state.
  3. Make sure to read the STM32Duino guide for adding a new variant to understand the configuration possibilities. You won’t have to do any really ground-work though since stuff like the PeripheralPins.c are already pre-provided from the copied variant.
  4. Adapt the variant files as needed. In the case of choosing the BLACK_407XX as template, make sure you remove the #if defined(ARDUINO_BLACK_F407VG) stuff in the header file and the colliding #if defined(ARDUINO_BLACK_F407ZE) || defined(ARDUINO_BLACK_F407ZG) pin definitions in the variant.cpp and .h file. Adapt the variant.h for default pins for peripherals and the cpp file for clock init (by default it expects an 8MHz crystal for the HSE oscillator – if there’s no crystal, change the code to HSI. STM32Cube auto-generates the startup code.)
  5. You should be able to compile a simple project now to test basic functionality, like if the setup() function is ever reached, whether digital I/O works, serial, SPI, etc.
  6. Once you have finalized your variant files inside the framework-arduinoststm32 folder you can upload the contents of the folder to a repository and point to it using platform_packages, e.g.
platform_packages =

that makes it completely portable.
8. If it’s a publically buyable board, it might make sense to feed back the created variant to STM32Duino through a pull-request.

1 Like

Thank you for the thorough reply!

I’ll follow the above instructions and let you know how it worked

FYI for people reading this at a later time, you don’t have to modify your framework folder ( C:\Users\<users>\.platformio\packages\framework-arduinoststm32), you can also create a project-local new variant and board definition, as shown in e.g. GitHub - maxgerhardt/pio-custom-stm32duino-variants: A short example of how to use a custom variant folder for the PlatformIO + STM32Duino environment.