Unless you use only Arduino IDE 2, you will need to use whatever
command line shell your development computer operating system has to
make use of this framework. macOS and Linux computers (including Linux
On ChromeOS aka Crostini containers)
always have one or more command line shells, named something like
Terminal or Console.
In order to use this framework, you will first need to clone the
arm-mcu git repository with the
following command:
git clone https://github.com/pmunts/arm-mcu.git
After you have cloned the repository, you will most likely want to set
the ARMSKETCHBOOK environment variable to point to the arduino/
subdirectory of the arm-mcu checkout directory (e.g.
export ARMSKETCHBOOK=$HOME/arm-mcu/arduino). You can add the export
command to e.g. ~/.bashrc to make it permanent.
An Arduino Framework for ARM MCU Platforms project directory
contains a number of files. The easiest way to create a new project is
with the arduino-arm-newproject shell script:
$HOME/arm-mcu/arduino/scripts/arduino-arm-newproject myproject
Each Arduino Framework for ARM MCU Platforms program project
contains a minimal Makefile for gmake that simply defines a default
value for the macro ARMSKETCHBOOK and then includes
$(ARMSKETCHBOOK)/libraries/MuntsTech_ARM/Arduino_ARM.mk, which defines
default values for some more macros and the project default target
arduino_arm_mk_default, and finally includes a platform dependent
board family gmake include file selected by the BOARDFAMILY macro.
BOARDFAMILY Value |
Description | Core Package | Default BOARDNAME |
|---|---|---|---|
RP2040 |
Raspberry Pi RP2040 boards | Arduino-Pico | sparkfun_promicrorp2040 |
RP2350 |
Raspberry Pi RP2350 boards | Arduino-Pico | sparkfun_promicrorp2350 |
Disco |
STMicroelectronics Discovery evaluation boards | STM32Duino | DISCO_F407VG |
Nucleo_32 |
STMicroelectronics Nucleo-32 evaluation boards | STM32Duino | NUCLEO_L432KC |
Nucleo_64 |
STMicroelectronics Nucleo-64 evaluation boards | STM32Duino | NUCLEO_F411RE |
Nucleo_144 |
STMicroelectronics Nucleo-144 evaluation boards | STM32Duino | NUCLEO_F767ZI |
This is a small subset of the vast variety of 32-bit ARM microcontrollers supported by the Arduino ecosystem, and limited to the boards that I actually possess and can validate support for. It is almost trivially easy to add support for more board families.
All of the STM32 board families I have chosen to support have an on-board ST-LINK in-circuit debugger/flash programmer.
Builds the sketch with arduino-cli compile.
Uploads (more properly: Downloads) the compiled sketch with
arduino-cli upload to a target microcontroller board.
For the RP2040 and RP2350 board families, setting environment
variable FLASHPICO=yes before make install switches from
arduino-cli upload to a script named
flashpico.
Across the range of RP2040 and RP2350 boards, and
Chromebook/Linux/macOS/Windows development host computers, I have found
flashpico to be more reliable than arduino-cli upload.
Removes working files (i.e. build/).
Equivalent to clean install.
The exact target board is selected by two gmake macros: BOARDFAMILY
and BOARDNAME. Both of these can and should be initialized by
environment variables before invoking gmake.
For the RP2040 and RP2350 board families, the Arduino FQBN (Fully Qualified Board Name) shall be defined as:
ARDUINOFQBN := rp2040:rp2040:$(BOARDNAME)
For the various STM32 board families, the Arduino FQBN passed to
arduino-cli shall be defined as:
ARDUINOFQBN := STMicroelectronics:stm32:$(BOARDFAMILY):pnum=$(BOARDNAME),upload_method=swdMethod
The following shell pseudocode illustrates how to build an Arduino
Framework for ARM MCU Platforms project with gmake (most operating
systems symlink or alias make to gmake):
export ARMSKETCHBOOK=<your arm-mcu checkout directory>/arduino
export BOARDFAMILY=<your board family>
export BOARDNAME=<your board name>
make <your make target>
export ARMSKETCHBOOK=$HOME/arm-mcu/arduino
export BOARDFAMILY=RP2040
export BARDNAME=sparkfun_promicrorp2040
# Build without flashing target board
make build
# Flash target board without rebuilding unnecessarily
make install
# The two following commands are equivalent:
# Build from scratch and then flash target board
make clean install
make
# Use flashpico instead of arduino-cli upload
export FLASHPICO=yes
make
To use this framework within the Arduino IDE 2, all you need to do is:
- Start Arduino IDE 2.
- Select your target platform from
Tools → Board. - Select the communication port from
Tools → Port. - Set the sketchbook directory to your Arduino Framework for ARM
MCU Platforms checkout directory (e.g.
~/arm-mcu/arduino/) fromFile → Preferences → Sketchbook location.
Your project directory does not need to be within the Arduino Framework for ARM MCU Platforms checkout directory tree.
The Arduino IDE 2 does not use anything from the GNU make project
except for the sketch source file(s).
An official Arduino IDE 2 release Debian package for Linux x86-64 aka amd64 machines and an unofficial release Debian package for arm64 aka AArch64 machines are available at the Munts Technologies Debian Package Repository.
You will need to install the Microsoft C/C++ for Visual Studio
Code extension and
invoke Visual Studio Code with make code or make edit instead of
the usual code .. The gmake targets code or edit prepend some
environment variables to the code command that are necessary for
IntelliSense to find system header files.
IntelliSense for Arduino Framework for ARM MCU Platforms projects is not perfect: Indexing library source files within the Arduino core packages can take a very long time, and declarations and/or definitions qualified by preprocessing directives are often invisible, as they often cannot be resolved until compile time. On the whole, I still prefer Visual Studio Code over Arduino IDE 2, because the latter does not store target configuration in the project directory.
The file .vscode/tasks.json within each Arduino Framework for ARM
MCU Platforms project defines some task actions make <program> et
al that simply run make clean install et al. These can be invoked
from the command menu Terminal → Run Task... or
Terminal → Run Build Task....
The most efficient way to build and install from within Visual Studio
Code is to press CONTROL + SHIFT + B (⌘ + SHIFT + B for macOS), the
shortcut key sequence for Run Build Task....
FreeRTOS is an open source lightweight Real Time Operating System that has been ported to many microcontrollers, including ARM 32-bit microcontrollers. FreeRTOS was originally published in 2003 by Richard Barry. Amazon Web Services acquired ownership or a least stewardship of the FreeRTOS project in 2017, apparently to facilitate the creation of microcontroller Internet of Things nodes to feed AWS backend applications. FreeRTOS has been very widely used throughout the world by developers across industries ranging from hobbyists to Fortune 500 companies.
To enable FreeRTOS, just add #define ENABLE_FREERTOS before
#include <Arduino_ARM.h>.
The Arduino-Pico core package for RP2040 and RP2350 microcontrollers includes a tightly integrated implementation of FreeRTOS SMP (Symmetric Multi-Processing). The following minimal sketch skeleton illustrates how to create a multicore RP2040 or RP2350 Arduino FreeRTOS application:
#define ENABLE_FREERTOS
#include <Arduino_ARM.h>
void Task0(void *parameters)
{
vTaskCoreAffinitySet(NULL, 0x01); // Pin task to core 0
for (;;)
{
taskYIELD();
}
}
void Task1(void *parameters)
{
vTaskCoreAffinitySet(NULL, 0x02); // Pin task to core 1
for (;;)
{
taskYIELD();
}
}
void setup()
{
xTaskCreate(Task0, "task0", 512, NULL, 1, NULL);
xTaskCreate(Task0, "task1", 512, NULL, 1, NULL);
}
All of loop(), setup1(), and loop1() are optional. For
compatibility, an idle task running on core 0 will call loop() if it
is defined and an idle task running on core 1 will call loop1() if it
is defined. The Arduino-Pico main() function calls
vTaskStartScheduler() therefore setup() must not call it again.
For this reason, Arduino_ARM.h defines vTaskStartScheduler() as an
empty macro for RP2040 and RP2350 platforms, with the side effect that
the classic STM32 FreeRTOS sketch in the next subsection will also run
on RP2040 and RP2350 boards.
To build an RP2040 or RP2350 FreeRTOS application, you must append
:os=freertos to the FQBN (Fully Qualified Board Name). When building
with gmake, either from the command line or from Visual Studio Code,
this is automatically done by RP2040.mk or RP2350.mk. When building
with Arduino IDE 2, this must be done explicitly from
Tools → Operating System → FreeRTOS SMP.
Because of how well FreeRTOS has been integrated into the Arduino-Pico core package, it is now probably easier to develop a FreeRTOS application for an Arduino RP2040 or RP2350 platform than for any other hardware/software combination.
Note: Many, if not most, STM32 Nucleo evaluation boards have too little
RAM to run FreeRTOS, especially if the sketch creates C++ object
instances with the new operator which uses memory from the
heap.
The
Nucleo-L432KC
and
Nucleo-F411RE
successfully run
test_button_led_freertos.
The STM32FreeRTOS Arduino
library provides FreeRTOS support for STM32 microcontrollers. Since it
is delivered as a library, it is not integrated as tightly with the
STM32 core package, and FreeRTOS applications for Arduino are
implemented exactly the same as with any other GCC C or C++ framework,
albeit with the FreeRTOS setup code moved from main() to setup().
The following minimal sketch skeleton illustrates how create an STM32
Arduino FreeRTOS application:
#define ENABLE_FREERTOS
#include <Arduino_ARM.h>
void Task0(void *parameters)
{
for (;;)
{
taskYIELD();
}
}
void setup()
{
xTaskCreate(Task0, "main", 512, NULL, 1, NULL);
vTaskStartScheduler();
}
void loop()
{
}
Your setup() function must call xTaskCreate() to create at least one
FreeRTOS task and then call vTaskStartScheduler() which does not
return and replaces all of the normal Arduino background processing. For
compatibility, the FreeRTOS idle task calls loop(), which is not
optional.
Questions or comments to Philip Munts phil@munts.net