As I mentioned a few posts back, I’ve been interested in following a tutorial on programming microcontrollers in Assembly. There’s been some interesting challenges to overcome, but this morning I’ve finally done it and can actually start the tutorial proper. Considering how tricky it was for an average schmuck like me to do this, I figured it’d be worth a small write-up for other people wanting to try this as well.
Firstly, I noticed that the originating pool of information on Assembly programming online now has a surprisingly small number of sources. Mostly, if you’ll look into the uses of AVRDUDE to upload programming to microcontrollers, it will be about uploading C code. The same goes for the main Arch Wiki article on compiling for AVR. That makes perfect sense, of course, because it’s easier to do more with C than with Assembly for the average person; and, from what I’ve read, the speed advantages of Assembly over C for a lot of these purposes are negligable. Apparently, AVR microchips are already optimized quite a bit for C, and the slight advantage that you may get by programming in Assembly pales in comparison to just getting a faster microchip to begin with. So, given that programming these in Assembly mostly seems to be a niche hobby (the programming equivalent of choosing off-the-grid survival rather than camping, perhaps?), there seem to be less than a dozen people online that are a solid source for programming in Assembly, and less when you want answers directly for Linux.
The issue there is that one of the main methods of doing Assembly coding and uploading seems to be Microchip Studio (formerly Atmel Studio, and often referred to as such online, still). The big issue being that this is online available for Windows. So, for Linux, you have to get a little creative. The actual programming, of course, isn’t that tough: use whatever editor or IDE you prefer; my favorite is still Vim, largely because my needs are small and this seems quite fine. The first problem is compiling your assembly, however.
As wonderful as the Arch Wiki usually is, the only relevant post I could find about Assembly is their listing of programming languages. All that tells me is that as is the compiler provided by the packages binutils, fasm, nasm, and yasm. Those, though, are general Assembly compilers. What it doesn’t mention is that there’s also a compiler available specified for the Atmel AVR microchips: avra. Furthermore, the person who wrote the tutorial I linked to at the start also coded his own assembler: gavrasm. Once you’ve written your Assembly file, compiling is ridiculously easy. For example, using gavrasm, you just type:
gavrasm -seb example_file.asm
Or for avra, it’s:
avra example_file.asm -o example_file.hex
Both will give you a hex file that you can upload to your microcontroller. A crucial difference in my case with the ATtiny13 is that gavrasm had its own definitions file for AVR microcontrollers, so didn’t need me to include those. Avra, however, doesn’t, and needed me to supply it. Fortunately, somebody has kindly provided a whole list of them over on GitHub, so I just downloaded the relevant one for me, which turned out to be “tn13def.inc”.
After compiling the .hex file, I needed to figure out how to upload it to the microcontroller via ISP. The tutorial linked above explained a good setup for an ISP header set, and the right connections to the microchip in the first lesson, but it used Microchip Studio for the uploading. So, I had to figure out the Linux alternative. AVRDUDE is that solution, but it took a little more fiddling to get working. Firstly, I needed to figure out what exactly my usb programmer was called (as there are multiple types). Using the command “lsusb” gave me the following output:
Bus 002 Device 013: ID 1781:0c9f Multiple Vendors USBtiny
So, I guessed that “usbtiny” would be the correct name. Using the information provided by Mitchel Davis in episode 5 of his YouTube playlist on Bare-Metal MCU, I ended up with the following command for AVRDUDE:
avrdude -v -p attiny13 -c usbtiny -U flash:w:2_led_on.hex:i
That calls AVRDUDE in verbose (-v) mode for more feedback, telling it we’re programming an attiny13 (-p attiny13) using a usbtiny programmer (-c usbtiny), and that we’re uploading and writing to flash memory, the hex file (-U flash:w:2_led_on.hex) and doing that immediately (:i). That looked great, except it didn’t work. Luckily, the verbose command let me know that it was a permissions issue for the USB programmer. So, sudo-ing the command made it work. Ideally, I’d like to find the correct permissions setting for my user so I wouldn’t have to use sudo for this, but I haven’t been able to find the right one yet. Neither adding uucp nor tty has helped, nor has installing usbasp-udev and avrisp-udev.
So, there’s more to learn still. Possibilities to improve the workflow, for instance, lie in using makefiles to set up some standard settings. And, of course, trying to fix those permissions errors. Either way, with the process described here, I managed to write, compile, and upload the relevant program from the tutorial linked above. So, more learning lies ahead!