Writing assembly programs requires an understanding of the AVR memory types and their uses. This page will give a generic overview, but you will need to consult the datasheet for your microcontroller to get specific values.
There are three types of memory in the AVR architecture:
- Program Memory
- Data Memory
Program Memory, also referred to as flash, is where your code is stored. Depending on settings in the fuse bits, the entire flash memory can be used as application storage or a portion can be code-blocked off for a bootloader program.
Flash memory is non-volatile meaning its data does not go away when the microcontroller loses power. Flash cannot be accessed as quickly as Data Memory and individual bytes cannot be modified at a time so it is not a good place to store variables which constantly change. However, in addition to storing your application code, it is a good place to put constants like lookup tables or strings.
Data Memory is composed of four parts:
- Register File
- I/O Registers
- Extended I/O Registers
- Internal SRAM
Unlike flash, Data Memory is not composed of a single memory type. Rather, it is a contiguous mapping of addresses across multiple memory types.
The breakdown of data memory is shown below. The location and size of the general purpose working registers, I/O registers, and extended I/O registers are the same across all chips (even if some of the extended I/O features are not implemented). However, the size of internal SRAM varies between different models.
The register file begins at the start of Data Memory and contains 32 general purpose working registers that are directly connected to the arithmetic logic unit (ALU). The general purpose working registers are used as operands for most instructions. The general purpose working registers are extremely important and useful. Any data manipulation in the AVR requires using one of these registers.
Registers R26:R27, R28:R29, and R30:R31 are given the names X, Y, and Z respectively. They are often referred to as the X, Y and Z pointers as they can be used to store or retrieve data from memory by placing an address in them.
The I/O Registers are locations in Data Memory which control certain microcontroller functions. All of the data direction registers and ports (e.g. DDRB and PORTB) are located in the I/O Register portion of Data Memory. Because they are needed so often, there are special instructions which allow quick access and modification of the I/O Registers.
The I/O Registers are non-volatile. They will initialize to default values that may or may not need to be changed by your program.
Extended I/O Registers
Most microcontrollers have more functions and peripherals than can be supported by the 64 bytes allocated to the I/O Registers. Thus there is an Extended I/O Register section. The Extended I/O section only differs from the regular I/O section in that does not support all of the same instructions to set, clear, or copy its contents. However, its function and purpose are exactly the same.
Like the regular I/O Registers, the Extended I/O Registers are non-volatile.
Static Random Access Memory - referred to as SRAM - is the last part of Data Memory. SRAM is volatile so its contents cannot be guaranteed at startup. However, unlike flash, single bytes can be written to SRAM and its access time is quicker, making it much better for storing temporary values.
SRAM is a very convenient runtime memory type. It is great when you have more variables than can fit in the general purpose working registers and need a place to put them while they are not being used.
EEPROM is another non-volatile storage location in the AVR architecture. Unlike flash, individual bytes may be written to it, although its access time is much slower. EEPROM is best served for configuration settings, i.e. things that need to be available at startup but may be changed at runtime and used the next time the chip starts up.
You should now have a little better understanding of the memory types in the AVR architecture and what they are used for.
The most important takeaways are that code is stored in Program Memory, General Purpose and I/O Registers are in Data Memory, and SRAM is volatile memory with quick access that can be used to store values at runtime.
Now we will look at a simple program to compute 16-bit arithmetic.