Linux Quick Start: Difference between revisions

From Miosix Wiki
Jump to navigation Jump to search
mNo edit summary
mNo edit summary
 
(19 intermediate revisions by 3 users not shown)
Line 1: Line 1:
This page explains how to install the precompiled Miosix Toolchain. If you prefer compiling GCC from sources, see [[Building GCC from sources]].


=== Before you begin ===
= Installing the required software =


'''64 bit Linux distros'''
== Install the Miosix Toolchain ==


The precompiled Miosix Toolchain is compiled for 32bit x86, to be compatible with as many Linux installations as possible. If you have a 64bit OS, you need to install a few 32bit libraries to be able to use it.
To be able to compile the Miosix kernel and your application, you need a patched version of the GCC compiler called [[Miosix Toolchain]]. This page explains how to install the precompiled Miosix Toolchain. If you prefer compiling GCC from sources, see [[Building GCC from sources]]. The commands to run are as follows, where you'll need to replace <version> with the (usually latest) version found in the [[Miosix Toolchain]] page.


<source lang="bash">
<source lang="bash">
sudo apt-get install libstdc++6:i386 # Install 32bit compatibility libraries for Ubuntu/Debian
wget https://miosix.org/toolchain/MiosixToolchainInstaller<version>.run
sudo pacman -S lib32-libstdc++5      # Install 32bit compatibility libraries for Arch Linux
sh MiosixToolchainInstaller<version>.run
</source>
</source>


''' QSTLink2 '''
The installer will ask for your root password to copy the compiler to the ''/opt'' directory, and put symlinks to ''/usr/bin''. If you later want to uninstall the compiler, as part of the installation process an ''uninstall.sh'' script is placed together with the compiler in ''/opt/arm-miosix-eabi''. Uninstalling the previous compiler is done automatically when upgrading to a newer version.


If you want to program STM32 microcontrollers, you will also need a tool to the transfer your programs to the microcontroller. A popular choice for boards like the ''stm32f4discovery'' that have an embedded STLinkV2 USB programmer/debugger is [https://code.google.com/p/qstlink2 QSTLink2]. The installation on Ubuntu/Debian requires to add a ''ppa'' and install it via ''apt-get''. Also, it is recomended to install the udev rules, which allow QSTLink2 to connect to the USB port without the need to run it from root.
If you do not trust the installer and want to verify its content, or you want to install it locally (in your home folder instead of system-wide), it is possible to extract the content of the installer with the following command. This operation also extracts, without running it, the ''installer.sh'' installation script.


<source lang="bash">
<source lang="bash">
sudo add-apt-repository ppa:fpoussin/ppa
sh MiosixToolchainInstaller<version>.run --noexec --keep
sudo apt-get update
sudo apt-get install qstlink2
wget https://raw.githubusercontent.com/mobyfab/QStlink2/master/res/49-stlinkv2.rules
sudo mv 49-stlinkv2.rules /etc/udev/rules.d
sudo chown root:root /etc/udev/rules.d/49-stlinkv2.rules
</source>
</source>


An alternative tool to program STM32 microcontrollers using the serial port bootloader is [https://code.google.com/p/stm32flash stm32flash]. Finally, for historical reasons, the Miosix Toolchain includes ''lpc21isp'', a tool to program LPC2000 microcontrollers using their serial bootloader.
For a local install you will need to set the ''PATH'' environment variable to include the extracted ''arm-miosix-eabi/bin'' directory.


''' Serial port setup '''
== Install a flashing tool ==


Miosix redirects ''stdin''/''stdout'' to a serial port by default on most boards, so it is important to set up serial ports correctly on your development machine. On most Linux distros serial ports, both the physical ones like ''/dev/ttyS0'' and the USB to serial adapters like ''/dev/ttyUSB0'' are owned by the ''dialout'' group, so you need to add your user to that group before you can access them.
With the installed Miosix toolchain you'll be able to compile the kernel, but you'll also need a way to transfer it to your microcontroller. This operation is usually called 'flashing' the microcontroller. Miosix can work with any flashing utility that accepts as input raw binary files, so pick whatever your GNU/Linux distro of choice provides. Here is a list of suggestions for the most common microcontrollers used with Miosix: [[Linux flashing tools]].
 
== Serial port setup ==
 
Miosix redirects ''stdin''/''stdout'' to a serial port by default on most boards, so to see the boot log and the output of ''printf()'' in your application you need a program to interact with the serial port. A common one is ''GNU screen'', but there are alternatives such as ''minicom'' or ''tio''.


<source lang="bash">
<source lang="bash">
sudo usermod -a -G dialout `id -un` # Add yourself to the dialout group
sudo apt install screen # For Ubuntu/Debian
sudo pacman -S screen  # For Arch Linux
</source>
</source>


Note that you may need to reboot your computer before the change takes effect. Also, you need a program to interact with the serial port, like ''GNU screen''.
 
On most GNU/Linux distros serial ports and USB to serial adapters like ''/dev/ttyUSB0'' and ''/dev/ttyACM0'' are owned by the ''dialout'' group, so to avoid the need to use ''sudo'' every time you run ''screen'' you need to add your user to that group before you can access them.


<source lang="bash">
<source lang="bash">
sudo apt-get install screen # For Ubuntu/Debian
sudo usermod -a -G dialout `id -un` # Add yourself to the dialout group
sudo pacman -S screen      # For Arch Linux
</source>
</source>


=== Install the Miosix Toolchain ===
Note that you may need to reboot your computer before the change takes effect.


Download the latest version of the [[Miosix Toolchain]] and launch it. The installer will ask for your root password to copy the compiler to the ''/opt/arm-miosix-eabi'' directory, and put symlinks to ''/usr/bin''.  
= Downloading and configuring the Miosix kernel =
 
To download the Miosix kernel you need [https://en.wikipedia.org/wiki/Git_%28software%29 git]. If you do not already have it installed you can install it now


<source lang="bash">
<source lang="bash">
wget https://miosix.org/toolchain/MiosixToolchainInstaller.run
sudo apt install git # For Ubuntu/Debian
sh MiosixToolchainInstaller.run
sudo pacman -S git  # For Arch Linux
</source>
</source>


If you do not trust the installer and want to verify its content, or you want to install it locally, it is possible to extract the content of the installer with the following command.
This section is a stripped down guide with the bare minimum to get you started, we also have a full guide about [[Miosix and git workflow]]. Following the tutorial in this page, your project directory will '''not''' be under version control (git). The [[Miosix and git workflow]] page shows how to create a git repository for your project and add the Miosix kernel as a git submodule.
 
Before downloading the kernel, however, you first have to create '''a directory for your project''' (in this case, the hello world), and then clone the kernel '''as a subdirectory'''.


<source lang="bash">
<source lang="bash">
sh MiosixToolchainInstaller.run --noexec --target arm-miosix-eabi
mkdir hello
cd hello
git clone https://github.com/fedetft/miosix-kernel.git
</source>
</source>


Keep in mind that for a local install you will need to set the ''PATH'' environment variable to the ''arm-miosix-eabi/bin'' directory.
== Initializing a Miosix project ==


=== Get the Miosix kernel sources ===
For reasons explained in depth in the [[Miosix and git workflow]] page, you'll need to copy the Miosix configuration directory from the kernel sources to your project directory, as well as create a template project where you can start writing code.
This can be automated with a [https://en.wikipedia.org/wiki/Perl Perl] script called ''init_project_out_of_git_tree.pl'':


The preferred way to download the Miosix kernel is through [https://en.wikipedia.org/wiki/Git_%28software%29 git]. If you do not already have it installed you can install it now
<source lang="bash">
perl miosix-kernel/tools/init_project_out_of_git_tree.pl
</source>
 
You should run the script from the directory where you want to initialize your empty project, such as the '''hello''' directory in this tutorial. A successful run of the script produces the following output:


<source lang="bash">
<source lang="bash">
sudo apt-get install git # For Ubuntu/Debian
Successfully created Miosix project
sudo pacman -S git      # For Arch Linux
Target directory: hello
Kernel directory: hello/miosix-kernel/miosix
</source>
</source>


The Miosix git repository used to be hosted at [http://gitorious.org gitorious.org], but the service was shut down. For this reason, the kernel is now hosted directly at miosix.org. There is also a [https://github.com/fedetft/miosix-kernel github mirror] and the two repositories will be always kept in sync. Currently, the ''master'' branch contains the stable 2.0 kernel, while the ''testing'' branch contains the current development version. Kernel versions prior to 2.0 are deprecated.
Although Perl is pre-installed in almost all GNU/Linux distros, this script depends on the ''File::Copy::Recursive'' Perl module which often is not. If you get errors running the script, install the missing module as follows and try again:


<source lang="bash">
<source lang="bash">
git clone https://miosix.org/git-public/miosix-kernel.git
sudo apt install libfile-copy-recursive-perl # For Ubuntu/Debian
cd miosix-kernel
git fetch origin
## To select the development version of the kernel
#git checkout -b testing origin/testing
</source>
</source>


=== Configuring and compiling the kernel ===
Your project directory should now look like the following picture, with the ''miosix-kernel'' directory containing the kernel sources, the ''config'' directory with the kernel configuration, the empty ''main.cpp'' and the build files for the two alternative build systems supported by Miosix: Makefile and CMake:
 
More in-depth information on how th configure the kernel for your board can be found in the [[Board list]], but for now we will assume you have an stm32f4discovery, which is a common board, and briefly show how to get to a blinking LED example.


'''Top-level directory'''
[[File:Initialized-miosix-project-linux.png]]


First of all the miosix-kernel directory is often referred to as the '''top-level directory''' of the kernel. It contains, among other, the ''main.cpp'' file which is where you can start writing your application code, the ''Makefile'' where you can add additional C++ and C source files to be compiled, and the ''miosix'' directory which contains the kernel.
For this tutorial, we'll use the Makefile build system, have a look at the [[CMake]] page to learn how to use CMake instead.


[[File:Miosixtopleveldirectorylinux.png]]
== Configuring the kernel ==


All paths in this wiki, unless they start with a '/' (for Linux) or 'C:\' (For Windows), are intended relative to Miosix's top-level directory, so if we're talking about the 'miosix/config/Makefile.inc' file you can find it within the directory where you have downloaded the kernel from git.
The minimum configuration required to compile the kernel is to '''select a board''', as the kernel needs to build the appropriate board support package for it.


'''Configuring the kernel'''
The Miosix kernel has several other build-time configuration options, to enable optional components (filesystem, userspace processes), select algorithms such as the scheduler and trade feature support for code size, but these won't be covered here.
The kernel is configured by editing files in the config directory, the two most important ones are [https://github.com/fedetft/miosix-kernel/blob/master/miosix/config/Makefile.inc Makefile.inc] and [https://github.com/fedetft/miosix-kernel/blob/master/miosix/config/miosix_settings.h miosix_settings.h].


The kernel is configured by editing two files, named [[Makefile.inc|miosix/config/Makefile.inc]] and [[miosix_settings.h|miosix/config/miosix_settings.h]]. Open the first one, and select your board. To do so, look for the ''OPT_BOARD'' section of the file, which looks like this:
To select a board, open the first one, ''config/Makefile.inc''. Look for the ''OPT_BOARD'' section of the file, which contains the list of boards officially supported by the kernel. In this section, all boards appear commented out (the ''#'' sign is a comment in Makefile syntax), so you need to uncomment the line corrsponding to your board. [[Porting]] the kernel to a new board is an advanced topic not covered here, so we'll assume you'll want to use an officially supported board. As an example, in this tutorial we'll use the stm32f746zg_nucleo board:


<source lang="bash">
<source lang="bash">
##
...
## Target board, choose one. This also implicitly select the target
#OPT_BOARD := stm32f469ni_stm32f469i-disco
## architecture
OPT_BOARD := stm32f746zg_nucleo
##
#OPT_BOARD := stm32f765ii_marco_ram_board
#OPT_BOARD := lpc2138_miosix_board
...
OPT_BOARD := stm32f103ze_stm3210e-eval
#OPT_BOARD := stm32f103ve_mp3v2
#OPT_BOARD := stm32f100rb_stm32vldiscovery
#OPT_BOARD := stm32f103ve_strive_mini
#OPT_BOARD := stm32f103ze_redbull_v2
#OPT_BOARD := stm32f407vg_stm32f4discovery
#OPT_BOARD := stm32f207ig_stm3220g-eval
#OPT_BOARD := stm32f207zg_ethboard_v2
#OPT_BOARD := stm32f207ze_als_camboard
#OPT_BOARD := stm32l151_als_mainboard
#OPT_BOARD := stm32f407vg_bitsboard
#OPT_BOARD := stm32f205rg_sony-newman
</source>
</source>
In Makefile syntax a '#' sign denotes a comment, so to select a board you have to comment out (by prepending a '#') the default board selected, and uncomment (by removing the '#' at the start of the line) your board, in this case, which in this example will assume is the ''stm32f407vg_stm32f4discovery''.


Next, edit the ''miosix_settings.h'' file and uncomment (by removing the '//' at the start of the line) the following line
If you do not yet have a board, you can follow along and get to the compiled firmware anyway. If you're looking for suggestions on which board to get, consider that most boards currently supported by Miosix are for STM32 microcontrollers. Here's a basic guide:
<source lang="CPP">
* '''Nucleo''' STM32 boards produced by ST are good for beginners, as they allow to power the board, flash it, debug it and access the serial port all through a single USB connection with your computer. The stm32f401re_nucleo and stm32f411re_nucleo are realtively low cost.
//#define JTAG_DISABLE_SLEEP
* '''Discovery''' STM32 boards are also good, but they don't include an USB to serial adapter so you'll have to buy it separately and you'll end up having to connect two USB cables, one for power/programming/debugging and one for the serial port.
</source>
* '''Third party''' STM32 boards such as the stm32f411ce_blackpill are cheaper and great to embed in your hardware project, but you'll have to [https://en.wikipedia.org/wiki/Soldering solder] the pin header yourself, and you'll need to attach a separate USB to serial adapter, and if you want in-circuit debugging you'll need an STLink adapter, so you'll end up having to run up to three separate USB cables from your computer to the board for power/programming, serial port and debugging.
(which is towards the end of the file). This is a C++ header file, so the comment syntax is '//'. More information on the meaning of this line can be found in [[miosix_settings.h]], but a short summary is that this line prevents the kernel from putting shutting down the CPU when it has nothing to do, which saves power but interferes with the programming/debugging protocol used to program the board via QSTLink2.
* Venturing outside of STM32, the '''RP2040''' is a good choice. Also in this case, you'll need a separate USB to serial adapter and some soldering skills, though.


Also, comment out the ''#error'' line towards the beginning of the file. This line exists to cause a compilation error if the user forgets to edit the ''miosix_settings.h'' file. The result should look like this:
= Writing your first Miosix program =
<source lang="CPP">
// Before you can compile the kernel you have to configure it by editing this
// file. After that, comment out this line to disable the reminder error.
// The PARSING_FROM_IDE is because Netbeans gets confused by this, it is never
// defined when compiling the code.
#ifndef PARSING_FROM_IDE
//#error This error is a reminder that you have not edited miosix_settings.h yet.
#endif //PARSING_FROM_IDE
</source>


'''Blink a LED'''
== Hello world ==


Open the ''main.cpp'' file in the top-level directory, and replace its content with the following program:
Open the ''main.cpp'' file with your [[IDEs | IDE]] or text editor of choice, and replace its content with the following program:
<source lang="CPP">
<source lang="CPP">
#include <cstdio>
#include <thread>
#include <miosix.h>
#include <miosix.h>
#include <interfaces/bsp.h>
using namespace std;
using namespace miosix;
using namespace miosix;
int main()
int main()
{
{
     for(;;)
     for(;;)
     {
     {
        iprintf("Hello world\n");
         ledOn();
         ledOn();
         Thread::sleep(1000);
         this_thread::sleep_for(500ms);
         ledOff();
         ledOff();
         Thread::sleep(1000);
         this_thread::sleep_for(500ms);
     }
     }
}
}
</source>
</source>
The Miosix board support package defines the ''ledOn()'' and ''ledOff()'' functions to control a LED on the board for all the boards that have at least one software-accessible LED.


'''Compiling'''
At this point, it's good to have a quick walkthrough of this hello world program. Miosix is based on a [[Fluid kernel]] architecture: in a nutshell it's a kernel that supports writing applications both inside the kernel, and inside userspace programs. In this tutorial, we're using it as a unikernel. This means when power is applied to the board, the kernel will boot, and then start running the ''main()'' function you just wrote ''in kernelspace''. This means you have both support for C/C++ standard libraries and unrestricted hardware access.


To compile the kernel, open a terminal in the Miosix top-level directory and type ''make''. If all goes well, the result should look like this.
This main() function will print "Hello world" and blink an LED approximately every second.
The printing is done with the ''iprintf()'' function. If you expected just ''printf()'' without the ''i'', the reason is that Miosix uses the [https://sourceware.org/newlib/ Newlib] C standard library that provides both ''printf()'' and ''iprintf()'', an optimized version that is smaller in code size but incapable of printing floating point numbers. So you can also use ''printf()'' if you wish, but this optimization is worth knowing from the start.


[[File:Makeoutputlinux.png]]
Sleeping to blink the LED is done with the [https://en.cppreference.com/cpp/thread/sleep_for sleep_for()] function from the C++ standard library. Miosix supports other sleeping APIs, such as [https://pubs.opengroup.org/onlinepubs/9699919799/functions/nanosleep.html nanosleep()] from POSIX, or ''Thread::sleep()'', a native Miosix function. All these functions do the same thing: they tell the scheduler to stop the currently running thread, run some other thread, and resume execution after a given time interval. Miosix is a preemptive multithreading operating system, so you should get comfortable with the fact that the code you're writing lives in a thread and shares the CPU with other threads.


Otherwise, compiler errors will appear in the shell. The number that appears under ''text'' in the make output is the size in bytes of your application plus the kernel. If you think that 90KBytes is a bit too much for a blinking led, don't worry. The kernel by default includes support for C stdio functions, filesystem code including Unicode support and the C++ exception handling runtime, all of which can be disabled to significantly [[Miosix code size optimization|reduce code size]].
Many (but not all!) board support packages define the ''ledOn()'' and ''ledOff()'' functions to control one of the LED on the board. This should be true for all the boards that have at least one software-accessible LED. This is true for the ''stm32f746zg_nucleo'' board we selected, but if you selected a different board with no LEDs, then compiling will fail with an error related to ''ledOn()'' and ''ledOff()''. You can comment out those two lines in this case, your hello world will only print to the serial port.


'''Programming'''
== Compiling ==


There are two ways to program the stm32f4discovery board. One is to use QSTLink2 directly from the shell you already have open by typing 'make program' (connect the USB cable first!), the other is through QSTLink2's GUI.
To compile the kernel, open a terminal in the '''hello''' project directory and type:


[[File:Findqstlink2guilinux.png]]
<source lang="bash">
make -j`nproc`
</source>
 
The ''-j`nproc`'' is optional, it will compile faster by using the multicore CPU in your computer. If you know how many cores you have, you can also specify the number explicitly, such as ''make -j8''. If all goes well, the result should look like this:
 
[[File:Make-output-linux.png]]
 
Otherwise, compiler errors will appear in the shell. The number that appears under ''text'' in the make output is the size in bytes of your application plus the kernel. Don't worry about the 42KBytes code size, you're compiling with the default Miosix options, if you want you can play around with the options later to  [[Miosix code size optimization|reduce the code size]].
 
== Flashing ==


Once you start it, you have to click on ''Connect'', and it should find your ''stm32f4discovery'' board. After that, click on ''Send'' and select the ''main.bin'' file in the Miosix top-level directory.
To flash the board, you can use the ''make program'' Makefile rule to automatically download the kernel to the board. Connect the USB cable first, and then run:


[[File:Qstlink2flashinglinux.png]]
<source lang="bash">
make program
</source>


Note that, regardless of using QSTLink2 form the shell or the GUI, there is a bug that in some circumstances blocks the microcontroller until the next powercycle. Therefore, after having programmed the microcontroller, is is recomended to unplug and reconnect the USB cable to powercycle the ''stm32f4discovery'' board. At that point, you shuold see the red LED blinking.
If the operation completed successfully, then the output should be similar to this one, and the LED should blink on the board:


=== What's next? ===
[[File:Make program linux.png]]


You have finished the installation of the Miosix Toolchain. You may want to [[Quick start#IDE Configuration|install and configure an IDE]], or the [[Quick start#In-circuit debugger|debugger]].
If the operation did not succeed, here are some common problems:
* You get a ''command not found'' error. You probably did not install the right flashing tool on your computer, read here [[Linux flashing tools]].
* The flashing tool starts, but throws an error such as ''Couldn't find any ST-Link devices''. You probably do not have the right permissions to access the board. Try ''sudo make program''. If that one works, you'll have to install ''udev rules'' to make the USB device of your board's programming interface accessible from your user. Unfortunately the details to installing (or writing from scratch) the correct udev rules file depend on the combination of the flashing tool and board. None of these are specific to Miosix, so look online in the documentation of your flashing tool.


=== Uninstall the compiler ===
Another issue in some STM32 boards is that the flashing tool leaves the board in a state where the mcirocontroller blocks either after flashing or if you press the reset button on the board. This issue is again specific to the board and flashing tool and unrelated to Miosix. If you encounter this problem after having programmed the microcontroller, it is recommended to unplug and reconnect the USB cable to powercycle the board. At that point, you should see the LED blinking.


If for some reason you need to uninstall the compiler, there is an uninstall script in the ''/opt/arm-miosix-eabi'' directory (Note: if you have built the compiler from sources the uninstall script may not be there). Running the script will uninstall the compiler and the symbolic links in the ''/usr/bin'' directory. Just like the install script, the uninstaller will ask for your root password to be able to remove the installed files.
== Accessing the serial port ==


There is no need to uninstall and old compiler to install a new one, the installer will take care of that automatically. However, if you have installed the compiler and now you want to build it from sources, you first need to uninstall the old compiler.
Starting from Miosix v3.00, all boards use by default a baud rate of 115200bit/s.
If you're using a '''Nucleo''' board from ST, the USB to serial port adapter will appear on your computer as ''/dev/ttyACM0'', so use the ''screen'' program with the following parameters:


<source lang="bash">
<source lang="bash">
cd /opt/arm-miosix-eabi
screen /dev/ttyACM0 115200
./uninstall.sh
</source>
</source>


If you have chosen to install the compiler locally (i.e: not in the '/opt/arm-miosix-eabi' directory), simply remove the compiler directory.
Since the board will be already running when you connect, you can press the RESET button on the board to reboot it and see the boot logs:
 
[[File:Serial-view-linux.png]]
 
Exiting the screen program is cumbersome at first, but you'll get used to it quickly. You have to type ''Ctrl-A'', then ''k'' and ''y''. Typing ''Ctrl-C'' won't stop the program, it will just send a ''Ctrl-C'' to the microcontroller.
 
If you are using a board that does not have an integrated USB to serial adapter, you'll need to figure out to which pins is the default serial connected. To do so, you'll have to look for the kernel configuration file for your board. For example, for the ''stm32f411ce_blackpill'' the file is: [https://github.com/fedetft/miosix-kernel/blob/master/miosix/config/board/stm32f411ce_blackpill/board_settings.h config/board/stm32f411ce_blackpill/board_settings.h], where you'll find that the serial port TX pin is PA9, and the RX pin is PA10. Remember to cross the TX and RX pin, the TX pin of the microcontroller goes to the RX pin of the serial adapter! For reliable communication you'll also have to connect a wire between the board GND and the serial adapter GND.
 
Another example would be for the RP2040. In this case the configuration file is [https://github.com/fedetft/miosix-kernel/blob/master/miosix/config/board/rp2040_raspberry_pi_pico/board_settings.h config/board/rp2040_raspberry_pi_pico/board_settings.h] and the serial TX pin is P0.0, while RX is P0.1.
 
The most common standalone USB to serial adapters are based on the FTDI's FT232 chip, which appears on GNU/Linux as ''/dev/ttyUSB0'', so the command to access the serial port would be:
 
<source lang="bash">
screen /dev/ttyUSB0 115200
</source>


[[Category:Installation and Configuration]]
[[Category:Installation and Configuration]]

Latest revision as of 20:59, 10 May 2026

Installing the required software

Install the Miosix Toolchain

To be able to compile the Miosix kernel and your application, you need a patched version of the GCC compiler called Miosix Toolchain. This page explains how to install the precompiled Miosix Toolchain. If you prefer compiling GCC from sources, see Building GCC from sources. The commands to run are as follows, where you'll need to replace <version> with the (usually latest) version found in the Miosix Toolchain page.

wget https://miosix.org/toolchain/MiosixToolchainInstaller<version>.run
sh MiosixToolchainInstaller<version>.run

The installer will ask for your root password to copy the compiler to the /opt directory, and put symlinks to /usr/bin. If you later want to uninstall the compiler, as part of the installation process an uninstall.sh script is placed together with the compiler in /opt/arm-miosix-eabi. Uninstalling the previous compiler is done automatically when upgrading to a newer version.

If you do not trust the installer and want to verify its content, or you want to install it locally (in your home folder instead of system-wide), it is possible to extract the content of the installer with the following command. This operation also extracts, without running it, the installer.sh installation script.

sh MiosixToolchainInstaller<version>.run --noexec --keep

For a local install you will need to set the PATH environment variable to include the extracted arm-miosix-eabi/bin directory.

Install a flashing tool

With the installed Miosix toolchain you'll be able to compile the kernel, but you'll also need a way to transfer it to your microcontroller. This operation is usually called 'flashing' the microcontroller. Miosix can work with any flashing utility that accepts as input raw binary files, so pick whatever your GNU/Linux distro of choice provides. Here is a list of suggestions for the most common microcontrollers used with Miosix: Linux flashing tools.

Serial port setup

Miosix redirects stdin/stdout to a serial port by default on most boards, so to see the boot log and the output of printf() in your application you need a program to interact with the serial port. A common one is GNU screen, but there are alternatives such as minicom or tio.

sudo apt install screen # For Ubuntu/Debian
sudo pacman -S screen   # For Arch Linux


On most GNU/Linux distros serial ports and USB to serial adapters like /dev/ttyUSB0 and /dev/ttyACM0 are owned by the dialout group, so to avoid the need to use sudo every time you run screen you need to add your user to that group before you can access them.

sudo usermod -a -G dialout `id -un` # Add yourself to the dialout group

Note that you may need to reboot your computer before the change takes effect.

Downloading and configuring the Miosix kernel

To download the Miosix kernel you need git. If you do not already have it installed you can install it now

sudo apt install git # For Ubuntu/Debian
sudo pacman -S git   # For Arch Linux

This section is a stripped down guide with the bare minimum to get you started, we also have a full guide about Miosix and git workflow. Following the tutorial in this page, your project directory will not be under version control (git). The Miosix and git workflow page shows how to create a git repository for your project and add the Miosix kernel as a git submodule.

Before downloading the kernel, however, you first have to create a directory for your project (in this case, the hello world), and then clone the kernel as a subdirectory.

mkdir hello
cd hello
git clone https://github.com/fedetft/miosix-kernel.git

Initializing a Miosix project

For reasons explained in depth in the Miosix and git workflow page, you'll need to copy the Miosix configuration directory from the kernel sources to your project directory, as well as create a template project where you can start writing code. This can be automated with a Perl script called init_project_out_of_git_tree.pl:

perl miosix-kernel/tools/init_project_out_of_git_tree.pl

You should run the script from the directory where you want to initialize your empty project, such as the hello directory in this tutorial. A successful run of the script produces the following output:

Successfully created Miosix project
Target directory: hello
Kernel directory: hello/miosix-kernel/miosix

Although Perl is pre-installed in almost all GNU/Linux distros, this script depends on the File::Copy::Recursive Perl module which often is not. If you get errors running the script, install the missing module as follows and try again:

sudo apt install libfile-copy-recursive-perl # For Ubuntu/Debian

Your project directory should now look like the following picture, with the miosix-kernel directory containing the kernel sources, the config directory with the kernel configuration, the empty main.cpp and the build files for the two alternative build systems supported by Miosix: Makefile and CMake:

For this tutorial, we'll use the Makefile build system, have a look at the CMake page to learn how to use CMake instead.

Configuring the kernel

The minimum configuration required to compile the kernel is to select a board, as the kernel needs to build the appropriate board support package for it.

The Miosix kernel has several other build-time configuration options, to enable optional components (filesystem, userspace processes), select algorithms such as the scheduler and trade feature support for code size, but these won't be covered here. The kernel is configured by editing files in the config directory, the two most important ones are Makefile.inc and miosix_settings.h.

To select a board, open the first one, config/Makefile.inc. Look for the OPT_BOARD section of the file, which contains the list of boards officially supported by the kernel. In this section, all boards appear commented out (the # sign is a comment in Makefile syntax), so you need to uncomment the line corrsponding to your board. Porting the kernel to a new board is an advanced topic not covered here, so we'll assume you'll want to use an officially supported board. As an example, in this tutorial we'll use the stm32f746zg_nucleo board:

...
#OPT_BOARD := stm32f469ni_stm32f469i-disco
OPT_BOARD := stm32f746zg_nucleo
#OPT_BOARD := stm32f765ii_marco_ram_board
...

If you do not yet have a board, you can follow along and get to the compiled firmware anyway. If you're looking for suggestions on which board to get, consider that most boards currently supported by Miosix are for STM32 microcontrollers. Here's a basic guide:

  • Nucleo STM32 boards produced by ST are good for beginners, as they allow to power the board, flash it, debug it and access the serial port all through a single USB connection with your computer. The stm32f401re_nucleo and stm32f411re_nucleo are realtively low cost.
  • Discovery STM32 boards are also good, but they don't include an USB to serial adapter so you'll have to buy it separately and you'll end up having to connect two USB cables, one for power/programming/debugging and one for the serial port.
  • Third party STM32 boards such as the stm32f411ce_blackpill are cheaper and great to embed in your hardware project, but you'll have to solder the pin header yourself, and you'll need to attach a separate USB to serial adapter, and if you want in-circuit debugging you'll need an STLink adapter, so you'll end up having to run up to three separate USB cables from your computer to the board for power/programming, serial port and debugging.
  • Venturing outside of STM32, the RP2040 is a good choice. Also in this case, you'll need a separate USB to serial adapter and some soldering skills, though.

Writing your first Miosix program

Hello world

Open the main.cpp file with your IDE or text editor of choice, and replace its content with the following program:

#include <cstdio>
#include <thread>
#include <miosix.h>
#include <interfaces/bsp.h>

using namespace std;
using namespace miosix;

int main()
{
    for(;;)
    {
        iprintf("Hello world\n");
        ledOn();
        this_thread::sleep_for(500ms);
        ledOff();
        this_thread::sleep_for(500ms);
    }
}

At this point, it's good to have a quick walkthrough of this hello world program. Miosix is based on a Fluid kernel architecture: in a nutshell it's a kernel that supports writing applications both inside the kernel, and inside userspace programs. In this tutorial, we're using it as a unikernel. This means when power is applied to the board, the kernel will boot, and then start running the main() function you just wrote in kernelspace. This means you have both support for C/C++ standard libraries and unrestricted hardware access.

This main() function will print "Hello world" and blink an LED approximately every second. The printing is done with the iprintf() function. If you expected just printf() without the i, the reason is that Miosix uses the Newlib C standard library that provides both printf() and iprintf(), an optimized version that is smaller in code size but incapable of printing floating point numbers. So you can also use printf() if you wish, but this optimization is worth knowing from the start.

Sleeping to blink the LED is done with the sleep_for() function from the C++ standard library. Miosix supports other sleeping APIs, such as nanosleep() from POSIX, or Thread::sleep(), a native Miosix function. All these functions do the same thing: they tell the scheduler to stop the currently running thread, run some other thread, and resume execution after a given time interval. Miosix is a preemptive multithreading operating system, so you should get comfortable with the fact that the code you're writing lives in a thread and shares the CPU with other threads.

Many (but not all!) board support packages define the ledOn() and ledOff() functions to control one of the LED on the board. This should be true for all the boards that have at least one software-accessible LED. This is true for the stm32f746zg_nucleo board we selected, but if you selected a different board with no LEDs, then compiling will fail with an error related to ledOn() and ledOff(). You can comment out those two lines in this case, your hello world will only print to the serial port.

Compiling

To compile the kernel, open a terminal in the hello project directory and type:

make -j`nproc`

The -j`nproc` is optional, it will compile faster by using the multicore CPU in your computer. If you know how many cores you have, you can also specify the number explicitly, such as make -j8. If all goes well, the result should look like this:

Otherwise, compiler errors will appear in the shell. The number that appears under text in the make output is the size in bytes of your application plus the kernel. Don't worry about the 42KBytes code size, you're compiling with the default Miosix options, if you want you can play around with the options later to reduce the code size.

Flashing

To flash the board, you can use the make program Makefile rule to automatically download the kernel to the board. Connect the USB cable first, and then run:

make program

If the operation completed successfully, then the output should be similar to this one, and the LED should blink on the board:

If the operation did not succeed, here are some common problems:

  • You get a command not found error. You probably did not install the right flashing tool on your computer, read here Linux flashing tools.
  • The flashing tool starts, but throws an error such as Couldn't find any ST-Link devices. You probably do not have the right permissions to access the board. Try sudo make program. If that one works, you'll have to install udev rules to make the USB device of your board's programming interface accessible from your user. Unfortunately the details to installing (or writing from scratch) the correct udev rules file depend on the combination of the flashing tool and board. None of these are specific to Miosix, so look online in the documentation of your flashing tool.

Another issue in some STM32 boards is that the flashing tool leaves the board in a state where the mcirocontroller blocks either after flashing or if you press the reset button on the board. This issue is again specific to the board and flashing tool and unrelated to Miosix. If you encounter this problem after having programmed the microcontroller, it is recommended to unplug and reconnect the USB cable to powercycle the board. At that point, you should see the LED blinking.

Accessing the serial port

Starting from Miosix v3.00, all boards use by default a baud rate of 115200bit/s. If you're using a Nucleo board from ST, the USB to serial port adapter will appear on your computer as /dev/ttyACM0, so use the screen program with the following parameters:

screen /dev/ttyACM0 115200

Since the board will be already running when you connect, you can press the RESET button on the board to reboot it and see the boot logs:

Exiting the screen program is cumbersome at first, but you'll get used to it quickly. You have to type Ctrl-A, then k and y. Typing Ctrl-C won't stop the program, it will just send a Ctrl-C to the microcontroller.

If you are using a board that does not have an integrated USB to serial adapter, you'll need to figure out to which pins is the default serial connected. To do so, you'll have to look for the kernel configuration file for your board. For example, for the stm32f411ce_blackpill the file is: config/board/stm32f411ce_blackpill/board_settings.h, where you'll find that the serial port TX pin is PA9, and the RX pin is PA10. Remember to cross the TX and RX pin, the TX pin of the microcontroller goes to the RX pin of the serial adapter! For reliable communication you'll also have to connect a wire between the board GND and the serial adapter GND.

Another example would be for the RP2040. In this case the configuration file is config/board/rp2040_raspberry_pi_pico/board_settings.h and the serial TX pin is P0.0, while RX is P0.1.

The most common standalone USB to serial adapters are based on the FTDI's FT232 chip, which appears on GNU/Linux as /dev/ttyUSB0, so the command to access the serial port would be:

screen /dev/ttyUSB0 115200