CMSIS vs HAL vs Bibliothèque de périphériques standard

29

Je passe donc de PIC à ARM et j'ai acheté une carte de découverte STM32F4. Jusqu'à présent, je comprends que pour le programmer, vous pouvez accéder à tous les registres directement en mémoire (de manière évidente) et il existe également 3 bibliothèques principales que vous pouvez utiliser pour vous faciliter la vie. Maintenant, ma question est, lequel de ces 3 (CMSIS, HAL, Std Peripherals Lib) est le niveau le plus BAS? c'est à dire. celui avec le moins de frais généraux. Mon objectif est d'apprendre le fonctionnement interne du contrôleur et de ne pas me faciliter la vie (seulement un peu), donc je voudrais savoir lequel est le plus proche du noyau sans recourir à l'assemblage.

John
la source
10
[Le côté STM32 de] CMSIS est essentiellement juste des définitions de registre et aucun code, donc CMSIS == accès direct au registre. AFAIK ST n'a pas de téléchargement séparé uniquement pour le CMSIS, mais lorsque vous téléchargez StdPeriph Lib ou STM32Cube, vous pouvez choisir de n'utiliser que la partie CMSIS. Les définitions de registre STM32 se trouvent dans Libraries/CMSIS/Device/ST/STM32F4xx/Include/stm32f4xx.hou Drivers/CMSIS/Device/ST/STM32F4xx/Include/stm32f4xx.hrespectivement.
Aleksi Torhamo

Réponses:

27

Certainement le CMSIS. Ce n'est pas exactement une bibliothèque, elle contient surtout des définitions pour les différents registres.

C'est exactement ce dont on a besoin pour accéder facilement aux registres du microcontrôleur, afin d'implémenter sa propre HAL. Il n'a pas de surcharge, car vous accédez simplement aux registres.

Gardez à l'esprit que CMSIS, contrairement aux deux autres, est défini par ARM et non par ST. Cela signifie que les différentes bibliothèques CMSIS pour les différents microcontrôleurs sont assez similaires, ce qui facilite grandement la portabilité.

De plus, CMSIS est le plus simple, il est donc (IMO) le plus polyvalent et le plus fiable, avec peut-être moins (ou pas) de bogues. Certaines bibliothèques hal pour les différents mcu que j'ai utilisés sont assez tristement célèbres pour leurs bugs.

D'un autre côté, le CMSIS a besoin de beaucoup plus de travail de votre part. C'est cependant mon choix personnel, car je préfère investir mon temps à créer des bibliothèques de qualité, qui répondent à mes besoins, et à comprendre comment fonctionne la puce, que passer du temps à apprendre juste une nouvelle bibliothèque.

Fotis Panagiotopoulos
la source
Je ne suis pas sûr que ST supporte toujours la bibliothèque CMSIS
Scott Seidman
1
Eh bien ... quelque chose comme ça. Il n'y a pas de lien direct, ils le découragent (semble vouloir lier autant que possible les utilisateurs à leur code, les décourageant de partir pour une autre marque), mais il est utilisé dans leurs autres bibliothèques. Vous pouvez l'extraire de là. Il est assez simple, n'inclut pas beaucoup de code et semble mature. On dirait qu'il est sûr pour une utilisation en production, qu'ils le commercialisent comme supporté ou non.
Fotis Panagiotopoulos
Ouais, c'est une déception qu'ils ont cessé de développer dans cette direction. La conformité au CMSIS a été l'une des choses qui m'ont attiré vers ST en premier lieu. Je l'utilise toujours, mais j'ai l'impression que le jour viendra où ce ne sera pas pratique.
Scott Seidman
3
@ScottSeidman, je pense que vous avez confondu CMSIS avec StdPeriph. Le CMSIS est bien pris en charge et le sera indéfiniment. Son StdPeriph qui est fondamentalement obsolète maintenant, mais CMSIS est aussi vivant qu'il y a 10 ans.
ScienceSamovar
14

Pour savoir comment cela fonctionne, vous ne devez utiliser aucune des options ci-dessus. Obtenez un compilateur cross arm et la documentation de st, done. Commencez à coder. ces puces sont généralement très faciles à programmer. la documentation vous indique quels bits dans quels registres font quoi.

Toutes / toutes ces bibliothèques sont destinées à supprimer cette compréhension / ce fardeau / ce travail et à vous faire ressentir comme un simple appel à une expérience de programmation d'application comme une API. C'est ce que beaucoup de gens veulent. Vous pouvez utiliser toute la source de ces bibliothèques pour vous aider à comprendre, mais à mesure que vous vous améliorez, vous trouvez des trous et des problèmes dans les bibliothèques, parfois du code très effrayant. code jeté ensemble, écrit de manière générique et grossièrement porté d'une puce à une autre, peut-être en prenant en charge les fonctionnalités que votre puce ne possède pas, etc. Et elles ont toutes une surcharge excessive. 10 à 100 fois trop de code pour la tâche, bien sûr, une grande partie de celui-ci peut être optimisé, mais pourquoi l'y avoir en premier lieu?

Que vous utilisiez votre propre bibliothèque ou que vous utilisiez l'une de ces bibliothèques, vous devez toujours rechercher la source des bibliothèques que vous utilisez pour voir si vous êtes à l'aise avec ce qu'elles font, si cela a du sens, correspond à la documentation de la puce, etc. va mal, vous devrez probablement fouiller dans leurs affaires autant que les vôtres pour savoir pourquoi.

Notez que les documents sur les puces ne sont pas parfaits non plus, cela fait partie du plaisir.

Je ne comprends pas pourquoi l'assemblage revient dans une discussion sur la programmation bare metal. Vous pouvez vous en tirer avec très peu de montage. Pour ces puces cortex-m, vous n'avez techniquement besoin que de tant d'asm pour démarrer:

.globl _start
_start:
.word 0x20001000
.word main

Vous ne pouvez pas vous fier aux données ni aux bss et vous ne pouvez pas revenir de main avec ce minimum d'asm. Mais c'est tout ce dont vous avez besoin pour le moindre métal nu. Maintenant, si vous voulez faire des interruptions, vous avez besoin de plus d'entrées dans la table vectorielle. plus de lignes .word. Je recommande plus d'asm, mais peut-être 10 ou 20 lignes de plus.

c'est généralement tout l'asm que j'utilise.

.cpu cortex-m0
.thumb
.thumb_func
.global _start
_start:
stacktop: .word 0x20001000
.word reset
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.word hang
.thumb_func
reset:
    bl notmain
    b hang
.thumb_func
hang:   b .
.align
.thumb_func
.globl PUT16
PUT16:
    strh r1,[r0]
    bx lr
.thumb_func
.globl PUT32
PUT32:
    str r1,[r0]
    bx lr
.thumb_func
.globl GET32
GET32:
    ldr r0,[r0]
    bx lr
.thumb_func
.globl GET16
GET16:
    ldrh r0,[r0]
    bx lr
.thumb_func
.globl dummy
dummy:
    bx lr
.end

Oui, il dit cortex-m0 mais c'est un bootstrap réel pour mon code m4. Je préfère que ce soit le pouce et non le pouce2. Et je réutilise simplement ce code d'un cortex-m à un autre, en changeant l'adresse du pointeur de pile selon les besoins, donc cela fonctionne pour m0, m3 et m4. Je n'ai pas encore de M7 et je ne l'ai pas beaucoup recherché.

L'activation du processeur peut nécessiter quelques lignes d'asm supplémentaires car des instructions spécifiques sont nécessaires. Mais le fait est de ne pas confondre programmation de bas niveau et asm. C a ce dont vous avez besoin pour configurer la puce, ainsi que pour écrire une application. Les bibliothèques dont vous parlez sont écrites en C pas asm, donc évidemment elles n'ont pas besoin d'utiliser asm non plus.

Si vous voulez apprendre le fonctionnement interne, écrivez votre propre code. N'utilisez pas ces bibliothèques autrement que comme référence. Parfois, il est plus facile de le pirater que d'essayer de lire leur code. (pas seulement ST mais tous les vendeurs. Un des vendeurs avait une ligne de code donc alarmant je l'utilise comme une question d'interview, non je ne vais pas la poster ici).

ST sans aucun doute, mais d'autres fournisseurs également, pour économiser de l'énergie, ont des horloges activées pour des sections de la puce, donc avant d'entrer et d'essayer de faire clignoter une led, vous devez trouver le bit d'activation pour ce bloc gpio et voir s'il sort de réinitialisation activée, sinon l'activer, parler à cette logique gpio sans horloge permettant de simplement bloquer le processeur pendant qu'il attend une réponse de la logique qui ne répondra jamais. Ils ne vous parlent pas toujours de ces permis. Une fois activés, ils vous guident parfois à travers l'init pour un périphérique particulier. Les documents ST sont plutôt bons. Venant de la micropuce qui obtient une assez mauvaise note pour la documentation, vous ne devriez pas avoir de problème.

old_timer
la source
2
Le PO n'a pas posé de questions sur la procédure de démarrage ou quoi que ce soit du genre. Juste quelle bibliothèque est la plus adaptée à son utilisation.
Fotis Panagiotopoulos
asm a été mentionné et donc les commentaires sur asm
old_timer
2
Le CMSIS ne contient pas non plus de code, à part pour un strict minimum. Il n'inclut pas le code de démarrage, les scripts de l'éditeur de liens ou quelque chose comme ça. Il ne contient que des définitions pour les registres. Pourquoi écrire du code cryptique, ou réinventer la roue, au lieu d'utiliser un joli nom pour accéder directement aux registres?
Fotis Panagiotopoulos
2
@John Vous pouvez facilement démarrer un microcontrôleur ARM avec absolument aucun ASM, tout aussi efficacement. Si vous êtes intéressé, posez une nouvelle question et commentez un lien ici pour vous montrer quelques exemples.
Fotis Panagiotopoulos
1
@ user3634713 Je suis en fait très intéressé. Merci electronics.stackexchange.com/questions/224618/…
John
2

J'ai utilisé les deux, juste l'accès au registre de métal nu et la bibliothèque périphérique std. Je trouve plus facile de gérer les registres. De plus, si vous utilisez un débogueur, vous pouvez afficher les registres et confirmer qu'ils contiennent ce que vous avez programmé. Je pense que vous en apprenez davantage sur le fonctionnement de la puce de cette manière également.

Joe McCarron
la source
2

Venant du monde 8 bits, j'étais toujours habitué à programmer des périphériques via des registres. Les fiches techniques des microcontrôleurs (c'est-à-dire les manuels de référence STM32) décrivent les périphériques exclusivement en notation de registre. Puisque le programmeur doit lire cette même documentation pour connaître les fonctions et fonctionnalités périphériques avant toute tentative d'utilisation, il me semble naturel de commencer à programmer les registres. Avec une mise en page et des commentaires prudents, je trouve que le code peut être agréablement lu et modifié même après y être revenu des mois plus tard.

Adam
la source
2

Jusqu'à présent, j'ai utilisé des définitions CMSIS et j'ai apprécié d'utiliser directement les registres. Pendant ce temps, j'ai utilisé les bibliothèques HAL dans quelques projets. Cela a eu une influence considérable sur le temps d'exécution du code, je l'ai donc quitté. Bien que CMSIS serve mon intérêt, ces jours-ci, je vais être un fan de libopencm3 . C'est comme les LLbibliothèques fournies par ST. Cependant, il couvre plus de micro-contrôleurs même dans les familles ST:

Le projet libopencm3 (précédemment connu sous le nom de libopenstm32) vise à créer une bibliothèque de micrologiciels libres / libres / open-source pour divers microcontrôleurs ARM Cortex-M3, y compris ST STM32, Toshiba TX03, Atmel SAM3U, NXP LPC1000 et autres.

veuillez noter que:

Malgré son nom, libopencm3 prend également en charge d'autres microcontrôleurs ARM Cortex "liés" tels que Cortex-M0 ou Cortex-M4 / Cortex-M4F, par exemple.

vous pouvez trouver la liste des micro-contrôleurs pris en charge ici .

Pana
la source
Le problème réel est que ST a une mauvaise idée de ce qu'un HAL est censé faire. Une bonne HAL aura une fonction comme adc_get_result()qui enveloppe dans le pilote de périphérique complet ADC y compris les aspects en temps réel, des interruptions , etc. Le ST semble être plutôt write_to_scary_registerqui est fondamentalement juste un emballage pléthorique autour de l'accès au registre. En toute honnêteté, ST n'est pas le seul fournisseur à fournir un tel excès de ballonnement, Atmel ASF et d'autres sont tout aussi mauvais.
Lundin