Linker command -W1

I am working with a large amount of data using s Mega processor and I need to put in PROGMEM.

I am instructing the compiler to place the data in Sections .fini9, .fini8 and .fini7. I am also instructing the compiler to place the data after the program data using the following:

#define PROGMEM_Late1 __attribute_ ((__section(".fini9") ))

and that is working. I know this because my program continues to work even when the data involved is larger than 64k.

The problem I am having is that the data is getting corrupted when the data crosses over a 64k boundary. To fix this problem I want to force the compiler/linker to place the sections at specific memory locations.

The "avr" manual says I can do this with a "-W1" command. The "avr" manual says that the command can be used from the "C" compiler using the following command:

-W1,--section-start=.fini9=0xfa01    // 64k
-W1,--section-start=.fini8=0x1f401  // 128k
-W1,--section-start=.fini7=0x2ee01 // 192k

I can't get it to compile. I have tried all of the following:

 & avr -W1,--section-start=.fini9=0xfa00
 avr-W1,--section-start=.fini9=0xfa00

I have placed the command in the "Setup" loop as well as at the top of the program where my #include and #define statements are located.

Can this be done from the compiler and if so how??

My guess is that you would need to do this in the platform.txt of the selected board. I don't think you can do it from the sketch. I could certainly be wrong about this though. Maybe it's possible using attributes.

You need to use pgm_read_xxx_far() instead of pgm_read_xxx_near() to read things above 64k.

The --section-start parameter must be passed to the linker as a command line argument - it's not part of your code, it doesn't go in the sketch. As Pert said, the command line parameters are figured out from the platform.txt - making them rather inconvenient to modify.

…and you may not be able to fix the predefined .fini sections to specific addresses. The linker is bound by rules that apply to those sections (the rules are defined in a “linker script”).

But, if you are doing such things, you can just as easily use your own sections. There is no compelling reason to continue using .fini sections.

I have figured out how to use the pgm_read_xxx_far/near()calls to read the data. The problem I am having involves the fact that:

1) I don't know which one to use as I really don't know where the compiler put the data; and 2) when the data crosses over a 64k barrier, the data tends to become corrupted.

By using the following "define" statement, I am able to make the compiler put the "PROGMEM" data after the program instead of before the program. At least the program runs and does not get correpted and crash.

#define PROGMEM_LATE1 __attribute__ (( __section__(".fini9") ))

I am also using the following define statement to set the addressing for the data up as a "far address".

#define pgm_get_far_address(Image_2d_Array_1) // 31k array
#define pgm_get_far_address(Image_2d_Array_2) // 31k array

I was hoping to be able to force the compiler to put the sections at a specific place using some sort of "attribute" call or define statement.

I looked at the "platform.txt file and that does not look easy.

I suspected that the rules setup for the ".fini" sections were defined in the linker scripts and I have not looked at them.

As for using sections of my own design, wouldn't they need to be defined in the linker scripts??

Thanks for the input.

KenK:
As for using sections of my own design, wouldn’t they need to be defined in the linker scripts??

Or linker command-line as you are trying to do with .fini sections.

Looks like I have a significant amount of studying ahead of me.

I found a manual for the "Platform.txt" file and for the linker. I have done a cursory review of the "Platform.txt" manual. I guess I will have to do a lot more studying.

Thanks for all of your help