I am working on a research project where I need to compile a program with multiple sections. These sections need to be loaded with different PIE offsets. I am wondering how I can do it in GCC.
See below for a MWE. In my program there is a .my_region
section and other sections (.text
, .bss
, …). I want to make sure that all sections can be loaded at random addresses. Also, I want to make sure the relative offset between .my_region
and other sections are different.
For example, this is what I am looking for:
Run number | &my_array |
&start |
&normal_array |
---|---|---|---|
#1 | 0x01000000 | 0x00040000 | 0x00040120 |
#2 | 0x06000000 | 0x00040000 | 0x00040120 |
#3 | 0x0a000000 | 0x00080000 | 0x00080120 |
I think technically this can be implemented either using GOT or the .rela.dyn
section. However, I don’t know how to pass arguments to GCC and ld to achieve this.
Minimal working example (MWE):
a.c
:
int normal_array[10];
int my_array[10] __attribute__(( section(".my_data") ));
void start() {
normal_array[0] = 0;
my_array[1] = 1;
asm volatile("hlt");
}
l.lds
:
ENTRY(start)
MEMORY
{
all (rwxai) : ORIGIN = 3M, LENGTH = 1M
my_region (rwxai) : ORIGIN = 5M, LENGTH = 1M
}
SECTIONS
{
.my_data : {
*(.my_data)
} >my_region =0x9090
}
Makefile
:
CFLAGS = -fPIE
ASFLAGS = -fPIE
# I am on 64-bit x86 Linux platform.
a: a.o l.lds
ld -pie --dynamic-linker=/lib64/ld-linux-x86-64.so.2 -T l.lds -o $@ a.o
clean:
rm -f *.o a
Use make a
to compile. Use gdb a
to debug (set a break at start
and then step through each instruction).