Écrire son système d'exploitation - Partie 1 : préparer le terrain

Posté par . Édité par Benoît Sibaud et tankey. Modéré par tankey. Licence CC by-sa
46
19
fév.
2015
Technologie

L'auteur du journal à l'origine de la dépêche vous propose de vous raconter un peu les différentes étapes de son projet du moment : écrire un petit système d'exploitation pour un microcontrôleur STM32. Cet premier épisode présente le matériel possédé, la documentation collectée, les outils rassemblés et le dépôt de code utilisé.

De quoi ça s'agit ?

J'ai récupéré une carte de développement construite autour d'un STM32F103RBT6. C'est un microcontrôleur basé sur un cœur ARM Cortex-M3. Il est un peu daté mais bon, on fait avec ce qu'on a (surtout quand c'est gratuit :). Pour situer un peu le bousin, c'est un micro 32 bits qui embarque 20Ko de SRAM et 128Ko de Flash, plus un certain nombre de périphériques habituels (UART, SPI, I²C…).

La carte de développement est une MCBSTM32 de chez Keil. Le but du jeu c'est donc d'écrire un petit noyau capable de faire tourner une application sur cette puce.

Il ne s'agit pas de faire un truc de dingue (nothing big and professional like GNU), mais vraiment d'apprendre en faisant le plus simple et clair possible.

Récupérer de la doc

Bon allez c'est parti, la première des choses à faire c'est de récupérer toute la documentation susceptible de nous servir :

  • le schéma de la carte
  • le programming manual du cœur Cortex-M3
  • la datasheet de la "famille" de la puce (STM32F10xxx)
  • la datasheet du chip en lui-même
  • le Flash programming manual. Celui-là nous servira plus tard, une fois le développement un peu avancé, pour écrire du code capable de reprogrammer la Flash du micro (ceci afin de pouvoir mettre à jour le programme sans devoir sortir le JTAG).

Ensuite ? Ben y'a plus qu'à lire tout ça… Ça devrait vous occuper un certain temps. On lit jusqu'à ce qu'on ait une idée claire du boulot qui nous attend pour écrire un code qui démarre sur cette carte.

Préparer la boîte à outils

Une fois qu'on a bien digéré la doc, reste une étape avant de se lancer comme un dingue dans le code : préparer ses outils de développement.
Les ingrédients pour bien réussir cette recette sont :

  • une chaîne d'outils de compilation croisée pour notre cible (arm-none-eabi). Chez moi ça revient à sudo apt-get install gcc-arm-none-eabi binutils-arm-none-eabi.
  • un cross debugger (sudo apt-get install gdb-arm-none-eabi)
  • une sonde JTAG qui nous servira à programmer et déboguer le programme sur la puce. Sans vouloir faire de pub, j'ai opté pour un Olimex ARM-USB-TINY-H. Ça fonctionne bien sous Linux et c'est un poil moins cher qu'une sonde Lauterbach à 3000€ ;)
  • enfin, un OpenOCD, un programme sympa qui fait le traducteur entre votre sonde JTAG et GDB (sudo apt-get install openocd)

Ah et il nous faudra aussi un peu de make, du git et un éditeur de texte, mais je suppose que vous avez déjà tout ça…

Voilà, c'est tout pour cette fois, on se retrouve bientôt pour parler de la configuration des outils et commencer à écrire du code !

PS: il est où le code ?

Pour ceux que ça intéresse, le code est libre (licence BSD) et hébergé sur Github (pour faire plaisir aux trolls). Évidemment c'est un travail en cours, qui progresse suivant mes envies et mon temps libre.

  • # Bibliographie

    Posté par . Évalué à 6.

    Avant le «1: choix des outils», j'aurais bien vu un «0: bibliographie».

    Dans cette partie, je ne peux que citer les superbes articles publiés par David Decotigny & Thomas Petazzoni dans Linux Magazine sur un mini OS: SOS. C'est didactique, c'est clair, c'est limpide.
    Bon, c'est pour x86, mais ça mérite d'être lu, ainsi que pas mal des ressources qu'ils référencent.

  • # Bon plan, mais ...

    Posté par . Évalué à 3.

    Pas mal, je souhaite réussite et courage.

    Mais …

    C'est pas pour décourager, au contraire ! J'avoue que moi-même, j'aurais beaucoup à apprendre en appliquant cette démarche.

    Hors donc : je commence à connaitre les cartes de dév. ST. Au taff, j'ai du STM32F0 et du STM32F4 (discovery). C'est pas très cher non plus, et le gros avantage, c'est que ça peut se programmer sans JTAG en plus. Il suffit de dégoter stlink, et c'est tout bon.

    Je me suis fait des environnements de dév sous Windows/Cygwin et Linux, avec QtCreator pour l'édition du code.

    Pour les librairies, avant, il y avait les StLibraries (un truc du genre, je me rappelle plus le nom exact). C'était un peu galère, fallait recopier pas mal de tartines de code d'init, toujours plus ou moins identique. Mais ça, c'était avant …

    Le bon plan maintenant, c'est CubeMX qui permet de générer du code basé sur de nouvelles HAL (Hardware Abstraction Layers). C'est du clickdrome plutôt sympa : on choisi son proco ou la dev board, on configure et on génère. Il ne se mets pas trop en travers du chemin; je veux dire qu'on garde la main sur le code à 99%. Et les HAL sont bien foutues.

    Et pour revenir à l'OS, il inclut, d'un clic toujours, FreeRTOS. Alors là, par contre, je connais moins, je commence juste à pratiquer un peu ce truc. A priori, y'a du bon avec le multithreading (facile de se créer plusieurs tâches parallèles), mais je me méfie de la gestion du temps (quelques surprise à confirmer …). A suivre.

    Quoi qu'il en soit, rien à voir avec le monde CSR (les puces Bluetooth de 70% du marché) ! CSR est fermé, google n'est pas ton ami, et même quand tu as payé 4000 boules le kit de dév, le forum privé de CSR n'est pas non plus ton ami ! Le support est, euh, bof.
    Et après ça, pas étonnant que tous les produits basés sur ces puces BT se ressemblent : tout le monde part du seul et unique exemple fourni et l'adapte à ses besoins, le plus vite possible parce que ça doit arriver au magasin hier …
    Je crois qu'il ne viendrait à l'idée de personne de refaire une appli from scratch. OK, le BT n'est pas simple, y'a des tiroirs partout, mais quand même.

    Euh, bon, stop, j'arrête de me défouler, quittons nous sur un "aimez les puces ST, c'est presque gratuit" !

    (Non, je ne bosse ni pour l'un, ni pour l'autre, j'ai juste gouté au deux, et l'un des deux m'est resté en travers de la gorge …)

    • [^] # Re: Bon plan, mais ...

      Posté par (page perso) . Évalué à 3.

      Je te rassure, dans les puces Texas Instrument et Broadcom tu as du lourd aussi. :)
      Entre la doc, la qualité du code et des commentaires, il y en a pour tous les goûts !

  • # Bonne idée, comme tuto !

    Posté par . Évalué à 3.

    Super idée !

    Je vais suivre ça au fur et à mesure et tenter une adaptation sur PIC32 qui possède une architecture MIPS.
    Cela m'obligera à m'y mettre.
    D'ailleurs, à ce propos, je cherche quelques bonnes âmes compétentes sur le sujet, histoire de me sentir mois seul.

    A+

  • # bon courage.

    Posté par (page perso) . Évalué à 2.

    bonjour,

    Tout d'abord merci de partager ton "aventure". J'espère que tu iras jusqu'au bout. Néanmoins, je me demande si le projet a démarré sur un coup de tête ou si tu as déjà abordé des sous-éléments de la structure d'un sou-noyau.

    J'ai regardé la description sommaire de la carte Keil, effectivement ce n'est pas très costaud mais je travaille sur de l'ARM7TDMI avec une licence Keil, et j'ai commencé avec la carte d'éval MCB2300 pour ça. Ce n'est pas mon choix, j'aurai préféré prendre du Cortex avec quelques instructions DSP. Malgré tout nous faisons de la régulation à 100 us en virgule flottante avec ça !
    J'utilise tous les outils KEIL v4 (IDE, toolchain, debugger, uNoyau RTX, stack réseau) donc je suis un peu "conditionné", ta démarche utilise une alternative qui m'intéresse :). Je pense qu'en terme de puissance ce cortex est comparable à l'ARM7 mais malgré tout j'ai des limitations :
    - génération thumb, l'ARM7 c'est thumb1 et très pénalisant en terme de perf
    - pas de couche de configuration comme STMCube (jamais utilisé) => on a utilisé le wizard Keil pour une configuration "user friendly"
    - pas de lib "driver" (CMSIS,etc…) => tout fait nous même, et là, bien obligé de lire à fond le user manual du uC :)
    - niveau debug et profiling c'est très limité (deux point d'arrêts).

    J'ai rapidement survolé la structure du code :
    - code startup absent ?
    - makefile : génération "thumb", apparement du "Thumb-2" donc tu ne devrais pas être pénalisé en terme de performance, mais ça serait intéressant de pouvoir constater la différence avec des instructions ARM.
    - peut-être pourrais tu également comparer le comportement avec une génération par RVDS (Keil/Arm).

    Pour l'expérience mais aussi en terme de pédagogie je pense qu'il est intéressant d'aborder l'évaluation de performances d'un uC (temps de latence, consommation CPU, empreinte mémoire flash et RAM). C'est toujours les questions que l'on se pose lorsque l'on intègre un uNoyau, et même tout autre type de bibliothèque.
    ```

    • [^] # Re: bon courage.

      Posté par . Évalué à 2.

      En ce qui concerne le code startup (je pense que tu parles de la mise en place des stacks), il n'y en a tout simplement pas besoin dans un Cortex-M. En fait ARM a fait un effort pour que tout (ou presque) puisse être fait en C.
      Tu verras donc que le vecteur de reset (cpu/vectors.c) contient l'adresse de base de la stack à l'adresse 0 et l'adresse du point d'entrée en C à l'offset 0x4. Avec ça, le processeur charge le stack pointer et saute au point d'entrée directement au reset. Donc pas besoin de glue en assembleur pour le démarrage contrairement aux ARM7/ARM9 !

  • # ChibiOS/Nil

    Posté par . Évalué à 1. Dernière modification le 20/02/15 à 14:36.

    ChibiOS dans sa version 3, introduit NilRTOS, un OS avec des spécifications minimales. Le code (nil.h, nil.c, nilcore_v7m.h, nilcore_v7m.c) est plutôt simple et donc assez pédagogique.

  • # En version plus légère

    Posté par . Évalué à 2.

    Je connais encore mal le domaine, mais il me semble que des OS pour STM32 (ou autre micro-contrôleur), on en trouve à la pelle¹… Le tiens a-t-il quelque-chose de spécial en dehors de ce qui existe déjà ? Ou c'est juste pour s'amuser ?

    En passant, je mets un référence vers un « OS » un peu différent, basé également sur un STM32F103, qui ne gère que l'ordonnancement de threads et c'est tout : Chopstx https://gitorious.org/chopstx/
    Il a été écrit pour le projet GnuK http://www.fsij.org/gnuk/, qui utilisait auparavant ChibiOS/RT http://www.chibios.org/, un truc un peu plus lourd. Je le trouve intéressant car il n'essaye pas de réinventer une couche d'abstraction.

    1 : http://en.wikipedia.org/wiki/List_of_real-time_operating_systems

    • [^] # Re: En version plus légère

      Posté par . Évalué à 3.

      Je connais encore mal le domaine, mais il me semble que des OS pour STM32 (ou autre micro-contrôleur), on en trouve à la pelle¹… Le tiens a-t-il quelque-chose de spécial en dehors de ce qui existe déjà ? Ou c'est juste pour s'amuser ?

      En fait, je n'ai pas suffisamment insisté là-dessus dans l'intro, mais je remettrai un petit mot sur le sujet dans le prochain article, promis. Cet OS n'a rien de plus que les autres, c'est vraiment un projet pour le fun. Ça réinvente la roue et c'est fait exprès ! Mon but c'est de me confronter à toutes les étapes du développement pour apprendre. Il s'agit de se faire une expérience, pas de faire quelque chose de stable et qu'on pourrait mettre en production. D'ailleurs il n'y a pas de plan de tests ou d'intégration continue, parce que j'ai pas envie de me prendre la tête avec ça.
      C'est pour ça aussi que j'ai choisi de ne pas réutiliser de code existant.

      Donc ceux qui recherchent un OS pour mettre en production, passez votre chemin ! Il y a comme tu le dis des tas de RTOS pour microcontrôleur qui sont tout à fait éprouvés. Le but de ces articles c'est plutôt de faire de la pédagogie, pour ceux qui veulent découvrir avec moi ce qu'est un OS et comment ça marche sous le capot. Sachant qu'il s'agit d'avoir des fonctionnalités de base (gestion mémoire, gestion de threads, séparation user/kernel, et quelques drivers), pour que ça soit simple à comprendre. Je ne cherche pas à faire un concurrent à Linux :)

  • # Bibliographie ?

    Posté par . Évalué à 2.

    Excellente idée cette série de journaux. J'aime !

    Sinon dans ta première partie de récupération des docs, tu pourrais peut-être mettre une bibliographie ? Quelques bouquins/sites web incontournables ?

    Je suppose que tu vas pas te lancer là-dedans sans un minimum de connaissances théoriques ?

    Merci !

    • [^] # Re: Bibliographie ?

      Posté par . Évalué à 2.

      C'est vrai que ça serait bien, mais malheureusement je n'ai pas fait de recherche de documentation formelle en vue de ce projet, ce qui fait que je n'ai pas vraiment de bibliographie à proposer…

      Je ne pars évidemment pas sans connaissances théoriques, mais ce sont des connaissances acquises sur le tas sur plusieurs années (je travaille dans l'embarqué donc je trempe déjà dans le sujet). Il y a un mélange d'expérience professionnelle, et d'autodidacte à coup de recherches sur le Web, mais je n'ai pas vraiment noté tout ça quelque part. Mais effectivement j'ai déjà une bonne idée de ce qui m'attend, je ne pars pas la fleur au fusil !

    • [^] # Re: Bibliographie ?

      Posté par . Évalué à 3.

      Sinon dans ta première partie de récupération des docs, tu pourrais peut-être mettre une bibliographie ? Quelques bouquins/sites web incontournables ?

      Systèmes d'exploitation d'Andrew Tanenbaum

      "Quand certains râlent contre systemd, d'autres s'attaquent aux vrais problèmes." (merci Sinma !)

  • # Carte de dev alternative basé sur le STM32F10xxx à bas coût, le Leaf Maple Mini

    Posté par . Évalué à 1.

    Pour ceux d'entre-vous qui voudraient également tester le code ou développer sur un STM32F103RCBT6,
    il y a ce module, pas cher, pour commencer le développement:

    Leaf Maple Mini
    Wiki: http://leaflabs.com/docs/hardware/maple-mini.html
    Prix: environs 4€ (chez Ali…)

    Avec connectique Mini-USB, c'est assez rapide pour la programmation (upload) et très peu onéreux.

    Ce qui est bien c'est qu'il peut se faire programmer comme un Arduino (avec un GUI, presque le même).
    On peut tester directement le programme en RAM (sans écrire sur la mémoire flash), pratique pour les petits tests.

    Mais attention beaucoup des GPIO ne sont pas compatible 5v. C'est presque du 3,3v partout.

Suivre le flux des commentaires

Note : les commentaires appartiennent à ceux qui les ont postés. Nous n'en sommes pas responsables.