Search code examples
gcclinkerlinker-scripts

MEMORY command in linker script bloat the binary size


I want to have a image which loads at 2 different memory locations and all address linking is done at compile/link time.

Overall objective I want to achieve

  1. Define different load region for text and data
  2. Resolve all symbol dependencies as per load address
  3. Put the text and data region back to back in image ( my loader will put the text section to different address at run time )

So I created the following script

MEMORY
{
    mem1 : ORIGIN = 0xfff00000, LENGTH = 100K
    mem2 : ORIGIN = 0xfff80000, LENGTH = 100K
}

SECTIONS
{
    . = 0xfff00000;

    _image_base_origin = . - 0;


    ////////////////////////////////
    // TEXT
    ////////////////////////////////
    .text : {
         _text_origin = .;
         . = ALIGN(4); _text_offset = . - _image_base_origin;  *(.vectors)      *(.text) *(.eh_frame)
     } > mem2
     _text_size = . - _text_origin;

    ////////////////////////////////
    // DATA
    ////////////////////////////////
    .data : {
            _data_origin = .;
            . = ALIGN(8); _data_offset = . - _image_base_origin;  *(.data) *(.comment) *(.rodata*) *(.bss*)
     } > mem1
     _data_size = . - _data_origin;

}

The problem I am facing the when i put text section of my image in mem2, the sizeof binary increase by many folds.

If I run readelf on my file

Section Headers:
  [Nr] Name              Type            Addr     Off    Size   ES Flg Lk Inf Al
  [ 5] .text             PROGBITS        fff80000 020000 0017a8 00  AX  0   0 32
  [ 6] .data             PROGBITS        fff00398 010398 0004f8 00  WA  0   0  8

So image size become 80000 + 17a8 . It adds offset of mem2 in image and create the binary. It pads all extra memory with zero.

If i put the text section in mem1 only, that my image size is very small( it does not add offset 80000 to my image ).

Can you please help me here.


Solution

  • The larger file size is no doubt to satisfy demand-paging requirement that vma % pagesize == file_offset % pagesize. If your system isn't demand paged, then you can link with -n. If your system is demand-paged then it is possible the ld default page size is unnecessarily large. The -z max-page-size option can fix that.