Re: gcc-4.1, gcl, function pointers and unexec
- To: Martin Michlmayr <tbm@cyrius.com>
- Cc: Camm Maguire <camm@enhanced.com>, debian-mips@lists.debian.org, Thiemo Seufer <ths@networkno.de>, gcl-devel@gnu.org, David Daney <ddaney@avtrex.com>
- Subject: Re: gcc-4.1, gcl, function pointers and unexec
- From: Richard Sandiford <richard@codesourcery.com>
- Date: Thu, 17 May 2007 16:06:02 +0100
- Message-id: <[🔎] 874pmbtrqd.fsf@firetop.home>
- Mail-followup-to: Martin Michlmayr <tbm@cyrius.com>, Camm Maguire <camm@enhanced.com>, debian-mips@lists.debian.org, Thiemo Seufer <ths@networkno.de>, gcl-devel@gnu.org, David Daney <ddaney@avtrex.com>, richard@codesourcery.com
- In-reply-to: <[🔎] 20070517141443.GB3586@deprecation.cyrius.com> (Martin Michlmayr's message of "Thu, 17 May 2007 16:14:43 +0200")
- References: <[🔎] E1HoNM8-0002PQ-Sz@intech19.enhanced.com> <[🔎] 20070517141443.GB3586@deprecation.cyrius.com>
Martin Michlmayr <tbm@cyrius.com> writes:
> CCing Richard Sandiford and David Daney who might have an answer.
>> Greetings! gcc-4.1 breaks saving of initialized function pointers via
>> unexec. This worked in gcc 3.x.
>>
>> =============================================================================
>> #include <math.h>
>> void * gcl_cos=(void *)cos;
>> int reset_plt(void) {gcl_cos=(void *)cos;}
>>
>> int main() {
>>
>> return 0;
>>
>> }
>> =============================================================================
>>
>> When the above snippet is linked and run under gdb, gcl_cos points
>> directly to an address beyond the address space of the executable,
>> i.e. in the shared memory area (i.e. no plt like entry as on x86 where
>> a trampoline address is stored in the executable itself)
MIPS does not use true PLTs. It has lazy binding stubs, but they are
local to the object that contains them, and do not participate in symbol
lookup (unlike x86 and most other SVR4 targets).
MIPS lazy binding stubs can only be used if all references to a function
are direct calls; they cannot be used if a function's address is taken.
When lazy binding stubs are not used, all references will be resolved
directly to the true definition. So...
>> (gdb) file raw_pre_gcl
>> A program is being debugged already. Kill it? (y or n) y
>>
>> Load new symbol table from "/home/camm/gclcvs-2.7.0/unixport/raw_pre_gcl"? (y or n) y
>> Reading symbols from /home/camm/gclcvs-2.7.0/unixport/raw_pre_gcl...done.
>> (gdb) r
>> Starting program: /home/camm/gclcvs-2.7.0/unixport/raw_pre_gcl
>>
>> Breakpoint 1, main (argc=1, argv=0x7fb33d94, envp=0x7fb33d9c) at main.c:619
>> 619 return gcl_main ( argc, argv, envp );
>> (gdb) p gcl_cos
>> $15 = (void *) 0x2ab1b6a0
>> (gdb) shell
>> camm@vaughan:~/gclcvs-2.7.0/unixport$ ldd raw_pre_gcl
>> libm.so.6 => /lib/libm.so.6 (0x2ab00000)
>> libc.so.6 => /lib/libc.so.6 (0x2abbc000)
>> /lib/ld.so.1 (0x2aaa8000)
...this is what I'd expect; gcl_cos points directly to the libm definition.
I've never looked at the unexec code, so I can't really answer the
unexec question. I certainly don't know what would have changed in
gcc to make a difference.
Richard
Reply to: