Discussion:
Question about ADDR(SECTION) of ld in document
Cao jin
2018-10-31 13:01:45 UTC
Permalink
Hi,
(Please CC me when reply because I didn't subcribe)

I am learning linker script recently via reading the GUN linker
document. I find one piece of words confusing me, not sure if it is an
error in document. In "3.10.9 Builtin Functions" of `info ld`, there is:

'ADDR(SECTION)'
Return the address (VMA) of the named SECTION. Your script must
previously have defined the location of that section. In the
following example, 'start_of_output_1', 'symbol_1' and 'symbol_2'
are assigned equivalent values, except that 'symbol_1' will be
relative to the '.output1' section while the other two will be
absolute:
SECTIONS { ...
.output1 :
{
start_of_output_1 = ABSOLUTE(.);
...
}
.output :
{
symbol_1 = ADDR(.output1);
symbol_2 = start_of_output_1;
}
... }

My intuition tell me the symbol_1's value is relative to the ".output"
section, not ".output1", which is also the offset inside ".output", and
symbol_2's value is the same as symbol_1.

Why is that?

Sincerely,
Cao jin
Nick Clifton
2018-11-06 16:40:52 UTC
Permalink
Hi Cao,
Post by Cao jin
'ADDR(SECTION)'
Return the address (VMA) of the named SECTION. Your script must
previously have defined the location of that section. In the
following example, 'start_of_output_1', 'symbol_1' and 'symbol_2'
are assigned equivalent values, except that 'symbol_1' will be
relative to the '.output1' section while the other two will be
SECTIONS { ...
{
start_of_output_1 = ABSOLUTE(.);
...
}
{
symbol_1 = ADDR(.output1);
symbol_2 = start_of_output_1;
}
... }
My intuition tell me the symbol_1's value is relative to the ".output"
section, not ".output1", which is also the offset inside ".output", and
symbol_2's value is the same as symbol_1.
It is non-intuitive, I agree. But the documentation is correct. If you
look at the symbol table qfter linking something with the above linker
script you will see that symbol_1 is actually set to be relative to the
.output1 section, not the .output section. This is despite the fact that
it is defined in the .output section.

For example:

% readelf --syms --wide --sections a.out
Section Headers:
[Nr] Name Type Address Off Size ES Flg Lk Inf Al
[ 1] .output2 PROGBITS 0000000000000000 200000 000004 00 WA 0 0 1
[ 2] .output1 PROGBITS 0000000000000004 200004 000004 00 WA 0 0 1
[ 3] .output PROGBITS 0000000000000008 200008 00000c 00 WA 0 0 1

Symbol table '.symtab' contains 9 entries:
Num: Value Size Type Bind Vis Ndx Name
4: 0000000000000004 0 NOTYPE GLOBAL DEFAULT ABS start_of_output_1
5: 0000000000000004 0 NOTYPE GLOBAL DEFAULT 2 symbol_1
6: 000000000000000c 0 NOTYPE GLOBAL DEFAULT 3 symbol_2

Note that the "Ndx" field of symbol_1 is 2 (ie the .output1 section)
whereas the Ndx field of symbol_2 is 3 (ie the .output section).

(I am using a slightly tweaked version of the linker script from the documentation
which is why some of the actual values may not be what you expect).

Cheers
Nick
Cao jin
2018-11-11 11:38:46 UTC
Permalink
Hi Nick

Sorry for late and thanks very much for your demonstration.
Post by Nick Clifton
Hi Cao,
Post by Cao jin
'ADDR(SECTION)'
Return the address (VMA) of the named SECTION. Your script must
previously have defined the location of that section. In the
following example, 'start_of_output_1', 'symbol_1' and 'symbol_2'
are assigned equivalent values, except that 'symbol_1' will be
relative to the '.output1' section while the other two will be
SECTIONS { ...
{
start_of_output_1 = ABSOLUTE(.);
...
}
{
symbol_1 = ADDR(.output1);
symbol_2 = start_of_output_1;
}
... }
My intuition tell me the symbol_1's value is relative to the ".output"
section, not ".output1", which is also the offset inside ".output", and
symbol_2's value is the same as symbol_1.
It is non-intuitive, I agree. But the documentation is correct. If you
look at the symbol table qfter linking something with the above linker
script you will see that symbol_1 is actually set to be relative to the
.output1 section, not the .output section. This is despite the fact that
it is defined in the .output section.
% readelf --syms --wide --sections a.out
[Nr] Name Type Address Off Size ES Flg Lk Inf Al
[ 1] .output2 PROGBITS 0000000000000000 200000 000004 00 WA 0 0 1
[ 2] .output1 PROGBITS 0000000000000004 200004 000004 00 WA 0 0 1
[ 3] .output PROGBITS 0000000000000008 200008 00000c 00 WA 0 0 1
Num: Value Size Type Bind Vis Ndx Name
4: 0000000000000004 0 NOTYPE GLOBAL DEFAULT ABS start_of_output_1
5: 0000000000000004 0 NOTYPE GLOBAL DEFAULT 2 symbol_1
6: 000000000000000c 0 NOTYPE GLOBAL DEFAULT 3 symbol_2
Note that the "Ndx" field of symbol_1 is 2 (ie the .output1 section)
whereas the Ndx field of symbol_2 is 3 (ie the .output section).
(I am using a slightly tweaked version of the linker script from the documentation
which is why some of the actual values may not be what you expect).
I did the test as you did, it does shows the same as yours. It looks
like the confusing point is what does the "relative" mean exactly, after
looking at st_shndx of `man elf`, I can understand it a little bit more,
but still not clear how it would be used:(

Sincerely,
Cao jin

Loading...