Programming the AVR microcontroller with GCC, libc 1.0.4

Programming the AVR microcontroller with GCC, libc 1.0.4

[Illustration]

Abstract:

The AVR 8-Bit RISC microcontroller from Atmel is a very common microcontroller. This microcontroller is one chip with EEPROM, Ram, Analog to Digital converter, a lot of digital input and output lines, timers, UART for RS 232 communication and many other things.

The best is however that a complete programming environment is available under Linux: You can program this microcontroller in C using GCC.

I wrote already in March 2002 an article about the same subject. A lot of things have changed in the avr-libc development and the AT90S4433 microcontroller which I used in 2002 is no longer manufactured by Atmel. This is therefore an update of the March 2002 article. I will use libc-1.0.4 and the ATmega8 microcontroller.

This article shall be only an introduction and in a later series of articles we will again build interesting hardware but this time based on the ATmega8.

_________________ _________________ _________________

Introduction

Many people where interested in microcontroller programming after the article which I wrote in 2002. However this first step to get the development environment up and running is the hardest. If something does not work then you have absolutely no clue where the fault is. Programmer cable wrong?? Circuit faulty? Installation incorrect? Parallelport disabled in bios? Kernel modules for ppdev compiled wrong? There can be a lot of reasons why things don’t work.

To make the entrance to the exciting world of microcontrollers easier shop.tuxgraphics.org offers now a bootable CD with a manual and the programmer hardware. All you need to do then is boot from this CD and everything is up and running. No software installation is required and nothing is modified on your local computer.

Even I use such a CD now for a while because the hardware I build often survives several generations of kernels and software installations on my PC. If I want later on to update some microcontroller software then I do not have to worry if the development environment on my Linux PC is still working. I just boot from the CD and it is up and running.

Independent of this CD I will explain the installation of the GCC avr development environment in the following paragraphs. If you have the CD from tuxgraphics then continue with chapter “A small test project”.

Software installation: What you need

To use the GNU C development environment you need the following software:

binutils-2.15.tar.bz2 Available from:
ftp://ftp.gnu.org/gnu/binutils/
or any mirror. E.g:
ftp://gatekeeper.dec.com/pub/GNU/binutils/
gcc-core-3.4.2.tar.bz2 Available from: ftp://ftp.gnu.org/gnu/gcc/
or any mirror. E.g:
ftp://gatekeeper.dec.com/pub/GNU/gcc/
avr-libc-1.0.4.tar.bz2 The AVR C-library is available from: http://savannah.nongnu.org/projects/avr-libc/
uisp-20040311.tar.bz2 The AVR programmer software is available from: http://savannah.nongnu.org/projects/uisp

We will install all the programs to /usr/local/avr. This is to keep the program separate from your normal Linux C compiler. Create this directory with the command:

    mkdir /usr/local/avr

You can add it already now to your PATH:
    mkdir /usr/local/avr/bin
    export PATH=/usr/local/avr/bin:${PATH}

Software installation: GNU binutils

The binutils package provides all the low-level utilities needed for building object files. It includes an AVR assembler (avr-as), linker (avr-ld), library handling tools (avr-ranlib, avr-ar), programs to generate object files loadable to the microcontroller’s EEPROM (avr-objcopy), disassembler (avr-objdump) and utilities such as avr-strip and avr-size.

Run the following commands to build and install the binutils :

tar jxvf binutils-2.15.tar.bz2
cd binutils-2.15/
mkdir obj-avr
cd obj-avr
../configure --target=avr --prefix=/usr/local/avr --disable-nls
make

# as root:
make install

Add the line /usr/local/avr/lib to the file /etc/ld.so.conf and run the command /sbin/ldconfig to rebuild the linker cache.

Software installation: AVR gcc

avr-gcc will be our C compiler.

Run the following command to build and install it:

tar jxvf gcc-core-3.4.2.tar.bz2
cd gcc-3.4.2

mkdir obj-avr
cd obj-avr
../configure --target=avr --prefix=/usr/local/avr --disable-nls --enable-language=c

make

# as root:
make install

Software installation: The AVR C-library

The C-library is quite stable now compared to the one I presented in March 2002.
Run the following command to build and install it:

tar jxvf avr-libc-1.0.4.tar.bz2
cd avr-libc-1.0.4
PREFIX=/usr/local/avr
export PREFIX
sh -x ./doconf
./domake

cd build
#as root:
make install

Software installation: The Programmer

The programmer software loads the specially prepared object code into the EEPROM of our microcontroller.

The uisp programmer for Linux is a very good programmer. It can be used directly from within a Makefile. You just add a “make load” rule and you can compile and load the software in one go.

uisp is installed as follows:

tar jxvf uisp-20040311.tar.bz2.tar
cd uisp-20040311
./configure --prefix=/usr/local/avr
make

# as root:
make install

A small test project

We will start with a small test circuit which you can expand later on.

This circuit can also be used as a simple test environment for more complex hardware. You can easily test load software and attach sensors or measurement equipment.

Our test program as presented here will just cause a LED to blink.

Needed Hardware

[test circuit]
You need the parts listed in the table below. Although it is a very common microcontroller it might not be available in every local radio shop but bigger distributors for electronic components like ( http://www.conrad.de (germany), http://www.selectronic.fr (france), digikey.com (US, CA), etc… have it in store).
The best place to get the microcontroller and the other parts is however: shop.tuxgraphics.org ;-).

1 x ATmega8 DIP version, Atmel 8 bit Avr risc processor.
1 x 28 pin 7.5mm IC socket
The 28 pin socket is a bit more difficult to get. Usually the 28 sockets are 14mm wide but we need a 7.5mm socket.
1 x 10K resistor (color code: brown,black,orange)
1 x 1K resistor (color code: brown,black,red)
1 x 10uF electrolytic capacitor
Some wires
1 x LED
matrix board
The following is needed for the programmer (not needed if you get the “Linux AVR programming kit” from tuxgraphics):
1 x DB25 connector to plug into the parallel port.
Any kind of 5 pin connector/socket for the programmer. I recommend to use precision strip connectors (similar to IC sockets) and break 5 pins off.
1 x 220 Ohm resistor (color code: red,red,brown)
2 x 470 Ohm resistor (color code: yellow,purple,brown)

In addition to the above parts you need a 5V electronically stabilized DC power supply or you can use a 4.5V battery as power supply.

You have probably noticed that we do not need a crystal. This is because the ATmega8 has now a build-in oscilator. This oscilator can be used when accurate timing is not an issue. However if you want to build precise measurement equipment or you want to use the UART/RS232 interface then you will need a crystal. Which type of oscilator is used can be defined via fuse bits which you can modify with the programmer. By default (factory setting) the internal 1Mhz oscilator is active.

Building the programmer hardware

The AVR microcontrollers allows for in circuit programming (ISP). [Linux AVR programmer]
That is: you do not need to remove the microcontroller form the board to program it. You will see that you can get different programmer hardware from 50-150 Euro. However with Linux running it is also possible to build a very simple programmer that does the job. You need a free parallel port on your computer and the following cable.

Note that this is an improved programmer compared to the one presented in the March 2002 article. We build the protection resistors into the programmer. This will then save some space and parts on the circuit board. The wiring for the programmer cable has to be as follows:

pin on pcb pin on AVR protection resistor Pin on parallel port
5 Reset (1) Init (16)
4 MOSI (17) 470 Ohm D0 (2)
3 MISO (18) 220 Ohm Busy (11)
2 SCK (19) 470 Ohm Strobe (1)
1 GND GND (18)

The cable should not be longer than 70cm.

The protection resistors can be build into the connector as show on the picture on the right.

Writing software

The Atmeag 8 can be programmed in plain C with the help of gcc. To know some AVR assembler can be useful but it is not needed.

The AVR libc comes with an avr-libc-user-manual-1.0.4.pdf (1139921 bytes) which documents all functions available in C. From Atmel’s website, (www.atmel.com, go to: avr products -> 8 bit risc-> Datasheets), you can download the complete data sheet. It describes all the registers and how to use the CPU.

One thing to keep in mind when using a microcontroller is that it has only a few bytes of Ram. That means you must not declare large data structures or strings. Your program should not use deeply nested function calls or recursion.

Much better than all theory is a real example. We will write a program that causes our LED to blink in 0.5 seconds intervals. Not very useful but very good to get started.

The avr-libc has changed a lot. Previously you did set a bit on a port with sbi and you cleared it with cbi. Now those functions are deprecated. First I present the “good old way”:

    /* defines for future compatibility */
    #ifndef cbi
    #define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
    #endif
    #ifndef sbi
    #define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
    #endif

    void main(void)
    {
          /* INITIALIZE */
          /* enable PC5 as output */
          sbi(DDRC,PC5);

          /* BLINK, BLINK ... */
          while (1) {
                /* led on, pin=0 */
                cbi(PORTC,PC5);
                delay_ms(500);
                /* set output to 5V, LED off */
                sbi(PORTC,PC5);
                delay_ms(500);
          }
    }

The following example does exactly the same but uses the new syntax:

    void main(void)
    {
          /* INITIALIZE */
          /* enable PC5 as output */
          DDRC|= _BV(PC5);

          /* BLINK, BLINK ... */

          /* PC5 is 5 (see file include/avr/iom8.h) and _BV(PC5) is 00100000 */
          while (1) {
                /* led on, pin=0 */
                PORTC&= ~_BV(PC5);
                delay_ms(500);
                /* set output to 5V, LED off */
                PORTC|= _BV(PC5);
                delay_ms(500);
          }
    }

The above code snipet shows how simple it is to write a program. You see only the main program, the delay_ms function is included in the full listing (avrm8ledtest.c). To use pin PC5 as output you need to set the PC5 bit in the data direction register for port C (DDRC). After that you can set PC5 to 0V with the function cbi(PORTC,PC5) (clear bit PC5) or to 5V with sbi(PORTC,PC5) (set bit PC5). The value of “PC5” is defined in iom8.h which is included via io.h. You don’t have to worry about it. If you have already written programs for multi user / multi tasking systems such as Linux you know that one must never program a non blocking endless loop. This would be a waste of CPU time and slow the system very much down. In the case of the AVR this is different. We don’t have several tasks and there is no other program running. There is not even an operating system. It is therefore quite normal to busy loop forever.

Compiling and loading

Before you start make sure that you have /usr/local/avr/bin in the PATH. If needed edit your .bash_profile or .tcshrc and add:

export PATH=/usr/local/avr/bin:${PATH} (for bash)
setenv PATH /usr/local/atmel/bin:${PATH} (for tcsh)

We use the parallel port and uisp to program the AVR. Uisp uses the ppdev interface of the kernel. Therefore you need to have the following kernel modules loaded:

    # /sbin/lsmod
    parport_pc
    ppdev
    parport

Check with the command /sbin/lsmod that they are loaded otherwise load them (as root) with:

    modprobe parport
    modprobe parport_pc
    modprobe ppdev

It is a good idea to execute these commands automatically during startup. You can add them to a rc script (e.g for Redhat /etc/rc.d/rc.local).
To use the ppdev interface as normal user root needs to give you write access by once running the command

chmod 666 /dev/parport0

Make as well sure that no printer daemon is running on the parallel port. If you have one running then stop it before you connect the programmer cable. Now everything is ready to compile and program our microcontroller.

The package for our test program (avrm8ledtest-0.1.tar.gz) includes a make file. All you need to do is type:

make
make load

This will compile and load the software. I will not go into the details of all the commands. You can see them in the Makefile and they are always the same. I can my self not remember all of them. I just know that I need to use “make load”. If you want to write a different program then just replace all occurrences of avrm8ledtest in the Makefile with the name of your program.

Some interesting binutils

More interesting than the actual compilation process are some of the binutils.
Those utilities have however not really changed since March 2002. Take a look at the “Some interesting binutils” chapter in article231, March 2002.

Ideas and suggestions

The ATmega8 is compatible to the AT90S4433 for most uses. You need to program the fuse bits to use the external oscilator and the previously presented hardware might work with possibly minor changes. Unfortunatley I have not had time yet to re-test all circuits for the ATmega8. If you want to be on the save side then use the AT90S4433 for the old articles. If you don’t mind to troubleshoot and solve problems then try the ATmega8 with the old articles/circuits.

Here is a list of those previous hardware articles:

Note: the programmer presented here includes already the protection resistors which were build into the circuit board in the older hardware articles. To use the new programmer with the old boards you will just need to replace the protection resistors on the board by wires.

Atmel provides an application note “AVR081: Replacing AT90S4433 by ATmega8” which lists all the incompatibilities: at90s4433_to_atmega8.pdf (101343 bytes)

References

Developing for the Atmel AVR Microcontroller on Linux

January 5th, 2005 by Patrick Deegan in

You’ll enjoy the programming ease and built-in peripherals of the new generation of microcontrollers. Best of all, with these tools you can develop for the popular AVR series using a Linux host.

digg_url = ‘http://www.linuxjournal.com/article/7289’;
digg_title = “Developing for the Atmel AVR Microcontroller on Linux”;
digg_bodytext = “”;

digg_skin = ‘standard’;

Whether you are creating a small Internet appliance, some hardware instrumentation, data loggers or an army of autonomous robots to do your bidding, in numerous situations you need the flexibility of a programmable computer. In many cases, a general-purpose system, such as the workhorse sitting under your desk, doesn’t meet size, cost or power-consumption constraints and is simply overkill. What you need is a microcontroller.

This article provides step-by-step instructions for setting up a complete development system for the Atmel AVR series of microcontrollers, using free software and Linux. The detailed instructions provided here will allow you to transform your Linux system into a complete AVR development environment. This article walks you through all the steps of building, debugging and installing a simple program.

What Is a Microcontroller?

When all the electronic components required to make a central processing unit (CPU)—instruction decoder, arithmetic/logic unit, registers and so on—are integrated into a single chip, you have a microprocessor. When, in turn, you bundle this CPU with supporting components, memory and I/O peripherals, you’ve got a microcomputer. Extending the integration and miniaturization even further, you can combine all the elements of a microcomputer onto a single integrated circuit—behold the microcontroller.

The semiconductor industry evolves rapidly, making it difficult to provide an accurate and complete definition of the term microcontroller. Consider this: some microcontroller chips have capacities and clock speeds that surpass the 74KB of program memory and 4KB of RAM available to the 30kg Apollo Lunar Module computer. You can expect today’s screamer PCs to be running tomorrow’s embedded applications, with the definition of microcontroller shifting accordingly.

Microcontrollers all have a microprocessor core, memory and I/O interfaces, and many have additional peripherals onboard. The specific configuration of a particular chip influences its physical packaging, number of pins and cost. If you are accustomed to working with microcomputers, you may feel that microcontrollers are tight spots. They have a handful of kilobytes of program ROM and in the area of 256 bytes of RAM. Don’t fret though; a lot can be done in this space, as the MIT Instrumentation Lab demonstrated when developing the Apollo Lunar Module software that controls its moon landing, return from the surface and rendezvous in orbit.

AVR Microcontrollers

The AVRs are 8-bit RISC platforms with a Harvard architecture (program and data memory are separate). Figure 1 details the ATtiny26 AVR chip internal organization. Like each member of a family, it has its own particular combination of I/O and peripherals, but it shares a basic architecture and instruction set with all the other AVRs. The ATtiny26 has 2KB of program Flash memory, 128 bytes of onboard SRAM and EEPROM, two 8-bit counters and pulse-width modulators, 11 interrupts, 16 I/O pins spread over two 8-bit ports, an 11-channel 10-bit analog-to-digital converter and more—all on a single tiny 20-pin DIP.

A number of factors make the AVR microcontrollers a good choice, especially for beginners. AVRs are:

  • Easy to code for: AVRs were designed from the ground up to allow easy and efficient programming in high-level languages, with a particular focus on C.
  • Easy to program: the combination of onboard reprogrammable Flash program memory and the in-system programming interface keeps the process of transferring software to the microcontroller simple and cheap.
  • Powerful and inexpensive: AVRs pack a lot of power (1 MIPS/MHz, clocks up to 16MHz) and space (up to 128K of Flash program memory and 4K of EEPROM and SRAM) at low prices. Most AVRs even include additional peripherals, such as UARTs and analog-to-digital converters.
  • Hobbyist-friendly: most of the chips in the AVR family come in easy-to-use 8-, 20-, 28- or 40-pin dual in-line packages (DIPs) and can be ordered in unit quantities from a number of distributors.

Figure 1. ATtiny26 Block Diagram

CPU

The processor core, composed of the components in the upper-left portion of Figure 1, includes elements to read the program memory and to decode and execute the instructions within that memory. The CPU also can fetch and store data to and from the EEPROM, SRAM and the 32 registers. The registers act as extremely efficient storage for 8-bit values (1 byte), and the ALU (arithmetic/logic unit) can operate directly on each of the 32 registers. This AVR features a RAM-based stack. In a few other AVRs, which don’t have any SRAM, the stack is hardware-based, limiting the stack depth to three.

Most instructions take only a single clock cycle to execute, and there is no internal clock division on AVRs. The CPU fetches and decodes the next instruction as it is executing the current instruction. These combined facts mean that AVRs can reach performances of nearly 1 MIPS (million instructions per second) per MHz. With clock rates of up to 16MHz, you can choose the right balance of speed, power consumption and electromagnetic noise for your particular application.

Memory

Program space is a contiguous block of Flash memory, 16-bits wide that can be erased/rewritten 10,000 times. You can design your circuit to allow firmware upgrades in-circuit, using in-system programming.

All AVRs have some EEPROM, and most have SRAM; both are 8-bits wide. The EEPROM is designed to withstand at least 100,000 erase/write cycles. EEPROM is useful because it can be written from within your embedded program to retain data, even without a power supply, or during programming, such as for production-line calibration.

I/O and Peripherals

All AVRs, from the tiny 8-pin DIPs to the 44-pin Megas, have at least one data port. Data ports allow for input or output of logic-level data. The AVR ports are bidirectional, allowing you to set them for input or output on a pin-by-pin basis.

Many of the AVRs include additional hardware peripherals, such as UARTs for serial communication and calibrated RC oscillators used as internal system clocks. The external pins often serve two or more purposes, and how they are used depends on how you’ve configured the microcontroller. For instance, Figure 1 shows that certain I/O lines from both ports can be used with the multiplexed A/D converter.

Development Workstation Setup

The set of tools described here isn’t the only one available, but it allows you to do basically anything, and the tools function well together. The toolkit is comprised of Binutils, GCC, AVR Libc and our Makefile template to write and build programs for the AVR microcontrollers; GDB and simulavr to debug your software; and avrdude as well as a hardware programmer to transfer your software to the microcontrollers. See the on-line Resources for download URLs for all software.

Fortunately, the recent versions of all these tools include support for the AVR platform, so installation is straightforward. We assume you’ve chosen to install everything under /usr/local/AVR.

Binutils

Download a fresh copy of the current binutils source by following the link in the Resources. Untar the source, move into the binutils-X.XX directory and run:

$ ./configure --prefix=/usr/local/AVR --target=avr
$ make
# make install

The /usr/local/AVR/bin directory now contains AVR versions of ld, as, ar and the other binutils executables. Add the /usr/local/AVR/bin directory to your PATH now. You can apply the modification system-wide by adding:

PATH="$PATH:/usr/local/AVR/bin"

to the /etc/profile file. Make sure the directory is in your PATH and that the change has taken effect before proceeding.

GCC

After retrieving a recent release of the Gnu Compiler Collection from a mirror, run the following commands from within the unpacked top-level source directory:

$ ./configure --prefix=/usr/local/AVR \
        --target=avr --enable-languages="c,c++" \
        --disable-nls
$ make
# make install

This builds C and C++ compilers for AVR targets and installs avr-gcc and avr-g++ in /usr/local/AVR/bin.

AVR Libc

The AVR Libc package provides a subset of the standard C library for AVR microcontrollers, including math, I/O and string processing utilities. It also takes care of basic AVR startup procedures, such as initializing the interrupt vector table, stack pointer and so forth. To install, get the latest release of the library and run the following from the top-level source directory:

$ unset CC
$ PREFIX=/usr/local/AVR ./doconf
$ ./domake
# ./domake install
Makefile Template

The Psychogenic team has created a standard Makefile template that simplifies AVR project management. You can customize it easily for all your assembly, C and C++ AVR projects. It provides everything for a host of make targets, from compilation and upload to the microcontroller to debugging aids, such as source code intermixed with disassembly, and helpful gdbinit files. A detailed discussion of the template is available, and the Makefile template is available as Listing 1 on the Linux Journal FTP site (see Resources). Store the template with the other AVR tools, moving it to /usr/local/AVR/Makefile.tpl.

GDB and SimulAVR

Using avr-gdb and simulavr in tandem, you can run your software on a choice of AVR microcontrollers through the simulator, while using GDB to step through and observe the executing code. Acquire the simulavr source from the project site and perform the installation:

$ ./configure --prefix=/usr/local/AVR \
  --with-avr-includes=/usr/local/AVR/avr/include
$ make # make install

Install GDB, built for AVR targets, by compiling the source as follows:

$ ./configure --target=avr \
     --prefix=/usr/local/AVR
$ make
# make install
AVRDUDE

When you finally have a program ready for testing on actual hardware, you need some way to upload the data and write it to the microcontroller’s Flash program memory. AVRDUDE and a compatible hardware programmer are the last components of the development kit. Grab a copy of the AVRDUDE source and install it with:

$ ./configure --prefix=/usr/local/AVR
$ make
# make install

You now have installed every software component required for a complete AVR development environment. All you need is the physical means to transfer programs to microcontrollers.

AVRDUDE supports a number of different hardware programmer configurations. The simplest systems are described on the AVRDUDE site and are comprised of little more than a parallel port connector, a ceramic oscillator and a DIP socket. These are powered directly off the computer’s port and may not work for everyone.

Figure 2. Home-Brew PPI Programmer PCB

A step up in complexity, independently powered, buffered in-system programmers can be built easily (see Resources). Two programmers requiring only a few parts are discussed on the Psychogenic Web page, which describes the schematics, provides artwork and has complete instructions on creating your own printed circuit boards (as depicted in Figure 2) for the programmers.

Figure 3. Atmel STK500 Development Kit

A number of commercial solutions also are available. If you’re interested in easily programming a wide selection of the AVR family, go with Atmel’s STK500 kit. More than a simple programmer, the STK500 is a starter kit that allows you to program the microcontrollers and easily prototype new designs. It includes a number of LEDs and switches, an oscillator, RS-232 interface and other niceties that easily can be interfaced with your target chip.

A Complete AVR Project

Our focus here is on the development system rather than on programming for the AVR platform. The AVR Libc documentation is a good place to start for information on programming AVRs in Assembly, C and C++.

The Hello World program of the microcontroller universe is the classic flashing LEDs. A slightly different take on this theme, which Knight Rider fans should appreciate, is available on the Linux Journal FTP site, where you can download C (Listing 2) or C++ (Listing 3) versions of an example program that cycles each of eight light-emitting diodes (LEDs) back and forth.

Building the Program

Create a project directory—for instance, ~/helloavr/—and retrieve the program, saving Listing 2 as ~/helloavr/kr.c and Listing 3 as ~/helloavr/kitt.cpp. Also, copy the Makefile template, /usr/local/AVR/Makefile.tpl, to ~/helloavr/Makefile.

Using this Makefile is easy and makes compilation a snap. Open the Makefile in your favourite editor and modify the configuration section, near the top of the file, so that the MCU, PROJECTNAME and PRJSRC variables are set as shown in Listing 4. The MCU variable determines the AVR family member for which we are compiling the program, and the PRJSRC variable lists all the Assembly, C and C++ source files used in the project.

Once you’ve configured the Makefile, compiling and linking the program is as simple as typing make.

You can perform the compilation and linking steps manually instead, by issuing:

  $ avr-gcc -I.  -g -mmcu=at90s8515 -Os       \
             -fpack-struct -fshort-enums               \
             -funsigned-bitfields -funsigned-char \
             -Wall -Wstrict-prototypes -c kr.c

  $ avr-gcc -o helloavr.out kr.o

The most notable difference is the addition of the required -mmcu command-line argument, used to specify the target microcontroller. Either method compiles kr.c and creates the helloavr.out ELF-format program. This file cannot be executed on your development station but is used later during the debugging stage.

You also can build the C++ version of the program by doing a make clean, changing the Makefile PRJSRC variable to kitt.cpp and then issuing another make.

Debugging the Program

A Makefile target that is interesting, whether for sanity checking, optimization, low-level debugging or simply to get to know the AVR internals, is disasm. Running: $ make disasm prints some information concerning the program, such as its text/data/bss size, to the console and creates helloavr.s. This file contains a disassembled version of the executable, intermixed with the original C source code. A peek inside reveals AVR Libc and avr-gcc’s work behind the scenes, initializing the interrupt vector table and data, followed by the Assembly and C versions of the program.

Now we use GDB as a source-level debugger with simulavr running as a remote target. To do so, launch simulavr in the background and create a suitable gdbinit file:

$ simulavr --gdbserver --device at90s8515  &
$ make gdbinit

Running make in this manner creates gdbinit-helloavr, a file containing instructions for setting up GDB correctly, such that it connects to a simulavr, loads the compiled program, inserts a breakpoint and begins execution. Launch avr-gdb using the command:

$ avr-gdb -x gdbinit-helloavr

and you are presented with the GDB prompt; program execution is halted before the first instruction in main(). Set a breakpoint on line 71, using b 71, and enter C (continue) a few times. Every time you step over the instruction on line 71:

71       PORTB = ~currentValue;

~currentValue is output through PORTB. You should see a message to that effect, for example, writing 0xff to 0x0038. When you are done, issue a quit and kill the simulavr process, which is running in the background.

Installing the Program

If you’ve built or purchased the programmer hardware, you can install and test the software on a real AT90S8515 chip. Configure the avrdude section in the Makefile by setting the AVRDUDE_PROGRAMMERID and AVRDUDE_PORT variables, as explained in the comments above. Use:

AVRDUDE_PROGRAMMERID=stk500
AVRDUDE_PORT=/dev/ttyS0

for an STK500 programmer connected to the first serial port. Ensure that the programmer is connected to the appropriate port, insert the microcontroller in the programmer, apply power and type make writeflash. This generates the hex file used by AVRDUDE and writes its contents to the chip’s Flash program memory.

Figure 4. HelloAVR Program Test Circuit

For those using the STK500 development kit, simply connect PORTB to the eight onboard LEDs using the ten-wire cable (as illustrated in Figure 3), and watch das blinkenlights. You can set up your own test hardware by constructing the schematic shown in Figure 4, which connects LEDs with suitable limiting resistors such that each pin of PORTB can activate one by going low and sinking current.

Where to from Here?

You’ve seen the flashing LEDs? Congratulate yourself; you are ready to begin creating your own AVR designs and software. See Resources for loads of AVR-related information and projects. There’s almost no limit to what you can do.

Atmel shares a number of interesting project ideas through its AVR application notes, where it details implementation of stepper motor controllers, IR remote control receivers and transmitters and even an embedded Web server. One amazing project, ContikiOS (see Resources), distributes an open-source Internet-enabled, multitasking, graphical operating system that has been ported to the AVR and uses a version of the VNC server instead of a regular screen.

Enjoy experimenting with these versatile microcontrollers, be sure to share your discoveries and good luck building that robot horde!

Resources for this article: www.linuxjournal.com/article/7920.

Patrick Deegan was converted to IT and free software after being in contact with Linux while a student in the joint Math and Physics program at McGill U. Torn between working in physics, electronics and software development, Pat was bound to cofound Psychogenic, where he now gets to spend many days (and nights) playing with all three.