Intéressé par des cours d'informatique en ligne ?
Visitez mon nouveau site
https://www.yesik.it !
Suite à une erreur de commande, je me suis retrouvé avec un lot de micro-contrôleurs ATmega328-PU alors que je pensais m'être procuré des ATmega328P-PU. Quelle différence entre les deux? Cela tient dans l'explication que ce P signifie picopower. Autrement dit, le modèle P consomme moins que le modèle non-P. Hormis cela, il s'agit des mêmes micro-contrôleurs.
Pour être tout à fait honnête, je ne me suis rendu compte de ma méprise qu'au moment où j'ai voulu accéder à mon micro-contrôleur à l'aide d'avrdude (ici pour lire les fusibles):
sh$ avrdude -p m328p -c usbasp -U hfuse:r:/dev/stdout:b [...] avrdude: Device signature = 0x1e9514 avrdude: Expected signature for ATMEGA328P is 1E 95 0F Double check chip, or use -F to override this check.
signature | |||
---|---|---|---|
ATmega328P | 1E | 95 | 0F |
ATmega328 | 1E | 95 | 14 |
Oups! Effectivement, il ne s'agissait pas d'un ATmega328P – et de façon compréhensible, la signature du micro-contrôleur est différente de celle attendue. Après avoir pris conscience de mon erreur, me voici essayant avec l'option -m m328 tout court:
sh$ avrdude -p m328 -c usbasp -U hfuse:r:/dev/stdout:b avrdude: AVR Part "m328" not found.
Hein? C'est pas possible! Et bien si: la version d'avrdude que j'utilisais (5.10 incluse dans les paquets de Debian Squeeze) ne supportait pas l'ATmega328…
Si vous êtes dans le même cas, plusieurs solutions sont possibles. Par ordre croissant de préférence:
- Utiliser avrdude avec l'option -F pour ignorer l'inadéquation entre la signature attendue et celle du micro-contrôleur.
- Modifier /etc/avrdude.conf pour dupliquer la section de l'ATmega328P – mais avec la bonne signature.
- Faire la même opération, mais en ajoutant la description du micro-contrôleur à votre fichier ${HOME}/.avrduderc plutôt qu'en modifiant le fichier de configuration global.
- Télécharger et installer une version récente d'avrdude (postérieure à 2011-12-29 – voir le changelog-2011).
Car elles me sembles plus propres, ce ne sont que ces deux dernières options que je vais expliquer ici. Libre à vous de choisir celle que vous préférez.

Utilisateurs d'Arduino…
…si vous utilisez une version de l'IDE Arduino pour programmer un ATmega328 – et que la version d'avrdude incluse ne supporte pas l'ATmega328, je vous conseille fortement la première technique décrite ci-dessous, à savoir la modification de votre fichier ${HOME}/.avrduderc.
Cela vous évitera de devoir modifier les fichiers inclus dans la distribution Arduino, et assurera la pérénité de ces modifications même en cas de mise à jour de l'IDE.

Emplacement des fichiers
Je donne ici l'emplacement des fichiers de configuration pour ma machine linux Debian Squeeze. Sur une autre distribution ou un autre système d'exploitation, ces fichiers pourront être ailleurs. Pour vérifier leur emplacement, utilisez l'option -v d'avrdude:
sh$ avrdude -v avrdude: Version 5.10, compiled on Jun 27 2010 at 00:38:29 Copyright (c) 2000-2005 Brian Dean, http://www.bdmicro.com/ Copyright (c) 2007-2009 Joerg Wunsch System wide configuration file is "/etc/avrdude.conf" User configuration file is "/home/sylvain/.avrduderc"
Modifier le fichier de configuration utilisateur
Pour connaitre les caractéristiques des micro-contrôleurs auxquels il accède, avrdude utilise une description que l'on trouve dans le fichier /etc/avrdude.conf. Il s'agit d'un fichier texte que vous pouvez parcourir ou modifier avec n'importe quel éditeur de texte. Ou manipuler à l'aide des outils Unix standards. Par exemple, on peut extraire la configuration pour l'ATmega328P ainsi:
sh$ cat /etc/avrdude.conf | sed -n "/# ATmega328P/,/^;/p" # ATmega328P #------------------------------------------------------------ part id = "m328p"; desc = "ATMEGA328P"; has_debugwire = yes; flash_instr = 0xB6, 0x01, 0x11; eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, 0x99, 0xF9, 0xBB, 0xAF; stk500_devcode = 0x86; # avr910_devcode = 0x; signature = 0x1e 0x95 0x0F; pagel = 0xd7; bs2 = 0xc2; chip_erase_delay = 9000; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; cmdexedelay = 25; synchloops = 32; bytedelay = 0; pollindex = 3; pollvalue = 0x53; predelay = 1; postdelay = 1; pollmethod = 1; pp_controlstack = 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; togglevtg = 1; poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; programfusepolltimeout = 5; programlockpulsewidth = 0; programlockpolltimeout = 5; memory "eeprom" paged = no; page_size = 4; size = 1024; min_write_delay = 3600; max_write_delay = 3600; readback_p1 = 0xff; readback_p2 = 0xff; read = " 1 0 1 0 0 0 0 0", " 0 0 0 x x x a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", " 0 0 0 x x x a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", " 0 0 x x x x a9 a8", " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; delay = 5; blocksize = 4; readsize = 256; ; memory "flash" paged = yes; size = 32768; page_size = 128; num_pages = 256; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 x x x x x x", " x x x x x x x x"; mode = 0x41; delay = 6; blocksize = 128; readsize = 256; ; memory "lfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", "x x x x x x x x i i i i i i i i"; ; memory "hfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", "x x x x x x x x i i i i i i i i"; ; memory "efuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x x x x x x o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", "x x x x x x x x x x x x x i i i"; ; memory "lock" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x x x o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; ; memory "calibration" size = 1; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", "x x x x x x a1 a0 o o o o o o o o"; ; ;
J'ai transcris ci-dessus l'intégralité de la section relative à l'ATmega328P pour référence. Mais ne vous laissez pas impressionner: les seules modifications à apporter pour supporter l'ATmega328 tout court consisteront à changer les éléments que j'ai surlignés. À savoir le commentaire, l'id et la description du circuit, ainsi bien sûr que sa signature. C'est un travail rêvé pour sed:
sh$ cat /etc/avrdude.conf | \ sed -n "/# ATmega328P/,/^;/p" | \ sed 's/328[pP]/328/;/signature/s/0x0F/0x14/' \ >> ${HOME}/.avrduderc
Vous remarquerez au passage la redirection qui me permet d'ajouter directement la définition à mon fichier .avrduderc. Et voilà:
sh$ avrdude -p m328 -c usbasp -U hfuse:r:/dev/stdout:b avrdude: Device signature = 0x1e9514 avrdude: reading hfuse memory: avrdude: writing output file "/dev/stdout" 0b11011001
Installer une version récente d'avrdude

Installation
Sous Debian vous aurez besoin des paquets libusb-dev, libusb-1.0-0-dev, libelf-dev et libftdi-dev pour ce qui suit. Si ces logiciels ne sont pas déjà sur votre machine utilisez le gestionnaire de paquets de votre distribution pour procéder à l'installation.
sh# apt-get install libusb-dev sh# apt-get install libusb-1.0-0-dev sh# apt-get install libelf-dev sh# apt-get install libftdi-dev
Une approche différente du problème est d'installer une version plus récente davrdude. J'ai donc visité le site officiel d'avrdude (http://www.nongnu.org/avrdude/) … pour me rendre compte que malheureusement à ce jour il n'y a pas de release intégrant le support pour l'ATmega328. Par conséquent vous devrez utiliser svn pour télécharger une version de développement. Vous pouvez explorer avec votre navigateur web le dépôt subversion correspondant pour trouver votre bonheur. En ce qui me concerne, au moment où j'écris, seul le trunk intègre le support de mon micro-contrôleur. C'est donc la toute dernière version de développement que j'ai téléchargée et installée:
# télécharger / compiler / installer sh$ mkdir avrdude sh$ cd avrdude sh$ svn co http://svn.sv.gnu.org/svn/avrdude/trunk/avrdude/ sh$ cd avrdude sh$ ./bootstrap sh$ ./configure --prefix=/opt/avrdude [...] Configuration summary: ---------------------- DO HAVE libelf DO HAVE libusb DO HAVE libusb_1_0 DO HAVE libftdi DON'T HAVE libhid DO HAVE pthread sh$ make sh$ sudo make install
Une fois compilé et installé, il suffit d'ajouter le chemin vers cette nouvelle version d'avrdude en tête de votre PATH pour pouvoir l'utiliser:
# tester / utiliser sh$ export PATH="/opt/avrdude/bin:${PATH}" sh$ avrdude -v avrdude: Version 5.11svn, compiled on Dec 27 2012 at 23:29:25 Copyright (c) 2000-2005 Brian Dean, http://www.bdmicro.com/ Copyright (c) 2007-2009 Joerg Wunsch [...] sh$ avrdude -p m328 -c usbasp -U hfuse:r:/dev/stdout:b avrdude: Device signature = 0x1e9514 avrdude: reading hfuse memory: avrdude: writing output file "/dev/stdout" 0b11011001
Références
- (en) AVRDUDE Support For Non-PicoPower ATMega328 MCU – sur avrfreaks.net
