Pages

First of all this is a great tutorial. Thanks.
I am a little bit confused though. I am having a project in which I intend to use a menu to interface the uC.
Should I use progmem or eemem. Which one is better for LCD, menu
and a Keyboard?

AVRs by in large don't have much eemem, so unless you needs are small, there is probably not enough room in eemem. If you do fit in eemem, then it is up to you which you use, but I think that most would choose progmem. Reading from eemem takes longer than reading from progmem.

Thanks so much for this tutorial. It explains stuff that other authors miss.
May I suggest that you emphasize that PROGMEM assignments MUST be global. It took me quite a while to figure out the warning (which I think should be an error as it breaks all use of the constant)
Thanks
Kirk

So I followed this tutorial to put some strings into Program memory and then read them with pgm_read_byte(). While the string is reads correctly (when optimization is not at -Os) I can't explain what I see in the debugger!

The .lss file shows that the string is put in program memory right after the interrupt vector table, at address 0x7c. When I single step with the disassembler I can see that the LPM instruction via the Z pointer reads from address 0x7c.

HOWEVER when I bring up a memory window or scroll the disassembler to 0x7c there is no string. Instead I find the string at address 0x38, apparently right in the middle of the vector table, and I find that address 0x7c is inhabited by code. When I add a break point at 0x00007b the debugger stops there, so I'm clearly executing from there.
javascript:emoticon(':twisted:')
What is going on? Why does it appear that my string in memory is not where the .lss file says it should be and why am I executing code where a strings should be. What magic is this ?

You are mixing up byte and word addresses. The simulator/disassembler presents you everything related to the flash with word addresses, the GNU tools use byte addresses. So 0x7c in the .lss file is 0x3e in the simulator/disassembler.

What about trying to store data in the bootloader section using PROGMEM? Is there a way to change PROGMEM's start location. I can recall strings and variables just fine from FLASH at 0x00000, but not from the bootloader section.

What about trying to store data in the bootloader section using PROGMEM? Is there a way to change PROGMEM's start location. I can recall strings and variables just fine from FLASH at 0x00000, but not from the bootloader section.

If you write a bootloader then you move the whole Flash stuff by relocating the .text section. This also moves the PROGMEM section. So what is you actual problem?

Or don't you write a bootloader but only want to place some data in the bootloader section (whyever)? Then simply don't use the PROGMEM section. Use your own section and place it there.

I have a Atxmega128a1 and the boot section starts at 0x020000.
I know that it doesn't work past 64k but my boot section is only 8k, so if I move the .text section to the boot section address I shouldn't have any problems right?

I have a Atxmega128a1 and the boot section starts at 0x020000.
I know that it doesn't work past 64k but my boot section is only 8k, so if I move the .text section to the boot section address I shouldn't have any problems right?

So you don't think that 0x020000 is beyond 0x010000 (64k)?

BTW: I am not familiar with the XMegas. Has an Atxmega128 more than 128k Flash? If not, how then can the boot section start at 0x020000?
EDIT: Forget this. Meanwhile I took a look into the data sheet. ;-)

About the eemem question above (in case your still following the thread) - That portion of memory can tolerate 100000 writes as opposed to 10000 in flash, so ultimately flash seems to me best for constant strings or at strings that rarely change.

Hello, first of all, thanks for the tutorial!
I didn't read the whole thread but did do some quick search in it.
I was wondering if there was an easy way to directly load a resource file into a program memory destination.

for instance, I have the file res.txt with 800 bytes in it. I would like to copy its contents into program memory at address 0x1000, is there any special instructions in avr studio / avr-gcc to do so?

I have a quick question, if anyone here can help. I have a program where I have a large configuration struct that houses several different data types. Right now, I have two copies of this struct in EEPROM, which correspond to different configurations. I would like store defaults for each configuration in program memory, so a function like pgm_read_block (analogous to the eeprom_read_block I already use) would be very handy. I saw it mentioned earlier in the thread, but can't find it in pgmspace.h included with WinAVR-20100110. Is it an extension that I could find elsewhere, or will I have to write it myself?

Looks pretty good to me - obviously the array of pointers itself has to be in RAM not PROGMEM if you plan to change language at run time. But you could keep the initialisers for each language themselves in PROGMEM and do something like a memcpy_P() to copy an entire set of language pointers into place in one go.

I am using avr-gcc 4.3.5 to compile a cpp sourcecode (inherited from my Arduino environment). The example in the HOWTO leaves me with mismatching typeconversion errors or section type conflicts when I use "const".

Questions:
1. Can we change the flash contents by changing the content of the variable using PROGMEM?
2. If question 1 is Yes, then correct me if I'm wrong, the flash sector has to be erased, then store data to it. So how does it work?

Please help!
I have a Atmega M1284P. Data changeable by user and it's used to store in EEPROM, but now decide to store in flash. Here is my Flash memory organize:
App Region: 0 - 0xFFFF
Data Region: 0x10000 to 0x1DFFF
Boot Region: 0x1E000 to 0x1FFFF
I provide 2 commands to user READ_Data and WRITE_Data with 3 parameters: U16_t ui16Address, U16_t ui16Len, U8_t * pui8Buffer
The READ_Data function has no problem, I can use pgm_read_byte_far( 0x10000 + ui16Addr) where ui16Addr is from 0 to 0xDFFF (used to be the EEPROM address).
For the WRITE_Data function, should I assign Data Region Address of the Flash to be 0x1000 to a PROMEM variable? How can I do it?
When initialize, the data is used to read to RAM data structure variables. To save RAM memory, so now I benefit to use Flash instead.

Is there my any chance some sort of "test suite" for the pgmspace.h functions and definitions? I'm working on a compatibility shim for non-AVR processors and prospect of testing everything is daunting...

Thank you Clawson,
SPM doesn't support or disabled in Application Section, it works only in Bootloader Section. So there is NO WAY to change data in the flash when an app is running, user has to jump to BL mode to write data, then jump back to an app section. How do I read the program counter (PC) to save to EEPROM, so I could jump back to the application?

SPM doesn't support or disabled in Application Section, it works only in Bootloader Section. So there is NO WAY to change data in the flash when an app is running, user has to jump to BL mode to write data, then jump back to an app section. How do I read the program counter (PC) to save to EEPROM, so I could jump back to the application?

It's easy to write code that updates the flash at run time. As you say it just needs to use SPM and it has to be located in the bootloader section which is why has the BOOTLOADER_SECTION macro. But this is not the correct thread to be discussing this.

NOTE:
This thread is ONLY for discussing the original article about PROGMEM so I'm going to lock this thread now. If anyone has anything to add to correct/improve the original article then PM js, plons or clawson and ask one of us to temporarily unlock this thread to add your contribution.

pgm_read_byte needs an address to an array element, not the array element itself.

Thanks, John and Larry. In the end it was kinda obvious ;-)

The two questions in the last part of my recent posting will be concerned elsewhere, right? It rather has to do with the handling and displaying of FLASH locations within AVR STUDIO, not with the PROGMEM attribute itself.