* Re: recent SIGBUS/SIGSEGV mips kernel bug [not found] ` <87r5fksxby.fsf_-_@maguirefamily.org> @ 2010-10-20 16:38 ` David Daney 2010-10-20 21:31 ` Camm Maguire 0 siblings, 1 reply; 21+ messages in thread From: David Daney @ 2010-10-20 16:38 UTC (permalink / raw) To: Camm Maguire; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips On 10/20/2010 08:22 AM, Camm Maguire wrote: > Greetings! Recent mips (aka gabrielli sid) appears to have a new > SIGBUS/SIGSEGV bug. Briefly, attempted writes to pages mprotected > read-only occasionally pass a SIGBUS instead of SIGSEGV to the > sigaction handler. In such an instance, the code of the siginfo > structure is 128, and the fault address is not filled in. This > behavior appears to hinge on writing from the floating point registers > into the protected memory. > What processor is it running on? Specifically does it have hardware floating point, or are the floating point instructions being emulated in the kernel? It is conceivable that it is an FPU emulator bug. David Daney > strace: > > 30717 mprotect(0x2f59000, 4096, PROT_READ|PROT_EXEC) = 0 > 30717 mprotect(0x2f5a000, 745472, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 mprotect(0x3010000, 323584, PROT_READ|PROT_EXEC) = 0 > 30717 mprotect(0x305f000, 548864, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 mprotect(0x30e5000, 1220608, PROT_READ|PROT_EXEC) = 0 > 30717 mprotect(0x320f000, 53559296, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 mprotect(0x6523000, 53739520, PROT_READ|PROT_EXEC) = 0 > 30717 mprotect(0x9863000, 60375040, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 mprotect(0x6523000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 --- SIGSEGV (Segmentation fault) @ 0 (0) --- /* good */ > 30717 mprotect(0x31fb000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 rt_sigreturn(0xdc5e80) = -1 EPERM (Operation not permitted) > 30717 --- SIGSEGV (Segmentation fault) @ 0 (0) --- /* good */ > 30717 mprotect(0x9862000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 > 30717 rt_sigreturn(0xdc5e80) = -1 EBADF (Bad file descriptor) > 30717 --- SIGBUS (Bus error) @ 0 (0) --- /* bad handler call */ > > Here are the gdb details: > > (gdb) frame 28 > #28 0x004a3e98 in memprotect_handler (sig=10, code=2140765848, > scp=0x7f997f18, addr=0xfdb6c0 "\b") at sgbc.c:1687 > 1687 segmentation_catcher(0); > (gdb) p faddr > $1 = 0x0 > (gdb) p/x *((siginfo_t *)code ) > $2 = {si_signo = 0xa, si_code = 0x80, si_errno = 0x0, __pad0 = 0x7f997e98, > _sifields = {_pad = {0x0, 0x0, 0x7f997eb4, 0x7f997fd4, 0x2167b80, > 0x233c5b8, 0xde5e80, 0xbbec80, 0x65f8a80, 0x7f997ed0, 0x4951a8, > 0xbbec80, 0xffffffff, 0x7f997ee0, 0x495170, 0xbbec80, 0x65f8a48, > 0x7f997ef0, 0x4951a8, 0xbbec80, 0xffffffff, 0x7f997f00, 0x495170, > 0xbbec80, 0x31ecc48, 0x7f997f10, 0xfdead4, 0x7f997f18, 0x454ebc}, > _kill = {si_pid = 0x0, si_uid = 0x0}, _timer = {si_tid = 0x0, > si_overrun = 0x0, si_sigval = {sival_int = 0x7f997eb4, > sival_ptr = 0x7f997eb4}}, _rt = {si_pid = 0x0, si_uid = 0x0, > si_sigval = {sival_int = 0x7f997eb4, sival_ptr = 0x7f997eb4}}, > _sigchld = {si_pid = 0x0, si_uid = 0x0, si_status = 0x7f997eb4, > si_utime = 0x7f997fd4, si_stime = 0x2167b80}, _sigfault = { > si_addr = 0x0}, _sigpoll = {si_band = 0x0, si_fd = 0x0}}} > (gdb) up > #29<signal handler called> > (gdb) up > #30 0x004484e8 in fSaset1 (x=0x29b5930, i=0, val=0x2d8d870) at array.c:231 > 231 (x->lfa.lfa_self[i]) = Mlf(val); > (gdb) p/x x->lfa.lfa_self > $3 = 0x9861ff0 > (gdb) disassemble > 0x004484d8<+1352>: lwc1 $f0,12(v1) > 0x004484dc<+1356>: move at,at > 0x004484e0<+1360>: lwc1 $f1,8(v1) > 0x004484e4<+1364>: move at,at > => 0x004484e8<+1368>: swc1 $f0,4(v0) > 0x004484ec<+1372>: swc1 $f1,0(v0) > (gdb) i reg v1 > v1: 0x2d8d870 > (gdb) i reg f1 > f1: 0x3fa2056c flt: 1.26579046 > (gdb) i reg f0 > f0: 0x8f1afe4f flt: -7.64176427e-30 dbl: 0.035197632283140316 > (gdb) i reg v0 > v0: 0x9861ff0 > > How should this be filed? > > Take care, ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-20 16:38 ` recent SIGBUS/SIGSEGV mips kernel bug David Daney @ 2010-10-20 21:31 ` Camm Maguire 2010-10-21 16:19 ` David Daney 0 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-20 21:31 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings! Does this suffice? (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC 2010 mips64 GNU/Linux (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo system type : CUST_WSX16 (CN3860p3.X-500-EXP) processor : 0 cpu model : Cavium Octeon V0.3 BogoMIPS : 1001.60 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 1 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.91 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 2 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 3 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.90 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 4 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 5 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 6 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 7 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.90 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 8 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 9 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 10 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.90 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 11 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.88 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 12 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 13 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.89 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 14 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.90 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available processor : 15 cpu model : Cavium Octeon V0.3 BogoMIPS : 1000.90 wait instruction : yes microsecond timers : yes tlb_entries : 32 extra interrupt vector : yes hardware watchpoint : yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available (sid)camm@gabrielli:~/maxima-5.22.1/tests$ Take care, David Daney <ddaney@caviumnetworks.com> writes: > On 10/20/2010 08:22 AM, Camm Maguire wrote: >> Greetings! Recent mips (aka gabrielli sid) appears to have a new >> SIGBUS/SIGSEGV bug. Briefly, attempted writes to pages mprotected >> read-only occasionally pass a SIGBUS instead of SIGSEGV to the >> sigaction handler. In such an instance, the code of the siginfo >> structure is 128, and the fault address is not filled in. This >> behavior appears to hinge on writing from the floating point registers >> into the protected memory. >> > > What processor is it running on? Specifically does it have hardware > floating point, or are the floating point instructions being emulated > in the kernel? > > It is conceivable that it is an FPU emulator bug. > > David Daney > > >> strace: >> >> 30717 mprotect(0x2f59000, 4096, PROT_READ|PROT_EXEC) = 0 >> 30717 mprotect(0x2f5a000, 745472, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 mprotect(0x3010000, 323584, PROT_READ|PROT_EXEC) = 0 >> 30717 mprotect(0x305f000, 548864, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 mprotect(0x30e5000, 1220608, PROT_READ|PROT_EXEC) = 0 >> 30717 mprotect(0x320f000, 53559296, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 mprotect(0x6523000, 53739520, PROT_READ|PROT_EXEC) = 0 >> 30717 mprotect(0x9863000, 60375040, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 mprotect(0x6523000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 --- SIGSEGV (Segmentation fault) @ 0 (0) --- /* good */ >> 30717 mprotect(0x31fb000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 rt_sigreturn(0xdc5e80) = -1 EPERM (Operation not permitted) >> 30717 --- SIGSEGV (Segmentation fault) @ 0 (0) --- /* good */ >> 30717 mprotect(0x9862000, 4096, PROT_READ|PROT_WRITE|PROT_EXEC) = 0 >> 30717 rt_sigreturn(0xdc5e80) = -1 EBADF (Bad file descriptor) >> 30717 --- SIGBUS (Bus error) @ 0 (0) --- /* bad handler call */ >> >> Here are the gdb details: >> >> (gdb) frame 28 >> #28 0x004a3e98 in memprotect_handler (sig=10, code=2140765848, >> scp=0x7f997f18, addr=0xfdb6c0 "\b") at sgbc.c:1687 >> 1687 segmentation_catcher(0); >> (gdb) p faddr >> $1 = 0x0 >> (gdb) p/x *((siginfo_t *)code ) >> $2 = {si_signo = 0xa, si_code = 0x80, si_errno = 0x0, __pad0 = 0x7f997e98, >> _sifields = {_pad = {0x0, 0x0, 0x7f997eb4, 0x7f997fd4, 0x2167b80, >> 0x233c5b8, 0xde5e80, 0xbbec80, 0x65f8a80, 0x7f997ed0, 0x4951a8, >> 0xbbec80, 0xffffffff, 0x7f997ee0, 0x495170, 0xbbec80, 0x65f8a48, >> 0x7f997ef0, 0x4951a8, 0xbbec80, 0xffffffff, 0x7f997f00, 0x495170, >> 0xbbec80, 0x31ecc48, 0x7f997f10, 0xfdead4, 0x7f997f18, 0x454ebc}, >> _kill = {si_pid = 0x0, si_uid = 0x0}, _timer = {si_tid = 0x0, >> si_overrun = 0x0, si_sigval = {sival_int = 0x7f997eb4, >> sival_ptr = 0x7f997eb4}}, _rt = {si_pid = 0x0, si_uid = 0x0, >> si_sigval = {sival_int = 0x7f997eb4, sival_ptr = 0x7f997eb4}}, >> _sigchld = {si_pid = 0x0, si_uid = 0x0, si_status = 0x7f997eb4, >> si_utime = 0x7f997fd4, si_stime = 0x2167b80}, _sigfault = { >> si_addr = 0x0}, _sigpoll = {si_band = 0x0, si_fd = 0x0}}} >> (gdb) up >> #29<signal handler called> >> (gdb) up >> #30 0x004484e8 in fSaset1 (x=0x29b5930, i=0, val=0x2d8d870) at array.c:231 >> 231 (x->lfa.lfa_self[i]) = Mlf(val); >> (gdb) p/x x->lfa.lfa_self >> $3 = 0x9861ff0 >> (gdb) disassemble >> 0x004484d8<+1352>: lwc1 $f0,12(v1) >> 0x004484dc<+1356>: move at,at >> 0x004484e0<+1360>: lwc1 $f1,8(v1) >> 0x004484e4<+1364>: move at,at >> => 0x004484e8<+1368>: swc1 $f0,4(v0) >> 0x004484ec<+1372>: swc1 $f1,0(v0) >> (gdb) i reg v1 >> v1: 0x2d8d870 >> (gdb) i reg f1 >> f1: 0x3fa2056c flt: 1.26579046 >> (gdb) i reg f0 >> f0: 0x8f1afe4f flt: -7.64176427e-30 dbl: 0.035197632283140316 >> (gdb) i reg v0 >> v0: 0x9861ff0 >> >> How should this be filed? >> >> Take care, > > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-20 21:31 ` Camm Maguire @ 2010-10-21 16:19 ` David Daney 2010-10-21 16:32 ` Camm Maguire 2010-10-21 17:29 ` David Daney 0 siblings, 2 replies; 21+ messages in thread From: David Daney @ 2010-10-21 16:19 UTC (permalink / raw) To: Camm Maguire; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips On 10/20/2010 02:31 PM, Camm Maguire wrote: > Greetings! > > Does this suffice? > > (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a > Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC 2010 mips64 GNU/Linux > (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo > system type : CUST_WSX16 (CN3860p3.X-500-EXP) > processor : 0 > cpu model : Cavium Octeon V0.3 [...] Hah! I have those things piled up all around me. No guarantees, but I will try to reproduce it. If I can reproduce it, it should be easy to fix. David Daney ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-21 16:19 ` David Daney @ 2010-10-21 16:32 ` Camm Maguire 2010-10-21 17:29 ` David Daney 1 sibling, 0 replies; 21+ messages in thread From: Camm Maguire @ 2010-10-21 16:32 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings! David Daney <ddaney@caviumnetworks.com> writes: > On 10/20/2010 02:31 PM, Camm Maguire wrote: >> Greetings! >> >> Does this suffice? >> >> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a >> Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC 2010 mips64 GNU/Linux >> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo >> system type : CUST_WSX16 (CN3860p3.X-500-EXP) >> processor : 0 >> cpu model : Cavium Octeon V0.3 > [...] > > Hah! I have those things piled up all around me. > > No guarantees, but I will try to reproduce it. If I can reproduce it, > it should be easy to fix. > > David Daney > Thanks so much! Please keep me posted. Take care, > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-21 16:19 ` David Daney 2010-10-21 16:32 ` Camm Maguire @ 2010-10-21 17:29 ` David Daney 2010-10-21 19:07 ` Camm Maguire ` (2 more replies) 1 sibling, 3 replies; 21+ messages in thread From: David Daney @ 2010-10-21 17:29 UTC (permalink / raw) To: David Daney Cc: Camm Maguire, debian-mips, Frederick Isaac, gcl-devel, linux-mips On 10/21/2010 09:19 AM, David Daney wrote: > On 10/20/2010 02:31 PM, Camm Maguire wrote: >> Greetings! >> >> Does this suffice? >> >> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a >> Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC >> 2010 mips64 GNU/Linux >> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo >> system type : CUST_WSX16 (CN3860p3.X-500-EXP) >> processor : 0 >> cpu model : Cavium Octeon V0.3 > [...] > > Hah! I have those things piled up all around me. > > No guarantees, but I will try to reproduce it. If I can reproduce it, it > should be easy to fix. > Definitely a kernel bug. Consider this program: ------------8<--------sigbus.c------- #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <sys/mman.h> int main(int argc, char *argv[]) { int pgsize; float *p1; float *p2; int r; pgsize = getpagesize(); p1 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); if (p1 == MAP_FAILED) { perror("mmap p1 failed"); exit(1); } p2 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); if (p2 == MAP_FAILED) { perror("mmap p2 failed"); exit(1); } *p1 = 2.5; *p2 = 3.5; r = mprotect(p1, pgsize, PROT_READ); if (r) { perror("mprotect p1 failed"); exit(1); } r = mprotect(p2, pgsize, PROT_READ); if (r) { perror("mprotect p2 failed"); exit(1); } *p2 = *p1; asm volatile("" ::: "memory"); puts("All done!"); exit(0); } ------------8<----------------------- $ mips64-octeon-linux-gnu-gcc -Wall -mhard-float -march=mips64 -O3 -o sigbus sigbus.c $ mips64-octeon-linux-gnu-objdump -d sigbus > sigbus.dis The float copy '*p2 = *p1;' dissassembles as: 120000b30: c6400000 lwc1 $f0,0(s2) 120000b34: e6000000 swc1 $f0,0(s0) When run on an FPU-less system I get: ~ # ./sigbus Bus error When run on my x86_64 workstation: $ ./sigbus Segmentation fault (core dumped) I will fix this kernel bug. David Daney ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-21 17:29 ` David Daney @ 2010-10-21 19:07 ` Camm Maguire 2010-10-25 20:11 ` Camm Maguire 2010-10-25 21:32 ` gdb for mips64 Camm Maguire 2 siblings, 0 replies; 21+ messages in thread From: Camm Maguire @ 2010-10-21 19:07 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings! David Daney <ddaney@caviumnetworks.com> writes: > On 10/21/2010 09:19 AM, David Daney wrote: >> On 10/20/2010 02:31 PM, Camm Maguire wrote: >>> Greetings! >>> >>> Does this suffice? >>> >>> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a >>> Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC >>> 2010 mips64 GNU/Linux >>> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo >>> system type : CUST_WSX16 (CN3860p3.X-500-EXP) >>> processor : 0 >>> cpu model : Cavium Octeon V0.3 >> [...] >> >> Hah! I have those things piled up all around me. >> >> No guarantees, but I will try to reproduce it. If I can reproduce it, it >> should be easy to fix. >> > > Definitely a kernel bug. Consider this program: > > ------------8<--------sigbus.c------- > #include <stdio.h> > #include <stdlib.h> > #include <unistd.h> > > #include <sys/mman.h> > > int main(int argc, char *argv[]) > { > int pgsize; > float *p1; > float *p2; > int r; > > pgsize = getpagesize(); > > p1 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, > MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); > > if (p1 == MAP_FAILED) { > perror("mmap p1 failed"); > exit(1); > } > > p2 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, > MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); > > if (p2 == MAP_FAILED) { > perror("mmap p2 failed"); > exit(1); > } > > *p1 = 2.5; > *p2 = 3.5; > > r = mprotect(p1, pgsize, PROT_READ); > if (r) { > perror("mprotect p1 failed"); > exit(1); > } > > r = mprotect(p2, pgsize, PROT_READ); > if (r) { > perror("mprotect p2 failed"); > exit(1); > } > > *p2 = *p1; > > asm volatile("" ::: "memory"); > > puts("All done!"); > > exit(0); > } > ------------8<----------------------- > > $ mips64-octeon-linux-gnu-gcc -Wall -mhard-float -march=mips64 -O3 -o > sigbus sigbus.c > $ mips64-octeon-linux-gnu-objdump -d sigbus > sigbus.dis > > The float copy '*p2 = *p1;' dissassembles as: > > 120000b30: c6400000 lwc1 $f0,0(s2) > 120000b34: e6000000 swc1 $f0,0(s0) > > When run on an FPU-less system I get: > > ~ # ./sigbus > Bus error > > When run on my x86_64 workstation: > > $ ./sigbus > Segmentation fault (core dumped) > > I will fix this kernel bug. > Great! Thanks! If you have time to drop a quick note when done, that would be awesome. Separately, do you know where I can find pre-built gdb binaries for mips64, i.e. to debug -mabi=64? I'm assuming that is the 'official one' going foward. (I have an account on the gcc compile farm.) Thanks so much! > David Daney > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: recent SIGBUS/SIGSEGV mips kernel bug 2010-10-21 17:29 ` David Daney 2010-10-21 19:07 ` Camm Maguire @ 2010-10-25 20:11 ` Camm Maguire 2010-10-25 21:32 ` gdb for mips64 Camm Maguire 2 siblings, 0 replies; 21+ messages in thread From: Camm Maguire @ 2010-10-25 20:11 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings, and thanks so much for this and the kernel fix! I've committed a little test which hopefully will enable trapping these signals when the kernel fix is in place: --- o/sgbc.c 1 Oct 2010 19:15:40 -0000 1.9.4.1.2.12.6.1.2.1.6.4 +++ o/sgbc.c 25 Oct 2010 19:46:35 -0000 @@ -1146,10 +1146,6 @@ memset(b1,32,2*p); memset(b2,0,p); memprotect_test_address=(void *)(((unsigned long)b1+p-1) & ~(p-1)); - if (mprotect(memprotect_test_address,p,PROT_READ_EXEC)) { - memprotect_result=memprotect_cannot_protect; - return -1; - } sa.sa_sigaction=(void *)memprotect_handler_test; sa.sa_flags=MPROTECT_ACTION_FLAGS; if (sigaction(SIGSEGV,&sa,&sao)) { @@ -1161,6 +1157,29 @@ memprotect_result=memprotect_sigaction; return -1; } + { /* mips kernel bug test -- SIGBUS with no faddr when floating point is emulated. */ + float *f1=(void *)memprotect_test_address,*f2=(void *)b2; + + if (mprotect(memprotect_test_address,p,PROT_READ_EXEC)) { + memprotect_result=memprotect_cannot_protect; + return -1; + } + memprotect_result=memprotect_bad_return; + *f1=*f2; + if (memprotect_result==memprotect_bad_return) + memprotect_result=memprotect_no_signal; + if (memprotect_result!=memprotect_none) { + sigaction(SIGSEGV,&sao,NULL); + sigaction(SIGBUS,&saob,NULL); + return -1; + } + memprotect_handler_invocations=0; + + } + if (mprotect(memprotect_test_address,p,PROT_READ_EXEC)) { + memprotect_result=memprotect_cannot_protect; + return -1; + } memprotect_result=memprotect_bad_return; memset(memprotect_test_address,0,p); if (memprotect_result==memprotect_bad_return) This seems to work, but if you see any shortcomings, please let me know. Thanks so much again! David Daney <ddaney@caviumnetworks.com> writes: > On 10/21/2010 09:19 AM, David Daney wrote: >> On 10/20/2010 02:31 PM, Camm Maguire wrote: >>> Greetings! >>> >>> Does this suffice? >>> >>> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ uname -a >>> Linux gabrielli 2.6.35.4-dsa-octeon #1 SMP Fri Sep 17 21:15:34 UTC >>> 2010 mips64 GNU/Linux >>> (sid)camm@gabrielli:~/maxima-5.22.1/tests$ cat /proc/cpuinfo >>> system type : CUST_WSX16 (CN3860p3.X-500-EXP) >>> processor : 0 >>> cpu model : Cavium Octeon V0.3 >> [...] >> >> Hah! I have those things piled up all around me. >> >> No guarantees, but I will try to reproduce it. If I can reproduce it, it >> should be easy to fix. >> > > Definitely a kernel bug. Consider this program: > > ------------8<--------sigbus.c------- > #include <stdio.h> > #include <stdlib.h> > #include <unistd.h> > > #include <sys/mman.h> > > int main(int argc, char *argv[]) > { > int pgsize; > float *p1; > float *p2; > int r; > > pgsize = getpagesize(); > > p1 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, > MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); > > if (p1 == MAP_FAILED) { > perror("mmap p1 failed"); > exit(1); > } > > p2 = mmap(NULL, pgsize, PROT_READ | PROT_WRITE, > MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); > > if (p2 == MAP_FAILED) { > perror("mmap p2 failed"); > exit(1); > } > > *p1 = 2.5; > *p2 = 3.5; > > r = mprotect(p1, pgsize, PROT_READ); > if (r) { > perror("mprotect p1 failed"); > exit(1); > } > > r = mprotect(p2, pgsize, PROT_READ); > if (r) { > perror("mprotect p2 failed"); > exit(1); > } > > *p2 = *p1; > > asm volatile("" ::: "memory"); > > puts("All done!"); > > exit(0); > } > ------------8<----------------------- > > $ mips64-octeon-linux-gnu-gcc -Wall -mhard-float -march=mips64 -O3 -o > sigbus sigbus.c > $ mips64-octeon-linux-gnu-objdump -d sigbus > sigbus.dis > > The float copy '*p2 = *p1;' dissassembles as: > > 120000b30: c6400000 lwc1 $f0,0(s2) > 120000b34: e6000000 swc1 $f0,0(s0) > > When run on an FPU-less system I get: > > ~ # ./sigbus > Bus error > > When run on my x86_64 workstation: > > $ ./sigbus > Segmentation fault (core dumped) > > I will fix this kernel bug. > > David Daney > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* gdb for mips64 2010-10-21 17:29 ` David Daney 2010-10-21 19:07 ` Camm Maguire 2010-10-25 20:11 ` Camm Maguire @ 2010-10-25 21:32 ` Camm Maguire 2010-10-25 21:45 ` David Daney 2 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-25 21:32 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings! Can gdb be made to work on mips64? (gdb) r Starting program: /home/camm/gcl-2.6.8pre/unixport/saved_pre_gcl /home/wingsun/develop/build/gdb/gdb-6.8/gdb/mips-tdep.c:603: internal-error: bad register size A problem internal to GDB has been detected, further debugging may prove unreliable. Take care, -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: gdb for mips64 2010-10-25 21:32 ` gdb for mips64 Camm Maguire @ 2010-10-25 21:45 ` David Daney 2010-10-26 12:47 ` Maciej W. Rozycki 2010-10-26 14:47 ` gdb for mips64 Camm Maguire 0 siblings, 2 replies; 21+ messages in thread From: David Daney @ 2010-10-25 21:45 UTC (permalink / raw) To: Camm Maguire; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips On 10/25/2010 02:32 PM, Camm Maguire wrote: > Greetings! Can gdb be made to work on mips64? > You have to have a 64-bit toolchain. Then something like this (untested): CC='mips64-linux-gnu -mabi=64' configure --host=mips64-linux --target=mips64-linux. I don't think a 32-bit gdb can debug 64-bit processes :-(. David Daney > (gdb) r > Starting program: /home/camm/gcl-2.6.8pre/unixport/saved_pre_gcl > /home/wingsun/develop/build/gdb/gdb-6.8/gdb/mips-tdep.c:603: internal-error: bad register size > A problem internal to GDB has been detected, > further debugging may prove unreliable. > > Take care, ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: gdb for mips64 2010-10-25 21:45 ` David Daney @ 2010-10-26 12:47 ` Maciej W. Rozycki 2010-10-26 17:19 ` David Daney 2010-10-26 14:47 ` gdb for mips64 Camm Maguire 1 sibling, 1 reply; 21+ messages in thread From: Maciej W. Rozycki @ 2010-10-26 12:47 UTC (permalink / raw) To: David Daney Cc: Camm Maguire, debian-mips, Frederick Isaac, gcl-devel, linux-mips On Mon, 25 Oct 2010, David Daney wrote: > I don't think a 32-bit gdb can debug 64-bit processes :-(. And it should (assuming ptrace(2) gets things right) -- if what you say is true, then it's a bug rather than a deliberate design decision. To add some irony, MIPS GDB is always 64-bit internally. > > (gdb) r > > Starting program: /home/camm/gcl-2.6.8pre/unixport/saved_pre_gcl > > /home/wingsun/develop/build/gdb/gdb-6.8/gdb/mips-tdep.c:603: internal-error: > > bad register size > > A problem internal to GDB has been detected, > > further debugging may prove unreliable. Try a newer version though -- GDB 7.2 has been out for a (short) while now. You're missing 2.5 years of development. If still unsuccessful with a pristine release from ftp.gnu.org, then file a bug report at http://sourceware.org/gdb/bugs/. Maciej ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: gdb for mips64 2010-10-26 12:47 ` Maciej W. Rozycki @ 2010-10-26 17:19 ` David Daney 2010-11-01 16:24 ` mips and ADDR_NO_RANDOMIZE Camm Maguire 0 siblings, 1 reply; 21+ messages in thread From: David Daney @ 2010-10-26 17:19 UTC (permalink / raw) To: Maciej W. Rozycki Cc: Camm Maguire, debian-mips, Frederick Isaac, gcl-devel, linux-mips On 10/26/2010 05:47 AM, Maciej W. Rozycki wrote: > On Mon, 25 Oct 2010, David Daney wrote: > >> I don't think a 32-bit gdb can debug 64-bit processes :-(. > > And it should (assuming ptrace(2) gets things right) -- if what you say > is true, then it's a bug rather than a deliberate design decision. To add > some irony, MIPS GDB is always 64-bit internally. > >>> (gdb) r >>> Starting program: /home/camm/gcl-2.6.8pre/unixport/saved_pre_gcl >>> /home/wingsun/develop/build/gdb/gdb-6.8/gdb/mips-tdep.c:603: internal-error: >>> bad register size >>> A problem internal to GDB has been detected, >>> further debugging may prove unreliable. > > Try a newer version though -- GDB 7.2 has been out for a (short) while > now. You're missing 2.5 years of development. If still unsuccessful with > a pristine release from ftp.gnu.org, then file a bug report at > http://sourceware.org/gdb/bugs/. > After more though, I think you may have to configure with --enable-64-bit-bfd for a 32-bit gdb to work on 64-bit processes. Although I have not actually tested that. In the past, I have just built a native 64-bit gdb. David Daney ^ permalink raw reply [flat|nested] 21+ messages in thread
* mips and ADDR_NO_RANDOMIZE 2010-10-26 17:19 ` David Daney @ 2010-11-01 16:24 ` Camm Maguire 2010-11-01 18:06 ` David Daney 0 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-11-01 16:24 UTC (permalink / raw) To: David Daney Cc: Maciej W. Rozycki, debian-mips, gcl-devel, Andreas Barth, linux-mips Greetings! Executing personality() with the ADDR_NO_RANDOMIZE bit set, and re-executing via execve, should yield a process with traditional contiguous brk() addresses appended to the .data segment, independent of the setting of sysctl kernel.randomize_va_space, right? At least this is the way the linux kernel has been working on x86 for many years. The latest Debian mips kernel is not honoring this setting. I'd like to know if this is a kernel bug. ============================================================================= h/unrandomize.h ============================================================================= #include <sys/personality.h> #include <syscall.h> #include <unistd.h> #include <alloca.h> #include <errno.h> { errno=0; { long pers = personality(0xffffffffUL); if (pers==-1) {printf("personality failure %d\n",errno);exit(-1);} if (!(pers & ADDR_NO_RANDOMIZE) && !getenv("GCL_UNRANDOMIZE")) { errno=0; if (personality(pers | ADDR_NO_RANDOMIZE) != -1 && personality(0xffffffffUL) & ADDR_NO_RANDOMIZE) { int i; char **n; for (i=0;envp[i];i++); n=alloca((i+2)*sizeof(*n)); n[i+1]=0; n[i--]="GCL_UNRANDOMIZE=t"; for (;i>=0;i--) n[i]=envp[i]; #ifdef GCL_GPROF gprof_cleanup(); #endif errno=0; execve(*argv,argv,n); printf("execve failure %d\n",errno); exit(-1); } else { printf("personality change failure %d\n",errno); exit(-1); } } } } ============================================================================= f.c ============================================================================= #include <stdio.h> void gprof_cleanup() {}; int main(int argc,char * argv[],char * envp[]) { FILE *f; #include "h/unrandomize.h" if (!(f=fopen("conftest1","w"))) return -1; fprintf(f,"%u",sbrk(0)); return 0;} ============================================================================= ./f && cat conftest1 && echo && ./f && cat conftest1 10043392 10584064 ============================================================================= strace -f ./f ============================================================================= execve("./f", ["./f"], [/* 16 vars */]) = 0 brk(0) = 0x7a4000 old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2b938000 uname({sys="Linux", node="phrixos", ...}) = 0 access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) open("/etc/ld.so.cache", O_RDONLY) = 3 fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2b93c000 close(3) = 0 access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) open("/lib/libc.so.6", O_RDONLY) = 3 read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 lseek(3, 760, SEEK_SET) = 760 read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2b948000 mprotect(0x2baac000, 49152, PROT_NONE) = 0 old_mmap(0x2bab8000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bab8000 old_mmap(0x2bac8000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bac8000 close(3) = 0 set_thread_area(0x2b940ad0) = 0 mprotect(0x2bab8000, 49152, PROT_READ) = 0 munmap(0x2b93c000, 16547) = 0 personality(0xffffffff /* PER_??? */) = 0 personality(0x40000 /* PER_??? */) = 0 personality(0xffffffff /* PER_??? */) = 262144 execve("./f", ["./f"], [/* 17 vars */]) = 0 brk(0) = 0x670000 old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2ba70000 uname({sys="Linux", node="phrixos", ...}) = 0 access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) open("/etc/ld.so.cache", O_RDONLY) = 3 fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2ba74000 close(3) = 0 access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) open("/lib/libc.so.6", O_RDONLY) = 3 read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 lseek(3, 760, SEEK_SET) = 760 read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2ba80000 mprotect(0x2bbe4000, 49152, PROT_NONE) = 0 old_mmap(0x2bbf0000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bbf0000 old_mmap(0x2bc00000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bc00000 close(3) = 0 set_thread_area(0x2ba78ad0) = 0 mprotect(0x2bbf0000, 49152, PROT_READ) = 0 munmap(0x2ba74000, 16547) = 0 personality(0xffffffff /* PER_??? */) = 0 brk(0) = 0x670000 brk(0x694000) = 0x694000 open("conftest1", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3 fstat64(3, {st_mode=S_IFREG|0644, st_size=0, ...}) = 0 old_mmap(NULL, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2bc04000 write(3, "6897664", 7) = 7 exit_group(0) = ? ============================================================================= uname -a ============================================================================= Linux phrixos 2.6.36-rc6-loongson-2f #1 Mon Oct 4 20:36:22 UTC 2010 mips64 GNU/Linux ============================================================================= /proc/cpuinfo ============================================================================= system type : lemote-fuloong-2f-box processor : 0 cpu model : ICT Loongson-2 V0.3 FPU V0.1 BogoMIPS : 528.38 wait instruction : yes microsecond timers : yes tlb_entries : 64 extra interrupt vector : no hardware watchpoint : yes, count: 0, address/irw mask: [] ASEs implemented : shadow register sets : 1 core : 0 VCED exceptions : not available VCEI exceptions : not available ============================================================================= Take care, -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: mips and ADDR_NO_RANDOMIZE 2010-11-01 16:24 ` mips and ADDR_NO_RANDOMIZE Camm Maguire @ 2010-11-01 18:06 ` David Daney 2010-11-01 18:24 ` Camm Maguire 0 siblings, 1 reply; 21+ messages in thread From: David Daney @ 2010-11-01 18:06 UTC (permalink / raw) To: Camm Maguire Cc: Maciej W. Rozycki, debian-mips, gcl-devel, Andreas Barth, linux-mips On 11/01/2010 09:24 AM, Camm Maguire wrote: > Greetings! Executing personality() with the ADDR_NO_RANDOMIZE bit set, > and re-executing via execve, should yield a process with traditional > contiguous brk() addresses appended to the .data segment, independent > of the setting of sysctl kernel.randomize_va_space, right? At least > this is the way the linux kernel has been working on x86 for many > years. > > The latest Debian mips kernel is not honoring this setting. I'd like > to know if this is a kernel bug. > For things like this, we need to know what kind of kernel it is. Is it a 64-bit kernel running a 32-bit application? I am going to guess that it is. The 32-bit sys_personality wrapper in the kernel looks incorrect. But It should probably still work, to set ADDR_NO_RANDOMIZE, so I don't really know where it is going off track yet. Having implemented the randomization, I would like to see it work correctly, so I guess I will look at it. You seem to have a certain knack for uncovering obscure bugs. David Daney > ============================================================================= > h/unrandomize.h > ============================================================================= > #include<sys/personality.h> > #include<syscall.h> > #include<unistd.h> > #include<alloca.h> > #include<errno.h> > > > { > errno=0; > > { > > long pers = personality(0xffffffffUL); > if (pers==-1) {printf("personality failure %d\n",errno);exit(-1);} > if (!(pers& ADDR_NO_RANDOMIZE)&& !getenv("GCL_UNRANDOMIZE")) { > errno=0; > if (personality(pers | ADDR_NO_RANDOMIZE) != -1&& personality(0xffffffffUL)& ADDR_NO_RANDOMIZE) { > int i; > char **n; > for (i=0;envp[i];i++); > n=alloca((i+2)*sizeof(*n)); > n[i+1]=0; > n[i--]="GCL_UNRANDOMIZE=t"; > for (;i>=0;i--) > n[i]=envp[i]; > #ifdef GCL_GPROF > gprof_cleanup(); > #endif > errno=0; > execve(*argv,argv,n); > printf("execve failure %d\n",errno); > exit(-1); > } else { > printf("personality change failure %d\n",errno); > exit(-1); > } > } > } > } > ============================================================================= > f.c > ============================================================================= > #include<stdio.h> > void gprof_cleanup() {}; > int main(int argc,char * argv[],char * envp[]) { > FILE *f; > > #include "h/unrandomize.h" > > if (!(f=fopen("conftest1","w"))) return -1; > fprintf(f,"%u",sbrk(0)); > return 0;} > ============================================================================= > ./f&& cat conftest1&& echo&& ./f&& cat conftest1 > 10043392 > 10584064 > ============================================================================= > strace -f ./f > ============================================================================= > execve("./f", ["./f"], [/* 16 vars */]) = 0 > brk(0) = 0x7a4000 > old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2b938000 > uname({sys="Linux", node="phrixos", ...}) = 0 > access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) > access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) > open("/etc/ld.so.cache", O_RDONLY) = 3 > fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 > old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2b93c000 > close(3) = 0 > access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) > open("/lib/libc.so.6", O_RDONLY) = 3 > read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 > lseek(3, 760, SEEK_SET) = 760 > read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 > fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 > old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2b948000 > mprotect(0x2baac000, 49152, PROT_NONE) = 0 > old_mmap(0x2bab8000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bab8000 > old_mmap(0x2bac8000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bac8000 > close(3) = 0 > set_thread_area(0x2b940ad0) = 0 > mprotect(0x2bab8000, 49152, PROT_READ) = 0 > munmap(0x2b93c000, 16547) = 0 > personality(0xffffffff /* PER_??? */) = 0 > personality(0x40000 /* PER_??? */) = 0 > personality(0xffffffff /* PER_??? */) = 262144 > execve("./f", ["./f"], [/* 17 vars */]) = 0 > brk(0) = 0x670000 > old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2ba70000 > uname({sys="Linux", node="phrixos", ...}) = 0 > access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) > access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) > open("/etc/ld.so.cache", O_RDONLY) = 3 > fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 > old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2ba74000 > close(3) = 0 > access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) > open("/lib/libc.so.6", O_RDONLY) = 3 > read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 > lseek(3, 760, SEEK_SET) = 760 > read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 > fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 > old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2ba80000 > mprotect(0x2bbe4000, 49152, PROT_NONE) = 0 > old_mmap(0x2bbf0000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bbf0000 > old_mmap(0x2bc00000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bc00000 > close(3) = 0 > set_thread_area(0x2ba78ad0) = 0 > mprotect(0x2bbf0000, 49152, PROT_READ) = 0 > munmap(0x2ba74000, 16547) = 0 > personality(0xffffffff /* PER_??? */) = 0 > brk(0) = 0x670000 > brk(0x694000) = 0x694000 > open("conftest1", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3 > fstat64(3, {st_mode=S_IFREG|0644, st_size=0, ...}) = 0 > old_mmap(NULL, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2bc04000 > write(3, "6897664", 7) = 7 > exit_group(0) = ? > ============================================================================= > uname -a > ============================================================================= > Linux phrixos 2.6.36-rc6-loongson-2f #1 Mon Oct 4 20:36:22 UTC 2010 > mips64 GNU/Linux > ============================================================================= > /proc/cpuinfo > ============================================================================= > system type : lemote-fuloong-2f-box > processor : 0 > cpu model : ICT Loongson-2 V0.3 FPU V0.1 > BogoMIPS : 528.38 > wait instruction : yes > microsecond timers : yes > tlb_entries : 64 > extra interrupt vector : no > hardware watchpoint : yes, count: 0, address/irw mask: [] > ASEs implemented : > shadow register sets : 1 > core : 0 > VCED exceptions : not available > VCEI exceptions : not available > ============================================================================= > > Take care, ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: mips and ADDR_NO_RANDOMIZE 2010-11-01 18:06 ` David Daney @ 2010-11-01 18:24 ` Camm Maguire 0 siblings, 0 replies; 21+ messages in thread From: Camm Maguire @ 2010-11-01 18:24 UTC (permalink / raw) To: David Daney Cc: Maciej W. Rozycki, debian-mips, gcl-devel, Andreas Barth, linux-mips Greetings! David Daney <ddaney@caviumnetworks.com> writes: > On 11/01/2010 09:24 AM, Camm Maguire wrote: >> Greetings! Executing personality() with the ADDR_NO_RANDOMIZE bit set, >> and re-executing via execve, should yield a process with traditional >> contiguous brk() addresses appended to the .data segment, independent >> of the setting of sysctl kernel.randomize_va_space, right? At least >> this is the way the linux kernel has been working on x86 for many >> years. >> >> The latest Debian mips kernel is not honoring this setting. I'd like >> to know if this is a kernel bug. >> > > For things like this, we need to know what kind of kernel it is. Is > it a 64-bit kernel running a 32-bit application? > The kernel is Debian 2.6.36-rc6-loongson-2f. Does this suffice? > I am going to guess that it is. > > The 32-bit sys_personality wrapper in the kernel looks incorrect. But > It should probably still work, to set ADDR_NO_RANDOMIZE, so I don't > really know where it is going off track yet. > > Having implemented the randomization, I would like to see it work > correctly, so I guess I will look at it. > Thanks so much! > You seem to have a certain knack for uncovering obscure bugs. > :-) Take care, > David Daney > >> ============================================================================= >> h/unrandomize.h >> ============================================================================= >> #include<sys/personality.h> >> #include<syscall.h> >> #include<unistd.h> >> #include<alloca.h> >> #include<errno.h> >> >> >> { >> errno=0; >> >> { >> >> long pers = personality(0xffffffffUL); >> if (pers==-1) {printf("personality failure %d\n",errno);exit(-1);} >> if (!(pers& ADDR_NO_RANDOMIZE)&& !getenv("GCL_UNRANDOMIZE")) { >> errno=0; >> if (personality(pers | ADDR_NO_RANDOMIZE) != -1&& personality(0xffffffffUL)& ADDR_NO_RANDOMIZE) { >> int i; >> char **n; >> for (i=0;envp[i];i++); >> n=alloca((i+2)*sizeof(*n)); >> n[i+1]=0; >> n[i--]="GCL_UNRANDOMIZE=t"; >> for (;i>=0;i--) >> n[i]=envp[i]; >> #ifdef GCL_GPROF >> gprof_cleanup(); >> #endif >> errno=0; >> execve(*argv,argv,n); >> printf("execve failure %d\n",errno); >> exit(-1); >> } else { >> printf("personality change failure %d\n",errno); >> exit(-1); >> } >> } >> } >> } >> ============================================================================= >> f.c >> ============================================================================= >> #include<stdio.h> >> void gprof_cleanup() {}; >> int main(int argc,char * argv[],char * envp[]) { >> FILE *f; >> >> #include "h/unrandomize.h" >> >> if (!(f=fopen("conftest1","w"))) return -1; >> fprintf(f,"%u",sbrk(0)); >> return 0;} >> ============================================================================= >> ./f&& cat conftest1&& echo&& ./f&& cat conftest1 >> 10043392 >> 10584064 >> ============================================================================= >> strace -f ./f >> ============================================================================= >> execve("./f", ["./f"], [/* 16 vars */]) = 0 >> brk(0) = 0x7a4000 >> old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2b938000 >> uname({sys="Linux", node="phrixos", ...}) = 0 >> access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) >> access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) >> open("/etc/ld.so.cache", O_RDONLY) = 3 >> fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 >> old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2b93c000 >> close(3) = 0 >> access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) >> open("/lib/libc.so.6", O_RDONLY) = 3 >> read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 >> lseek(3, 760, SEEK_SET) = 760 >> read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 >> fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 >> old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2b948000 >> mprotect(0x2baac000, 49152, PROT_NONE) = 0 >> old_mmap(0x2bab8000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bab8000 >> old_mmap(0x2bac8000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bac8000 >> close(3) = 0 >> set_thread_area(0x2b940ad0) = 0 >> mprotect(0x2bab8000, 49152, PROT_READ) = 0 >> munmap(0x2b93c000, 16547) = 0 >> personality(0xffffffff /* PER_??? */) = 0 >> personality(0x40000 /* PER_??? */) = 0 >> personality(0xffffffff /* PER_??? */) = 262144 >> execve("./f", ["./f"], [/* 17 vars */]) = 0 >> brk(0) = 0x670000 >> old_mmap(NULL, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2ba70000 >> uname({sys="Linux", node="phrixos", ...}) = 0 >> access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) >> access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) >> open("/etc/ld.so.cache", O_RDONLY) = 3 >> fstat64(3, {st_mode=S_IFREG|0644, st_size=16547, ...}) = 0 >> old_mmap(NULL, 16547, PROT_READ, MAP_PRIVATE, 3, 0) = 0x2ba74000 >> close(3) = 0 >> access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory) >> open("/lib/libc.so.6", O_RDONLY) = 3 >> read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\10\0\1\0\0\0\24s\1\0004\0\0\0"..., 512) = 512 >> lseek(3, 760, SEEK_SET) = 760 >> read(3, "\4\0\0\0\20\0\0\0\1\0\0\0GNU\0\0\0\0\0\2\0\0\0\6\0\0\0\22\0\0\0", 32) = 32 >> fstat64(3, {st_mode=S_IFREG|0755, st_size=1594664, ...}) = 0 >> old_mmap(NULL, 1576560, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x2ba80000 >> mprotect(0x2bbe4000, 49152, PROT_NONE) = 0 >> old_mmap(0x2bbf0000, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x160000) = 0x2bbf0000 >> old_mmap(0x2bc00000, 3696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x2bc00000 >> close(3) = 0 >> set_thread_area(0x2ba78ad0) = 0 >> mprotect(0x2bbf0000, 49152, PROT_READ) = 0 >> munmap(0x2ba74000, 16547) = 0 >> personality(0xffffffff /* PER_??? */) = 0 >> brk(0) = 0x670000 >> brk(0x694000) = 0x694000 >> open("conftest1", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3 >> fstat64(3, {st_mode=S_IFREG|0644, st_size=0, ...}) = 0 >> old_mmap(NULL, 65536, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2bc04000 >> write(3, "6897664", 7) = 7 >> exit_group(0) = ? >> ============================================================================= >> uname -a >> ============================================================================= >> Linux phrixos 2.6.36-rc6-loongson-2f #1 Mon Oct 4 20:36:22 UTC 2010 >> mips64 GNU/Linux >> ============================================================================= >> /proc/cpuinfo >> ============================================================================= >> system type : lemote-fuloong-2f-box >> processor : 0 >> cpu model : ICT Loongson-2 V0.3 FPU V0.1 >> BogoMIPS : 528.38 >> wait instruction : yes >> microsecond timers : yes >> tlb_entries : 64 >> extra interrupt vector : no >> hardware watchpoint : yes, count: 0, address/irw mask: [] >> ASEs implemented : >> shadow register sets : 1 >> core : 0 >> VCED exceptions : not available >> VCEI exceptions : not available >> ============================================================================= >> >> Take care, > > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: gdb for mips64 2010-10-25 21:45 ` David Daney 2010-10-26 12:47 ` Maciej W. Rozycki @ 2010-10-26 14:47 ` Camm Maguire 2010-10-26 20:12 ` [Gcl-devel] " Camm Maguire 1 sibling, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-26 14:47 UTC (permalink / raw) To: David Daney; +Cc: debian-mips, Frederick Isaac, gcl-devel, linux-mips Greetings! David Daney <ddaney@caviumnetworks.com> writes: > On 10/25/2010 02:32 PM, Camm Maguire wrote: >> Greetings! Can gdb be made to work on mips64? >> > > You have to have a 64-bit toolchain. > > Then something like this (untested): > > CC='mips64-linux-gnu -mabi=64' configure --host=mips64-linux > --target=mips64-linux. > > I don't think a 32-bit gdb can debug 64-bit processes :-(. > Thanks. Why doesn't _IO_getc get a stub on mips64, like say _setjmp? readelf -a saved_ansi_gcl |grep IO_getc 2812: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@GLIBC_2.0 (2) 15315: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@@GLIBC_2.0 readelf -a saved_ansi_gcl |grep setjmp 2159: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@GLIBC_2.0 (2) 15978: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@@GLIBC_2.0 Is there anything I can do about this? Take care, > David Daney > > >> (gdb) r >> Starting program: /home/camm/gcl-2.6.8pre/unixport/saved_pre_gcl >> /home/wingsun/develop/build/gdb/gdb-6.8/gdb/mips-tdep.c:603: internal-error: bad register size >> A problem internal to GDB has been detected, >> further debugging may prove unreliable. >> >> Take care, > > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-26 14:47 ` gdb for mips64 Camm Maguire @ 2010-10-26 20:12 ` Camm Maguire 2010-10-28 10:50 ` Maciej W. Rozycki 0 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-26 20:12 UTC (permalink / raw) To: David Daney; +Cc: linux-mips, debian-mips, gcl-devel Greetings! Camm Maguire <camm@maguirefamily.org> writes: > Thanks. > > Why doesn't _IO_getc get a stub on mips64, like say _setjmp? > > readelf -a saved_ansi_gcl |grep IO_getc > 2812: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@GLIBC_2.0 (2) > 15315: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@@GLIBC_2.0 > readelf -a saved_ansi_gcl |grep setjmp > 2159: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@GLIBC_2.0 (2) > 15978: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@@GLIBC_2.0 > > Is there anything I can do about this? > A little more info here. Latest toolchain on the gcc compile farm does provide a stub, but the slightly older gentoo on a sicortex machine does not. Clearly not too much to worry about unless you might know of an easy workaround. Take care, -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-26 20:12 ` [Gcl-devel] " Camm Maguire @ 2010-10-28 10:50 ` Maciej W. Rozycki 2010-10-28 21:28 ` Camm Maguire 0 siblings, 1 reply; 21+ messages in thread From: Maciej W. Rozycki @ 2010-10-28 10:50 UTC (permalink / raw) To: Camm Maguire; +Cc: David Daney, linux-mips, debian-mips, gcl-devel On Tue, 26 Oct 2010, Camm Maguire wrote: > > Why doesn't _IO_getc get a stub on mips64, like say _setjmp? > > > > readelf -a saved_ansi_gcl |grep IO_getc > > 2812: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@GLIBC_2.0 (2) > > 15315: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@@GLIBC_2.0 > > readelf -a saved_ansi_gcl |grep setjmp > > 2159: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@GLIBC_2.0 (2) > > 15978: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@@GLIBC_2.0 > > > > Is there anything I can do about this? > > > > A little more info here. Latest toolchain on the gcc compile farm > does provide a stub, but the slightly older gentoo on a sicortex > machine does not. Clearly not too much to worry about unless you > might know of an easy workaround. Can you quote what `ld --version' says on the affected system? It *might* be a linker bug, though the exact circumstances may be complicated as I have n64 MIPS64 binaries as old as from mid 2005 with a stub for _IO_getc() correctly installed. Nobody should be using any older binutils, especially with the MIPS64 target as 64-bit support for MIPS was quite immature back then. I suggest that you switch to binutils 2.20.1; version 2.21 is due out in a couple of weeks too. A legitimate cause for a stub to be omitted by the linker are pointer references to the function in question as in this case the symbol has to be fully resolved for pointer comparison to produce reliable results. It could be that one version of GCC produces code that looks to the linker as if referring to the symbol this way (i.e. the object files presented to the linker contain relocations normally used for data references rather than function calls associated with the symbol in question). You can determine if that is the case by running `objdump -r' on the program's object files used in the final link and checking if there are any GOT relocations (that'll be a part of their names, e.g. R_MIPS_GOT_PAGE) against _IO_getc. Again, that *might* be a GCC bug then. That said the only impact from a missing stub is a small program startup performance penalty as lazy binding cannot be applied to this single symbol only and the symbol has to be fully resolved at startup. Maciej ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-28 10:50 ` Maciej W. Rozycki @ 2010-10-28 21:28 ` Camm Maguire 2010-10-29 7:47 ` Maciej W. Rozycki 0 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-28 21:28 UTC (permalink / raw) To: Maciej W. Rozycki; +Cc: David Daney, linux-mips, debian-mips, gcl-devel "Maciej W. Rozycki" <macro@linux-mips.org> writes: > On Tue, 26 Oct 2010, Camm Maguire wrote: > >> > Why doesn't _IO_getc get a stub on mips64, like say _setjmp? >> > >> > readelf -a saved_ansi_gcl |grep IO_getc >> > 2812: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@GLIBC_2.0 (2) >> > 15315: 0000000000000000 472 FUNC GLOBAL DEFAULT UND _IO_getc@@GLIBC_2.0 >> > readelf -a saved_ansi_gcl |grep setjmp >> > 2159: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@GLIBC_2.0 (2) >> > 15978: 00000001204b9b40 32 FUNC GLOBAL DEFAULT UND _setjmp@@GLIBC_2.0 >> > >> > Is there anything I can do about this? >> > >> >> A little more info here. Latest toolchain on the gcc compile farm >> does provide a stub, but the slightly older gentoo on a sicortex >> machine does not. Clearly not too much to worry about unless you >> might know of an easy workaround. > > Can you quote what `ld --version' says on the affected system? > ld --version GNU ld (GNU Binutils) 2.18 Copyright 2007 Free Software Foundation, Inc. This program is free software; you may redistribute it under the terms of the GNU General Public License version 3 or (at your option) a later version. This program has absolutely no warranty. > It *might* be a linker bug, though the exact circumstances may be > complicated as I have n64 MIPS64 binaries as old as from mid 2005 with a > stub for _IO_getc() correctly installed. Nobody should be using any older > binutils, especially with the MIPS64 target as 64-bit support for MIPS was > quite immature back then. I suggest that you switch to binutils 2.20.1; > version 2.21 is due out in a couple of weeks too. > > A legitimate cause for a stub to be omitted by the linker are pointer > references to the function in question as in this case the symbol has to > be fully resolved for pointer comparison to produce reliable results. It > could be that one version of GCC produces code that looks to the linker as > if referring to the symbol this way (i.e. the object files presented to > the linker contain relocations normally used for data references rather > than function calls associated with the symbol in question). You can > determine if that is the case by running `objdump -r' on the program's > object files used in the final link and checking if there are any GOT > relocations (that'll be a part of their names, e.g. R_MIPS_GOT_PAGE) > against _IO_getc. Again, that *might* be a GCC bug then. Yep: File: gcl_readline.o 0000000000000928 R_MIPS_GOT_DISP _IO_getc int rl_getc_em(FILE *f) { static char *line = NULL; static int linepos = 0; int r; if (f!=stdin || !isatty(fileno(f)) ) return getc(f); .... > > That said the only impact from a missing stub is a small program startup > performance penalty as lazy binding cannot be applied to this single > symbol only and the symbol has to be fully resolved at startup. > This comment was very helpful. I had implemented a stub at the end of each loaded .o file to read the main stub, discern the got entry, read it, and jump. Now I skip the stub reading step and use the gotsym and locgotno from the .dynamic section and the dyn_symtab entries to compute the got offset. I can now handle symbols with 0 initial value. Thanks so much! > Maciej > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-28 21:28 ` Camm Maguire @ 2010-10-29 7:47 ` Maciej W. Rozycki 2010-10-29 15:52 ` Camm Maguire 0 siblings, 1 reply; 21+ messages in thread From: Maciej W. Rozycki @ 2010-10-29 7:47 UTC (permalink / raw) To: Camm Maguire; +Cc: David Daney, linux-mips, debian-mips, gcl-devel On Thu, 28 Oct 2010, Camm Maguire wrote: > > Can you quote what `ld --version' says on the affected system? > > > > ld --version > GNU ld (GNU Binutils) 2.18 > Copyright 2007 Free Software Foundation, Inc. > This program is free software; you may redistribute it under the terms of > the GNU General Public License version 3 or (at your option) a later version. > This program has absolutely no warranty. OK, they should be good I believe, as should be any version newer than 2.16-ish (I'd have to get at the ChangeLogs to recall exactly when usable support for the new ABIs went in), but I suggest an upgrade to the current version at your convenience anyway. > > A legitimate cause for a stub to be omitted by the linker are pointer > > references to the function in question as in this case the symbol has to > > be fully resolved for pointer comparison to produce reliable results. It > > could be that one version of GCC produces code that looks to the linker as > > if referring to the symbol this way (i.e. the object files presented to > > the linker contain relocations normally used for data references rather > > than function calls associated with the symbol in question). You can > > determine if that is the case by running `objdump -r' on the program's > > object files used in the final link and checking if there are any GOT > > relocations (that'll be a part of their names, e.g. R_MIPS_GOT_PAGE) > > against _IO_getc. Again, that *might* be a GCC bug then. > > Yep: > > File: gcl_readline.o > 0000000000000928 R_MIPS_GOT_DISP _IO_getc > > int rl_getc_em(FILE *f) { > static char *line = NULL; > static int linepos = 0; > int r; > > if (f!=stdin || !isatty(fileno(f)) ) return getc(f); > .... OK, so that does look like a problem with GCC as this piece of code only takes the address of getc() (that is #defined to _IO_getc() in <stdio.h>) for the purpose of making a function call. An R_MIPS_CALL16 relocation should therefore be used here instead. Would you care to quote the GCC version causing this and get an assembly output of the surrounding code (say +/-5 instructions from the relocation), preferably one generated by GCC along the lines of: $ gcc -S -dp <other_options_needed_here> gcl_readline.c (you can just copy and paste the invocation line quoted by `make' and substitute "-c" for "-S -dp" (and gcl_readline.o for gcl_readline.s, if applicable) leaving the rest of options intact), but if that turns out too difficult, then: $ objdump -dr gcl_readline.o might be good enough. > > That said the only impact from a missing stub is a small program startup > > performance penalty as lazy binding cannot be applied to this single > > symbol only and the symbol has to be fully resolved at startup. > > > > This comment was very helpful. I had implemented a stub at the end of > each loaded .o file to read the main stub, discern the got entry, read > it, and jump. Now I skip the stub reading step and use the gotsym and > locgotno from the .dynamic section and the dyn_symtab entries to > compute the got offset. I can now handle symbols with 0 initial > value. Hmm, what you're doing sounds odd to me -- are you trying to gather some sort of statistics about lazy binding calls or what? There may be functionality to cover this kind of processing already available in ld.so. Also once the program has been loaded the dynamic linker will have already resolved any strong symbol references and you shouldn't be seeing any that still has a null value (that does not apply to weak references that may remain unsatisfied). Also note that if you're doing stuff manually like this, then you may have to take the GOT model used (traditional GOT, xGOT, multi-GOT) into account. > Thanks so much! You are welcome! Maciej ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-29 7:47 ` Maciej W. Rozycki @ 2010-10-29 15:52 ` Camm Maguire 2010-10-30 12:39 ` Maciej W. Rozycki 0 siblings, 1 reply; 21+ messages in thread From: Camm Maguire @ 2010-10-29 15:52 UTC (permalink / raw) To: Maciej W. Rozycki; +Cc: David Daney, linux-mips, debian-mips, gcl-devel [-- Attachment #1: Type: text/plain, Size: 5685 bytes --] Greetings! "Maciej W. Rozycki" <macro@linux-mips.org> writes: > On Thu, 28 Oct 2010, Camm Maguire wrote: > >> > Can you quote what `ld --version' says on the affected system? >> > >> >> ld --version >> GNU ld (GNU Binutils) 2.18 >> Copyright 2007 Free Software Foundation, Inc. >> This program is free software; you may redistribute it under the terms of >> the GNU General Public License version 3 or (at your option) a later version. >> This program has absolutely no warranty. > > OK, they should be good I believe, as should be any version newer than > 2.16-ish (I'd have to get at the ChangeLogs to recall exactly when usable > support for the new ABIs went in), but I suggest an upgrade to the current > version at your convenience anyway. OK, this isn't my machine, but good to know. > >> > A legitimate cause for a stub to be omitted by the linker are pointer >> > references to the function in question as in this case the symbol has to >> > be fully resolved for pointer comparison to produce reliable results. It >> > could be that one version of GCC produces code that looks to the linker as >> > if referring to the symbol this way (i.e. the object files presented to >> > the linker contain relocations normally used for data references rather >> > than function calls associated with the symbol in question). You can >> > determine if that is the case by running `objdump -r' on the program's >> > object files used in the final link and checking if there are any GOT >> > relocations (that'll be a part of their names, e.g. R_MIPS_GOT_PAGE) >> > against _IO_getc. Again, that *might* be a GCC bug then. >> >> Yep: >> >> File: gcl_readline.o >> 0000000000000928 R_MIPS_GOT_DISP _IO_getc >> >> int rl_getc_em(FILE *f) { >> static char *line = NULL; >> static int linepos = 0; >> int r; >> >> if (f!=stdin || !isatty(fileno(f)) ) return getc(f); >> .... > > OK, so that does look like a problem with GCC as this piece of code only > takes the address of getc() (that is #defined to _IO_getc() in <stdio.h>) > for the purpose of making a function call. An R_MIPS_CALL16 relocation > should therefore be used here instead. > > Would you care to quote the GCC version causing this and get an assembly > output of the surrounding code (say +/-5 instructions from the > relocation), preferably one generated by GCC along the lines of: > > $ gcc -S -dp <other_options_needed_here> gcl_readline.c > > (you can just copy and paste the invocation line quoted by `make' and > substitute "-c" for "-S -dp" (and gcl_readline.o for gcl_readline.s, if > applicable) leaving the rest of options intact), but if that turns out too > difficult, then: > > $ objdump -dr gcl_readline.o > > might be good enough. > OK see attachment below. >> > That said the only impact from a missing stub is a small program startup >> > performance penalty as lazy binding cannot be applied to this single >> > symbol only and the symbol has to be fully resolved at startup. >> > >> >> This comment was very helpful. I had implemented a stub at the end of >> each loaded .o file to read the main stub, discern the got entry, read >> it, and jump. Now I skip the stub reading step and use the gotsym and >> locgotno from the .dynamic section and the dyn_symtab entries to >> compute the got offset. I can now handle symbols with 0 initial >> value. > > Hmm, what you're doing sounds odd to me -- are you trying to gather some > sort of statistics about lazy binding calls or what? There may be > functionality to cover this kind of processing already available in ld.so. > Also once the program has been loaded the dynamic linker will have already > resolved any strong symbol references and you shouldn't be seeing any that > still has a null value (that does not apply to weak references that may > remain unsatisfied). > Its simple but rather unconventional. GCL is a lisp system. It loads compiled object files at runtime into memory, and executes therefrom. It can then save the expanded memory image to disk via unexec for later execution on the same or different machines. Compiled code can reference symbols in external shared libraries. These must be directed toward some trampoline in the initial final-linked executable, as otherwise the address loaded might not be valid in a later execution. On mips, GCL adds a little stub to load the global got address from a local got table appended to the .o file, then to load the contents of this address, and then jump. GCL ensures that LD_BIND_NOW is set at runtime via pushing the environment and execve() on startup. On other systems, where .plt entries are available, GCL sets the address to the .plt which takes care of everything. This is much cleaner as it requires no little machine-specific assembly. In the cvs version of GCL, such external calls are made through a C pointer, which is redirected at startup to the correct address via dlsym(). A little faster, and makes the loader a little simpler. We tried to do this via bfd_get_relocated_section_contents, but the coverage here was very spotty. > Also note that if you're doing stuff manually like this, then you may > have to take the GOT model used (traditional GOT, xGOT, multi-GOT) into > account. > Thankfully thus far this has not proved necessary. But ia64 and hppa are the only targets yet unimplemented, so who knows. Take care, >> Thanks so much! > > You are welcome! > > Maciej > > > > -- Camm Maguire camm@maguirefamily.org ========================================================================== "The earth is but one country, and mankind its citizens." -- Baha'u'llah [-- Attachment #2: att --] [-- Type: application/octet-stream, Size: 44120 bytes --] # gcc -S -dp -mips3 -mabi=64 -Wall -DVOL=volatile -fsigned-char -pipe -fPIC -O3 -fomit-frame-pointer -I/rootl/usr/local/downloads/gcln1/o -I../h -I../gcl-tk gcl_readline.c </local/downloads/gcln1/o -I../h -I../gcl-tk gcl_readline.c # ls -lrt |tail ls -lrt |tail -rw-r--r-- 1 root root 40834 Oct 28 10:52 new_init.c -rw-r--r-- 1 root root 73104 Oct 28 10:52 new_init.o -rw-r--r-- 1 root root 7768 Oct 28 10:52 gcllib.a -rw-r--r-- 1 root root 168368 Oct 28 10:52 cmpinclude.h -rw-r--r-- 1 root root 25608 Oct 28 17:56 sfasl.o -rw-r--r-- 1 freddy freddy 12448 Oct 29 12:15 gcl_readline.d -rw-r--r-- 1 root root 60 Oct 29 12:15 gcl_readline.ini -rw-r--r-- 1 root root 12760 Oct 29 12:15 gcl_readline.o -rw-r--r-- 1 root root 12501 Oct 29 12:15 gcl_readline.c -rw-r--r-- 1 root root 41579 Oct 29 12:16 gcl_readline.s # objdump -r gcl_readline.o |grep IO_getc objdump -r gcl_readline.o |grep IO_getc 0000000000000928 R_MIPS_GOT_DISP _IO_getc # cat gcl_readline.s cat gcl_readline.s .file 1 "gcl_readline.c" .section .mdebug.abi64 .previous .abicalls .text .align 2 .align 3 .ent siLreadline_off .type siLreadline_off, @function siLreadline_off: .frame $sp,0,$31 # vars= 0, regs= 0/0, args= 0, gp= 0 .mask 0x00000000,0 .fmask 0x00000000,0 .set noreorder .set nomacro lui $3,%hi(%neg(%gp_rel(siLreadline_off))) # 30 *movdi_64bit/2 [length = 4] daddu $3,$3,$25 # 31 *adddi3/1 [length = 4] daddiu $3,$3,%lo(%neg(%gp_rel(siLreadline_off))) # 32 *lowdi [length = 4] ld $2,%got_disp(readline_on)($3) # 24 load_gotdi [length = 4] j $31 # 28 return [length = 4] sw $0,0($2) # 12 *movsi_internal/5 [length = 4] .set macro .set reorder .end siLreadline_off .section .rodata.str1.8,"aMS",@progbits,1 .align 3 .LC0: .ascii "TERM\000" .align 3 .LC1: .ascii "GCL\000" .align 3 .LC2: .ascii "dumb\000" .align 3 .LC3: .ascii "READLINE-ON\000" .align 3 .LC4: .ascii "READLINE-OFF\000" .text .align 2 .align 3 .globl gcl_init_readline_function .ent gcl_init_readline_function .type gcl_init_readline_function, @function gcl_init_readline_function: .frame $sp,32,$31 # vars= 0, regs= 4/0, args= 0, gp= 0 .mask 0x90030000,-8 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-32 # 112 *adddi3/2 [length = 4] sd $28,16($sp) # 114 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(gcl_init_readline_function))) # 131 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 132 *adddi3/1 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(gcl_init_readline_function))) # 133 *lowdi [length = 4] ld $4,%got_page(.LC0)($28) # 107 load_gotdi [length = 4] ld $25,%call16(getenv)($28) # 10 load_calldi [length = 4] sd $17,8($sp) # 115 *movdi_64bit/5 [length = 4] sd $16,0($sp) # 116 *movdi_64bit/5 [length = 4] sd $31,24($sp) # 113 *movdi_64bit/5 [length = 4] jal $25 # 11 call_value_internal/1 [length = 4] daddiu $4,$4,%got_ofst(.LC0) # 9 *lowdi [length = 4] move $16,$2 # 12 *movdi_64bit/1 [length = 4] ld $2,%got_page(.LC1)($28) # 108 load_gotdi [length = 4] ld $4,%got_disp(rl_readline_name)($28) # 109 load_gotdi [length = 4] ld $3,%got_page(rl_completion)($28) # 110 load_gotdi [length = 4] daddiu $2,$2,%got_ofst(.LC1) # 16 *lowdi [length = 4] sd $2,0($4) # 17 *movdi_64bit/5 [length = 4] ld $2,%got_disp(rl_attempted_completion_function)($28) # 111 load_gotdi [length = 4] ld $25,%call16(isatty)($28) # 25 load_calldi [length = 4] daddiu $3,$3,%got_ofst(rl_completion) # 93 *lowdi [length = 4] sd $3,0($2) # 22 *movdi_64bit/5 [length = 4] move $4,$0 # 24 *movdi_64bit/2 [length = 4] jal $25 # 26 call_value_internal/1 [length = 4] ld $17,%got_page(n.12486)($28) # 106 load_gotdi [length = 4] beq $2,$0,.L12 # 29 *branch_zerodi [length = 4] ld $4,%got_page(.LC3)($28) # 102 load_gotdi [length = 4] ld $5,%got_page(.LC2)($28) # 105 load_gotdi [length = 4] ld $25,%call16(strcmp)($28) # 38 load_calldi [length = 4] move $4,$16 # 35 *movdi_64bit/1 [length = 4] beq $16,$0,.L6 # 32 *branch_zerodi [length = 4] daddiu $5,$5,%got_ofst(.LC2) # 37 *lowdi [length = 4] jal $25 nop # 39 call_value_internal/1 [length = 8] bne $2,$0,.L13 # 41 *branch_zerodi [length = 4] ld $2,%got_disp(readline_on)($28) # 104 load_gotdi [length = 4] .align 3 .L4: ld $4,%got_page(.LC3)($28) # 102 load_gotdi [length = 4] .L12: ld $5,%got_page(siLreadline_on)($28) # 103 load_gotdi [length = 4] lw $2,%got_ofst(n.12486)($17) # 52 extendsidi2/2 [length = 4] ld $25,%call16(make_si_function_internal)($28) # 61 load_calldi [length = 4] daddiu $4,$4,%got_ofst(.LC3) # 58 *lowdi [length = 4] bne $2,$0,.L10 # 53 *branch_zerosi [length = 4] daddiu $5,$5,%got_ofst(siLreadline_on) # 60 *lowdi [length = 4] jal $25 nop # 62 call_value_internal/1 [length = 8] ld $4,%got_page(.LC4)($28) # 100 load_gotdi [length = 4] ld $5,%got_page(siLreadline_off)($28) # 101 load_gotdi [length = 4] ld $25,%call16(make_si_function_internal)($28) # 68 load_calldi [length = 4] daddiu $4,$4,%got_ofst(.LC4) # 65 *lowdi [length = 4] jal $25 # 69 call_value_internal/1 [length = 4] daddiu $5,$5,%got_ofst(siLreadline_off) # 67 *lowdi [length = 4] li $3,1 # 0x1 # 72 *movsi_internal/2 [length = 4] sw $3,%got_ofst(n.12486)($17) # 73 *movsi_internal/5 [length = 4] .L10: ld $31,24($sp) # 120 *movdi_64bit/4 [length = 4] ld $28,16($sp) # 121 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 122 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 123 *movdi_64bit/4 [length = 4] j $31 # 125 return_internal [length = 4] daddiu $sp,$sp,32 # 124 *adddi3/2 [length = 4] .align 3 .L6: ld $2,%got_disp(readline_on)($28) # 104 load_gotdi [length = 4] .L13: li $3,1 # 0x1 # 46 *movsi_internal/2 [length = 4] b .L4 # 134 jump [length = 4] sw $3,0($2) # 47 *movsi_internal/5 [length = 4] .set macro .set reorder .end gcl_init_readline_function .section .rodata.str1.8 .align 3 .LC5: .ascii "GCL is not being run from a terminal\000" .align 3 .LC6: .ascii "Controlling terminal is not readline capable\000" .text .align 2 .align 3 .ent siLreadline_on .type siLreadline_on, @function siLreadline_on: .frame $sp,16,$31 # vars= 0, regs= 2/0, args= 0, gp= 0 .mask 0x90000000,-8 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-16 # 84 *adddi3/2 [length = 4] sd $28,0($sp) # 86 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(siLreadline_on))) # 105 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 106 *adddi3/1 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(siLreadline_on))) # 107 *lowdi [length = 4] ld $25,%call16(isatty)($28) # 9 load_calldi [length = 4] sd $31,8($sp) # 85 *movdi_64bit/5 [length = 4] jal $25 # 10 call_value_internal/1 [length = 4] move $4,$0 # 8 *movdi_64bit/2 [length = 4] ld $4,%got_page(.LC0)($28) # 83 load_gotdi [length = 4] ld $25,%call16(getenv)($28) # 28 load_calldi [length = 4] move $5,$0 # 19 *movdi_64bit/2 [length = 4] bne $2,$0,.L15 # 13 *branch_zerodi [length = 4] daddiu $4,$4,%got_ofst(.LC0) # 27 *lowdi [length = 4] ld $4,%got_page(.LC5)($28) # 81 load_gotdi [length = 4] daddiu $4,$4,%got_ofst(.LC5) # 18 *lowdi [length = 4] .L22: ld $25,%got_disp(FEerror)($28) # 78 load_gotdi [length = 4] ld $28,0($sp) # 99 *movdi_64bit/4 [length = 4] ld $31,8($sp) # 98 *movdi_64bit/4 [length = 4] jr $25 # 49 sibcall_internal/1 [length = 4] daddiu $sp,$sp,16 # 100 *adddi3/2 [length = 4] .align 3 .L15: jal $25 nop # 29 call_value_internal/1 [length = 8] ld $5,%got_page(.LC2)($28) # 80 load_gotdi [length = 4] ld $25,%call16(strcmp)($28) # 38 load_calldi [length = 4] move $4,$2 # 35 *movdi_64bit/1 [length = 4] beq $2,$0,.L17 # 32 *branch_zerodi [length = 4] daddiu $5,$5,%got_ofst(.LC2) # 37 *lowdi [length = 4] jal $25 nop # 39 call_value_internal/1 [length = 8] ld $4,%got_page(.LC6)($28) # 79 load_gotdi [length = 4] move $5,$0 # 47 *movdi_64bit/2 [length = 4] beq $2,$0,.L22 # 41 *branch_zerodi [length = 4] daddiu $4,$4,%got_ofst(.LC6) # 46 *lowdi [length = 4] .L17: ld $2,%got_disp(readline_on)($28) # 77 load_gotdi [length = 4] li $3,1 # 0x1 # 55 *movsi_internal/2 [length = 4] sw $3,0($2) # 56 *movsi_internal/5 [length = 4] ld $31,8($sp) # 90 *movdi_64bit/4 [length = 4] ld $28,0($sp) # 91 *movdi_64bit/4 [length = 4] j $31 # 93 return_internal [length = 4] daddiu $sp,$sp,16 # 92 *adddi3/2 [length = 4] .set macro .set reorder .end siLreadline_on .align 2 .align 3 .ent rl_completion .type rl_completion, @function rl_completion: .frame $sp,0,$31 # vars= 0, regs= 0/0, args= 0, gp= 0 .mask 0x00000000,0 .fmask 0x00000000,0 .set noreorder .set nomacro lui $3,%hi(%neg(%gp_rel(rl_completion))) # 38 *movdi_64bit/2 [length = 4] daddu $3,$3,$25 # 39 *adddi3/1 [length = 4] daddiu $3,$3,%lo(%neg(%gp_rel(rl_completion))) # 40 *lowdi [length = 4] ld $5,%got_page(rl_completion_words_new)($3) # 34 load_gotdi [length = 4] ld $25,%got_disp(rl_completion_matches)($3) # 35 load_gotdi [length = 4] jr $25 # 16 sibcall_value_internal/1 [length = 4] daddiu $5,$5,%got_ofst(rl_completion_words_new) # 14 *lowdi [length = 4] .set macro .set reorder .end rl_completion .align 2 .align 3 .ent rl_completion_words_new .type rl_completion_words_new, @function rl_completion_words_new: .frame $sp,224,$31 # vars= 128, regs= 11/0, args= 0, gp= 0 .mask 0xd0ff0000,-16 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-224 # 739 *adddi3/2 [length = 4] sd $28,192($sp) # 742 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(rl_completion_words_new))) # 831 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 832 *adddi3/1 [length = 4] sd $20,160($sp) # 746 *movdi_64bit/5 [length = 4] sd $31,208($sp) # 740 *movdi_64bit/5 [length = 4] sd $fp,200($sp) # 741 *movdi_64bit/5 [length = 4] sd $23,184($sp) # 743 *movdi_64bit/5 [length = 4] sd $22,176($sp) # 744 *movdi_64bit/5 [length = 4] sd $21,168($sp) # 745 *movdi_64bit/5 [length = 4] sd $19,152($sp) # 747 *movdi_64bit/5 [length = 4] sd $18,144($sp) # 748 *movdi_64bit/5 [length = 4] sd $17,136($sp) # 749 *movdi_64bit/5 [length = 4] sd $16,128($sp) # 750 *movdi_64bit/5 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(rl_completion_words_new))) # 833 *lowdi [length = 4] bne $5,$0,.L26 # 10 *branch_zerodi [length = 4] move $20,$4 # 3 *movdi_64bit/1 [length = 4] ld $2,%got_disp(sSAreadline_prefixA)($28) # 738 load_gotdi [length = 4] ld $22,%got_page(pref.12253)($28) # 736 load_gotdi [length = 4] ld $21,%got_page(prefl.12245)($28) # 737 load_gotdi [length = 4] ld $3,0($2) # 21 *movdi_64bit/4 [length = 4] li $2,13 # 0xd # 661 *movsi_internal/2 [length = 4] sd $0,%got_ofst(pref.12253)($22) # 15 *movdi_64bit/5 [length = 4] ld $4,8($3) # 22 *movdi_64bit/4 [length = 4] sw $0,%got_ofst(prefl.12245)($21) # 18 *movsi_internal/5 [length = 4] lbu $3,0($4) # 23 *zero_extendqisi2/2 [length = 4] beq $3,$2,.L28 # 25 *branch_equalitysi [length = 4] move $17,$0 # 28 *movdi_64bit/2 [length = 4] move $18,$0 # 29 *movdi_64bit/2 [length = 4] .L30: ld $25,%call16(strchr)($28) # 81 load_calldi [length = 4] move $4,$20 # 79 *movdi_64bit/1 [length = 4] jal $25 # 82 call_value_internal/1 [length = 4] li $5,58 # 0x3a # 80 *movdi_64bit/2 [length = 4] beq $2,$0,.L35 # 86 *branch_zerodi [length = 4] move $19,$2 # 83 *movdi_64bit/1 [length = 4] move $4,$20 # 90 *movdi_64bit/1 [length = 4] move $17,$2 # 97 *movdi_64bit/1 [length = 4] sd $0,%got_ofst(pref.12253)($22) # 93 *movdi_64bit/5 [length = 4] sw $0,%got_ofst(prefl.12245)($21) # 96 *movsi_internal/5 [length = 4] .L37: beq $17,$4,.L91 # 122 *branch_equalitydi [length = 4] li $2,13 # 658 *movqi_internal/2 [length = 4] ld $25,%call16(find_package)($28) # 164 load_calldi [length = 4] dsubu $3,$17,$4 # 159 subdi3 [length = 4] sd $0,0($sp) # 149 *movdi_64bit/5 [length = 4] sb $2,0($sp) # 155 *movqi_internal/4 [length = 4] li $2,1 # 657 *movhi_internal/2 [length = 4] sd $0,16($sp) # 151 *movdi_64bit/5 [length = 4] sd $0,32($sp) # 153 *movdi_64bit/5 [length = 4] sd $4,24($sp) # 158 *movdi_64bit/5 [length = 4] sh $2,16($sp) # 157 *movhi_internal/4 [length = 4] sw $3,32($sp) # 160 truncdisi2/2 [length = 4] sd $0,8($sp) # 150 *movdi_64bit/5 [length = 4] jal $25 # 165 call_value_internal/1 [length = 4] move $4,$sp # 163 *movdi_64bit/1 [length = 4] .L88: ld $5,%got_page(package.12246)($28) # 730 load_gotdi [length = 4] move $16,$2 # 691 *movdi_64bit/1 [length = 4] beq $16,$0,.L92 # 174 *branch_zerodi [length = 4] sd $2,%got_ofst(package.12246)($5) # 168 *movdi_64bit/5 [length = 4] .L46: ld $3,%got_page(package.12246)($28) # 727 load_gotdi [length = 4] ld $2,32($16) # 185 *movdi_64bit/4 [length = 4] move $18,$0 # 191 *movdi_64bit/2 [length = 4] sd $16,%got_ofst(package.12246)($3) # 182 *movdi_64bit/5 [length = 4] ld $3,%got_page(use.12247)($28) # 728 load_gotdi [length = 4] beq $17,$0,.L50 # 188 *branch_zerodi [length = 4] sd $2,%got_ofst(use.12247)($3) # 186 *movdi_64bit/5 [length = 4] lb $2,1($17) # 196 *extendqisi2/2 [length = 4] xori $2,$2,0x3a # 197 *mips.md:2123/2 [length = 4] sltu $2,$2,1 # 200 *seq_si [length = 4] andi $18,$2,0x00ff # 201 *zero_extendqidi2/1 [length = 4] .L50: ld $2,%got_page(internal.12243)($28) # 725 load_gotdi [length = 4] ld $3,%got_page(ftext.12251)($28) # 726 load_gotdi [length = 4] daddiu $4,$19,1 # 213 *adddi3/2 [length = 4] sw $18,%got_ofst(internal.12243)($2) # 205 *movsi_internal/5 [length = 4] beq $19,$0,.L93 # 210 *branch_zerodi [length = 4] sd $20,%got_ofst(ftext.12251)($3) # 208 *movdi_64bit/5 [length = 4] .L53: lb $2,0($4) # 222 *extendqisi2/2 [length = 4] ld $3,%got_page(wtext.12252)($28) # 721 load_gotdi [length = 4] ld $25,%call16(strlen)($28) # 235 load_calldi [length = 4] xori $2,$2,0x3a # 594 *mips.md:2123/2 [length = 4] sltu $2,$2,1 # 595 *seq_si [length = 4] dsll $2,$2,32 # 719 *ashldi3 [length = 4] dsrl $2,$2,32 # 720 *lshrdi3 [length = 4] daddu $4,$4,$2 # 597 *adddi3/1 [length = 4] jal $25 # 236 call_value_internal/1 [length = 4] sd $4,%got_ofst(wtext.12252)($3) # 231 *movdi_64bit/5 [length = 4] ld $3,%got_page(len.12242)($28) # 722 load_gotdi [length = 4] sw $2,%got_ofst(len.12242)($3) # 238 truncdisi2/2 [length = 4] ld $2,%got_page(tp.12248)($28) # 723 load_gotdi [length = 4] sd $16,%got_ofst(tp.12248)($2) # 241 *movdi_64bit/5 [length = 4] ld $2,%got_page(i.12241)($28) # 724 load_gotdi [length = 4] beq $18,$0,.L56 # 246 *branch_zerodi [length = 4] sw $0,%got_ofst(i.12241)($2) # 244 *movsi_internal/5 [length = 4] ld $2,48($16) # 249 *movdi_64bit/4 [length = 4] ld $4,%got_page(base.12249)($28) # 718 load_gotdi [length = 4] lw $3,64($16) # 253 extendsidi2/2 [length = 4] sd $2,%got_ofst(base.12249)($4) # 251 *movdi_64bit/5 [length = 4] .L58: ld $2,0($2) # 270 *movdi_64bit/4 [length = 4] ld $17,%got_page(l.12250)($28) # 715 load_gotdi [length = 4] ld $4,%got_page(size.12244)($28) # 716 load_gotdi [length = 4] sd $2,%got_ofst(l.12250)($17) # 271 *movdi_64bit/5 [length = 4] sw $3,%got_ofst(size.12244)($4) # 267 *movsi_internal/5 [length = 4] ld $2,%got_disp(Cnil_body)($28) # 713 load_gotdi [length = 4] .L101: beq $16,$2,.L60 # 283 *branch_equalitydi [length = 4] ld $3,%got_page(pref.12253)($28) # 708 load_gotdi [length = 4] ld $2,%got_page(internal.12243)($28) # 707 load_gotdi [length = 4] ld $17,%got_page(l.12250)($28) # 712 load_gotdi [length = 4] ld $22,%got_ofst(pref.12253)($3) # 291 *movdi_64bit/4 [length = 4] lw $2,%got_ofst(internal.12243)($2) # 288 extendsidi2/2 [length = 4] ld $3,%got_page(prefl.12245)($28) # 710 load_gotdi [length = 4] sd $2,112($sp) # 670 *movdi_64bit/5 [length = 4] lw $16,%got_ofst(prefl.12245)($3) # 300 extendsidi2/2 [length = 4] ld $2,%got_page(len.12242)($28) # 709 load_gotdi [length = 4] ld $3,%got_page(wtext.12252)($28) # 711 load_gotdi [length = 4] lw $23,%got_ofst(len.12242)($2) # 294 extendsidi2/2 [length = 4] ld $fp,%got_ofst(wtext.12252)($3) # 296 *movdi_64bit/4 [length = 4] .L62: ld $3,%got_page(size.12244)($28) # 697 load_gotdi [length = 4] ld $4,%got_page(base.12249)($28) # 698 load_gotdi [length = 4] lw $20,%got_ofst(size.12244)($3) # 513 extendsidi2/2 [length = 4] ld $21,%got_ofst(base.12249)($4) # 516 *movdi_64bit/4 [length = 4] ld $8,%got_ofst(l.12250)($17) # 438 *movdi_64bit/4 [length = 4] .L100: lbu $2,0($8) # 439 *zero_extendqisi2/2 [length = 4] beql $2,$0,.L98 # 440 *branch_zerosi [length = 4] ld $6,16($8) # 309 *movdi_64bit/4 [length = 4] ld $5,%got_page(i.12241)($28) # 706 load_gotdi [length = 4] lw $2,%got_ofst(i.12241)($5) # 445 extendsidi2/2 [length = 4] .L99: addiu $2,$2,1 # 447 *addsi3_extended/2 [length = 4] beq $20,$2,.L74 # 451 *branch_equalitysi [length = 4] sw $2,%got_ofst(i.12241)($5) # 449 *movsi_internal/5 [length = 4] dsll $2,$2,3 # 457 *ashldi3 [length = 4] daddu $2,$2,$21 # 458 *adddi3/1 [length = 4] ld $4,0($2) # 459 *movdi_64bit/4 [length = 4] ld $3,%got_page(l.12250)($28) # 705 load_gotdi [length = 4] sd $4,%got_ofst(l.12250)($3) # 460 *movdi_64bit/5 [length = 4] ld $8,%got_ofst(l.12250)($17) # 776 *movdi_64bit/4 [length = 4] lbu $2,0($8) # 777 *zero_extendqisi2/2 [length = 4] bne $2,$0,.L99 # 778 *branch_zerosi [length = 4] lw $2,%got_ofst(i.12241)($5) # 445 extendsidi2/2 [length = 4] ld $6,16($8) # 309 *movdi_64bit/4 [length = 4] .L98: daddiu $7,$sp,40 # 311 *adddi3/2 [length = 4] daddiu $9,$6,64 # 312 *adddi3/2 [length = 4] .align 3 .L64: ld $2,0($6) # 314 *movdi_64bit/4 [length = 4] ld $3,8($6) # 315 *movdi_64bit/4 [length = 4] ld $4,16($6) # 316 *movdi_64bit/4 [length = 4] ld $5,24($6) # 317 *movdi_64bit/4 [length = 4] daddiu $6,$6,32 # 322 *adddi3/2 [length = 4] sd $2,0($7) # 318 *movdi_64bit/5 [length = 4] sd $3,8($7) # 319 *movdi_64bit/5 [length = 4] sd $4,16($7) # 320 *movdi_64bit/5 [length = 4] sd $5,24($7) # 321 *movdi_64bit/5 [length = 4] bne $6,$9,.L64 # 324 *branch_equalitydi [length = 4] daddiu $7,$7,32 # 323 *adddi3/2 [length = 4] ld $2,0($6) # 325 *movdi_64bit/4 [length = 4] sd $2,0($7) # 326 *movdi_64bit/5 [length = 4] ld $3,8($8) # 331 *movdi_64bit/4 [length = 4] ld $19,64($sp) # 327 *movdi_64bit/4 [length = 4] lw $18,72($sp) # 328 extendsidi2/2 [length = 4] beq $22,$0,.L65 # 334 *branch_zerodi [length = 4] sd $3,%got_ofst(l.12250)($17) # 332 *movdi_64bit/5 [length = 4] slt $2,$18,$16 # 338 *slt_si [length = 4] bne $2,$0,.L100 # 339 *branch_zerosi [length = 4] ld $8,%got_ofst(l.12250)($17) # 438 *movdi_64bit/4 [length = 4] ld $25,%call16(strncasecmp)($28) # 345 load_calldi [length = 4] move $4,$22 # 342 *movdi_64bit/1 [length = 4] move $5,$19 # 343 *movdi_64bit/1 [length = 4] jal $25 # 346 call_value_internal/1 [length = 4] move $6,$16 # 344 *movdi_64bit/1 [length = 4] bne $2,$0,.L100 # 348 *branch_zerodi [length = 4] ld $8,%got_ofst(l.12250)($17) # 438 *movdi_64bit/4 [length = 4] daddu $19,$19,$16 # 352 *adddi3/1 [length = 4] subu $18,$18,$16 # 355 *subsi3_extended [length = 4] .L65: slt $2,$18,$23 # 359 *slt_si [length = 4] bne $2,$0,.L100 # 360 *branch_zerosi [length = 4] ld $8,%got_ofst(l.12250)($17) # 438 *movdi_64bit/4 [length = 4] ld $25,%call16(strncasecmp)($28) # 366 load_calldi [length = 4] move $4,$fp # 363 *movdi_64bit/1 [length = 4] move $5,$19 # 364 *movdi_64bit/1 [length = 4] jal $25 # 367 call_value_internal/1 [length = 4] move $6,$23 # 365 *movdi_64bit/1 [length = 4] bne $2,$0,.L100 # 369 *branch_zerodi [length = 4] ld $8,%got_ofst(l.12250)($17) # 438 *movdi_64bit/4 [length = 4] ld $16,%got_page(ftext.12251)($28) # 692 load_gotdi [length = 4] ld $25,%call16(malloc)($28) # 380 load_calldi [length = 4] ld $17,%got_page(c.12263)($28) # 693 load_gotdi [length = 4] ld $4,%got_ofst(ftext.12251)($16) # 375 *movdi_64bit/4 [length = 4] dsubu $4,$fp,$4 # 376 subdi3 [length = 4] daddiu $4,$4,1 # 377 *adddi3/2 [length = 4] jal $25 # 381 call_value_internal/1 [length = 4] daddu $4,$18,$4 # 379 *adddi3/1 [length = 4] ld $3,%got_page(wtext.12252)($28) # 694 load_gotdi [length = 4] ld $5,%got_ofst(ftext.12251)($16) # 389 *movdi_64bit/4 [length = 4] ld $25,%call16(memcpy)($28) # 399 load_calldi [length = 4] ld $6,%got_ofst(wtext.12252)($3) # 391 *movdi_64bit/4 [length = 4] move $4,$2 # 396 *movdi_64bit/1 [length = 4] sd $2,%got_ofst(c.12263)($17) # 386 *movdi_64bit/5 [length = 4] jal $25 # 400 call_value_internal/1 [length = 4] dsubu $6,$6,$5 # 398 subdi3 [length = 4] ld $6,%got_page(wtext.12252)($28) # 695 load_gotdi [length = 4] ld $2,%got_ofst(ftext.12251)($16) # 406 *movdi_64bit/4 [length = 4] ld $3,%got_ofst(c.12263)($17) # 409 *movdi_64bit/4 [length = 4] ld $4,%got_ofst(wtext.12252)($6) # 405 *movdi_64bit/4 [length = 4] ld $25,%call16(memcpy)($28) # 417 load_calldi [length = 4] move $5,$19 # 415 *movdi_64bit/1 [length = 4] dsubu $4,$4,$2 # 407 subdi3 [length = 4] daddu $4,$4,$3 # 414 *adddi3/1 [length = 4] jal $25 # 418 call_value_internal/1 [length = 4] move $6,$18 # 416 *movdi_64bit/1 [length = 4] ld $2,%got_page(wtext.12252)($28) # 696 load_gotdi [length = 4] ld $5,%got_ofst(c.12263)($17) # 422 *movdi_64bit/4 [length = 4] ld $4,%got_ofst(ftext.12251)($16) # 426 *movdi_64bit/4 [length = 4] ld $3,%got_ofst(wtext.12252)($2) # 424 *movdi_64bit/4 [length = 4] daddu $2,$18,$5 # 428 *adddi3/1 [length = 4] dsubu $3,$3,$4 # 427 subdi3 [length = 4] daddu $2,$2,$3 # 429 *adddi3/1 [length = 4] sb $0,0($2) # 430 *movqi_internal/4 [length = 4] ld $31,208($sp) # 754 *movdi_64bit/4 [length = 4] ld $fp,200($sp) # 755 *movdi_64bit/4 [length = 4] ld $28,192($sp) # 756 *movdi_64bit/4 [length = 4] ld $23,184($sp) # 757 *movdi_64bit/4 [length = 4] ld $22,176($sp) # 758 *movdi_64bit/4 [length = 4] ld $21,168($sp) # 759 *movdi_64bit/4 [length = 4] ld $20,160($sp) # 760 *movdi_64bit/4 [length = 4] ld $19,152($sp) # 761 *movdi_64bit/4 [length = 4] ld $18,144($sp) # 762 *movdi_64bit/4 [length = 4] ld $17,136($sp) # 763 *movdi_64bit/4 [length = 4] ld $16,128($sp) # 764 *movdi_64bit/4 [length = 4] move $2,$5 # 530 *movdi_64bit/1 [length = 4] j $31 # 766 return_internal [length = 4] daddiu $sp,$sp,224 # 765 *adddi3/2 [length = 4] .L26: ld $6,%got_page(tp.12248)($28) # 714 load_gotdi [length = 4] ld $16,%got_ofst(tp.12248)($6) # 278 *movdi_64bit/4 [length = 4] bne $16,$0,.L101 # 279 *branch_zerodi [length = 4] ld $2,%got_disp(Cnil_body)($28) # 713 load_gotdi [length = 4] .L60: move $5,$0 # 521 *movdi_64bit/2 [length = 4] .L95: ld $31,208($sp) # 783 *movdi_64bit/4 [length = 4] ld $fp,200($sp) # 784 *movdi_64bit/4 [length = 4] ld $28,192($sp) # 785 *movdi_64bit/4 [length = 4] ld $23,184($sp) # 786 *movdi_64bit/4 [length = 4] ld $22,176($sp) # 787 *movdi_64bit/4 [length = 4] ld $21,168($sp) # 788 *movdi_64bit/4 [length = 4] ld $20,160($sp) # 789 *movdi_64bit/4 [length = 4] ld $19,152($sp) # 790 *movdi_64bit/4 [length = 4] ld $18,144($sp) # 791 *movdi_64bit/4 [length = 4] ld $17,136($sp) # 792 *movdi_64bit/4 [length = 4] ld $16,128($sp) # 793 *movdi_64bit/4 [length = 4] move $2,$5 # 781 *movdi_64bit/1 [length = 4] j $31 # 795 return_internal [length = 4] daddiu $sp,$sp,224 # 794 *adddi3/2 [length = 4] .align 3 .L74: ld $2,%got_page(use.12247)($28) # 703 load_gotdi [length = 4] ld $6,112($sp) # 673 *movdi_64bit/4 [length = 4] ld $3,%got_ofst(use.12247)($2) # 468 *movdi_64bit/4 [length = 4] ld $4,8($3) # 474 *movdi_64bit/4 [length = 4] ld $3,16($3) # 469 *movdi_64bit/4 [length = 4] sd $4,%got_ofst(use.12247)($2) # 475 *movdi_64bit/5 [length = 4] ld $4,%got_page(tp.12248)($28) # 704 load_gotdi [length = 4] beq $6,$0,.L76 # 477 *branch_zerodi [length = 4] sd $3,%got_ofst(tp.12248)($4) # 471 *movdi_64bit/5 [length = 4] ld $2,48($3) # 480 *movdi_64bit/4 [length = 4] ld $6,%got_page(base.12249)($28) # 702 load_gotdi [length = 4] lw $4,64($3) # 484 extendsidi2/2 [length = 4] sd $2,%got_ofst(base.12249)($6) # 482 *movdi_64bit/5 [length = 4] .L78: ld $2,0($2) # 504 *movdi_64bit/4 [length = 4] ld $6,%got_page(size.12244)($28) # 699 load_gotdi [length = 4] sw $0,%got_ofst(i.12241)($5) # 501 *movsi_internal/5 [length = 4] sd $2,%got_ofst(l.12250)($17) # 505 *movdi_64bit/5 [length = 4] ld $2,%got_disp(Cnil_body)($28) # 700 load_gotdi [length = 4] bne $3,$2,.L62 # 508 *branch_equalitydi [length = 4] sw $4,%got_ofst(size.12244)($6) # 498 *movsi_internal/5 [length = 4] b .L95 # 835 jump [length = 4] move $5,$0 # 800 *movdi_64bit/2 [length = 4] .align 3 .L76: ld $2,56($3) # 490 *movdi_64bit/4 [length = 4] lw $4,68($3) # 494 extendsidi2/2 [length = 4] ld $6,%got_page(base.12249)($28) # 701 load_gotdi [length = 4] b .L78 # 837 jump [length = 4] sd $2,%got_ofst(base.12249)($6) # 492 *movdi_64bit/5 [length = 4] .L56: ld $2,56($16) # 259 *movdi_64bit/4 [length = 4] lw $3,68($16) # 263 extendsidi2/2 [length = 4] ld $6,%got_page(base.12249)($28) # 717 load_gotdi [length = 4] b .L58 # 839 jump [length = 4] sd $2,%got_ofst(base.12249)($6) # 261 *movdi_64bit/5 [length = 4] .L28: lw $16,32($4) # 39 extendsidi2/2 [length = 4] ld $18,24($4) # 35 *movdi_64bit/4 [length = 4] ld $25,%call16(memchr)($28) # 46 load_calldi [length = 4] sw $16,%got_ofst(prefl.12245)($21) # 41 *movsi_internal/5 [length = 4] sd $18,%got_ofst(pref.12253)($22) # 37 *movdi_64bit/5 [length = 4] move $4,$18 # 43 *movdi_64bit/1 [length = 4] li $5,58 # 0x3a # 44 *movdi_64bit/2 [length = 4] jal $25 # 47 call_value_internal/1 [length = 4] move $6,$16 # 45 *movdi_64bit/1 [length = 4] beq $2,$0,.L30 # 49 *branch_zerodi [length = 4] move $17,$0 # 52 *movdi_64bit/2 [length = 4] lb $3,1($2) # 60 *extendqisi2/2 [length = 4] move $17,$2 # 57 *movdi_64bit/1 [length = 4] daddiu $4,$2,1 # 59 *adddi3/2 [length = 4] li $2,58 # 0x3a # 660 *movsi_internal/2 [length = 4] beql $3,$2,.L33 # 62 *branch_equalitysi [length = 4] daddiu $4,$17,2 # 65 *adddi3/2 [length = 4] .L33: dsubu $2,$4,$18 # 72 subdi3 [length = 4] sll $2,$2,0 # 73 truncdisi2/1 [length = 4] subu $2,$16,$2 # 74 subsi3 [length = 4] sw $2,%got_ofst(prefl.12245)($21) # 75 *movsi_internal/5 [length = 4] b .L30 # 841 jump [length = 4] sd $4,%got_ofst(pref.12253)($22) # 69 *movdi_64bit/5 [length = 4] .L91: lb $3,1($17) # 126 *extendqisi2/2 [length = 4] li $2,58 # 0x3a # 127 *movsi_internal/2 [length = 4] beql $3,$2,.L97 # 128 *branch_equalitysi [length = 4] ld $2,%got_disp(sLApackageA)($28) # 733 load_gotdi [length = 4] ld $2,%got_disp(keyword_package)($28) # 732 load_gotdi [length = 4] b .L88 # 843 jump [length = 4] ld $2,0($2) # 139 *movdi_64bit/4 [length = 4] .L35: bne $17,$0,.L37 # 103 *branch_zerodi [length = 4] move $4,$18 # 118 *movdi_64bit/1 [length = 4] ld $2,%got_disp(sLApackageA)($28) # 735 load_gotdi [length = 4] ld $5,%got_page(package.12246)($28) # 734 load_gotdi [length = 4] ld $3,0($2) # 109 *movdi_64bit/4 [length = 4] ld $4,8($3) # 110 *movdi_64bit/4 [length = 4] move $16,$4 # 690 *movdi_64bit/1 [length = 4] bne $16,$0,.L46 # 804 *branch_zerodi [length = 4] sd $4,%got_ofst(package.12246)($5) # 111 *movdi_64bit/5 [length = 4] .L92: ld $2,%got_disp(user_package)($28) # 729 load_gotdi [length = 4] b .L46 # 845 jump [length = 4] ld $16,0($2) # 178 *movdi_64bit/4 [length = 4] .L93: b .L53 # 847 jump [length = 4] move $4,$20 # 218 *movdi_64bit/1 [length = 4] .L97: ld $3,0($2) # 132 *movdi_64bit/4 [length = 4] b .L88 # 849 jump [length = 4] ld $2,8($3) # 133 *movdi_64bit/4 [length = 4] .set macro .set reorder .end rl_completion_words_new .align 2 .align 3 .globl rl_ungetc_em .ent rl_ungetc_em .type rl_ungetc_em, @function rl_ungetc_em: .frame $sp,32,$31 # vars= 0, regs= 4/0, args= 0, gp= 0 .mask 0x90030000,-8 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-32 # 67 *adddi3/2 [length = 4] sd $28,16($sp) # 69 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(rl_ungetc_em))) # 88 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 89 *adddi3/1 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(rl_ungetc_em))) # 90 *lowdi [length = 4] ld $2,%got_disp(stdin)($28) # 66 load_gotdi [length = 4] sd $17,8($sp) # 70 *movdi_64bit/5 [length = 4] sd $16,0($sp) # 71 *movdi_64bit/5 [length = 4] sd $31,24($sp) # 68 *movdi_64bit/5 [length = 4] ld $3,0($2) # 11 *movdi_64bit/4 [length = 4] move $17,$4 # 3 *movdi_64bit/1 [length = 4] ld $25,%call16(fileno)($28) # 16 load_calldi [length = 4] move $16,$5 # 4 *movdi_64bit/1 [length = 4] beq $3,$5,.L108 # 12 *branch_equalitydi [length = 4] move $4,$5 # 15 *movdi_64bit/1 [length = 4] .L103: ld $25,%got_disp(ungetc)($28) # 65 load_gotdi [length = 4] ld $28,16($sp) # 83 *movdi_64bit/4 [length = 4] move $4,$17 # 28 *movdi_64bit/1 [length = 4] move $5,$16 # 29 *movdi_64bit/1 [length = 4] ld $31,24($sp) # 82 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 84 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 85 *movdi_64bit/4 [length = 4] jr $25 # 31 sibcall_value_internal/1 [length = 4] daddiu $sp,$sp,32 # 86 *adddi3/2 [length = 4] .align 3 .L108: jal $25 nop # 17 call_value_internal/1 [length = 8] ld $25,%call16(isatty)($28) # 21 load_calldi [length = 4] jal $25 # 22 call_value_internal/1 [length = 4] move $4,$2 # 20 *movdi_64bit/1 [length = 4] beq $2,$0,.L103 # 25 *branch_zerodi [length = 4] andi $3,$17,0x00ff # 39 *zero_extendqisi2/1 [length = 4] ld $2,%got_page(rl_ungetc_em_char)($28) # 64 load_gotdi [length = 4] sw $3,%got_ofst(rl_ungetc_em_char)($2) # 40 *movsi_internal/5 [length = 4] ld $31,24($sp) # 75 *movdi_64bit/4 [length = 4] move $2,$17 # 49 *movdi_64bit/1 [length = 4] ld $28,16($sp) # 76 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 77 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 78 *movdi_64bit/4 [length = 4] j $31 # 80 return_internal [length = 4] daddiu $sp,$sp,32 # 79 *adddi3/2 [length = 4] .set macro .set reorder .end rl_ungetc_em .align 2 .align 3 .globl rl_putc_em .ent rl_putc_em .type rl_putc_em, @function rl_putc_em: .frame $sp,64,$31 # vars= 0, regs= 8/0, args= 0, gp= 0 .mask 0x903f0000,-8 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-64 # 164 *adddi3/2 [length = 4] sd $28,48($sp) # 166 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(rl_putc_em))) # 192 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 193 *adddi3/1 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(rl_putc_em))) # 194 *lowdi [length = 4] ld $2,%got_disp(stdout)($28) # 163 load_gotdi [length = 4] sd $17,8($sp) # 171 *movdi_64bit/5 [length = 4] sd $16,0($sp) # 172 *movdi_64bit/5 [length = 4] sd $31,56($sp) # 165 *movdi_64bit/5 [length = 4] sd $21,40($sp) # 167 *movdi_64bit/5 [length = 4] sd $20,32($sp) # 168 *movdi_64bit/5 [length = 4] sd $19,24($sp) # 169 *movdi_64bit/5 [length = 4] sd $18,16($sp) # 170 *movdi_64bit/5 [length = 4] ld $3,0($2) # 11 *movdi_64bit/4 [length = 4] move $16,$5 # 4 *movdi_64bit/1 [length = 4] beq $3,$5,.L122 # 12 *branch_equalitydi [length = 4] move $17,$4 # 3 *movdi_64bit/1 [length = 4] .L110: ld $25,%got_disp(_IO_putc)($28) # 155 load_gotdi [length = 4] ld $28,48($sp) # 176 *movdi_64bit/4 [length = 4] move $4,$17 # 118 *movdi_64bit/1 [length = 4] move $5,$16 # 119 *movdi_64bit/1 [length = 4] ld $31,56($sp) # 175 *movdi_64bit/4 [length = 4] ld $21,40($sp) # 177 *movdi_64bit/4 [length = 4] ld $20,32($sp) # 178 *movdi_64bit/4 [length = 4] ld $19,24($sp) # 179 *movdi_64bit/4 [length = 4] ld $18,16($sp) # 180 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 181 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 182 *movdi_64bit/4 [length = 4] jr $25 # 121 sibcall_value_internal/1 [length = 4] daddiu $sp,$sp,64 # 183 *adddi3/2 [length = 4] .align 3 .L122: ld $25,%call16(fileno)($28) # 16 load_calldi [length = 4] jal $25 # 17 call_value_internal/1 [length = 4] move $4,$5 # 15 *movdi_64bit/1 [length = 4] ld $25,%call16(isatty)($28) # 21 load_calldi [length = 4] jal $25 # 22 call_value_internal/1 [length = 4] move $4,$2 # 20 *movdi_64bit/1 [length = 4] beq $2,$0,.L110 # 25 *branch_zerodi [length = 4] li $2,13 # 0xd # 29 *movsi_internal/2 [length = 4] beq $17,$2,.L113 # 30 *branch_equalitysi [length = 4] li $2,10 # 0xa # 33 *movsi_internal/2 [length = 4] beq $17,$2,.L113 # 34 *branch_equalitysi [length = 4] ld $18,%got_page(current_length.12377)($28) # 158 load_gotdi [length = 4] ld $19,%got_page(allocated_length.12376)($28) # 159 load_gotdi [length = 4] lw $5,%got_ofst(current_length.12377)($18) # 55 extendsidi2/2 [length = 4] lw $3,%got_ofst(allocated_length.12376)($19) # 58 extendsidi2/2 [length = 4] addiu $2,$5,2 # 56 *addsi3/2 [length = 4] slt $2,$3,$2 # 59 *sgt_si [length = 4] bne $2,$0,.L123 # 60 *branch_zerosi [length = 4] ld $20,%got_page(rl_putc_em_line)($28) # 156 load_gotdi [length = 4] .L117: lw $2,%got_ofst(current_length.12377)($18) # 102 extendsidi2/2 [length = 4] ld $3,%got_ofst(rl_putc_em_line)($20) # 104 *movdi_64bit/4 [length = 4] addiu $4,$2,1 # 108 *addsi3_extended/2 [length = 4] daddu $5,$3,$4 # 112 *adddi3/1 [length = 4] daddu $2,$2,$3 # 105 *adddi3/1 [length = 4] sb $17,0($2) # 106 *movqi_internal/4 [length = 4] sw $4,%got_ofst(current_length.12377)($18) # 110 *movsi_internal/5 [length = 4] b .L110 # 195 jump [length = 4] sb $0,0($5) # 113 *movqi_internal/4 [length = 4] .L113: ld $2,%got_page(allocated_length.12376)($28) # 161 load_gotdi [length = 4] ld $3,%got_page(current_length.12377)($28) # 162 load_gotdi [length = 4] lw $4,%got_ofst(allocated_length.12376)($2) # 42 extendsidi2/2 [length = 4] blez $4,.L110 # 43 *branch_zerosi [length = 4] sw $0,%got_ofst(current_length.12377)($3) # 39 *movsi_internal/5 [length = 4] ld $2,%got_page(rl_putc_em_line)($28) # 160 load_gotdi [length = 4] ld $3,%got_ofst(rl_putc_em_line)($2) # 47 *movdi_64bit/4 [length = 4] b .L110 # 197 jump [length = 4] sb $0,0($3) # 48 *movqi_internal/4 [length = 4] .L123: sll $5,$5,1 # 64 *ashlsi3 [length = 4] ld $25,%call16(realloc)($28) # 75 load_calldi [length = 4] ld $21,%got_ofst(rl_putc_em_line)($20) # 71 *movdi_64bit/4 [length = 4] addiu $5,$5,16 # 66 *addsi3_extended/2 [length = 4] sw $5,%got_ofst(allocated_length.12376)($19) # 68 *movsi_internal/5 [length = 4] jal $25 # 76 call_value_internal/1 [length = 4] move $4,$21 # 73 *movdi_64bit/1 [length = 4] bne $2,$0,.L117 # 82 *branch_zerodi [length = 4] sd $2,%got_ofst(rl_putc_em_line)($20) # 80 *movdi_64bit/5 [length = 4] ld $25,%call16(free)($28) # 87 load_calldi [length = 4] jal $25 # 88 call_internal/1 [length = 4] move $4,$21 # 86 *movdi_64bit/1 [length = 4] sw $0,%got_ofst(allocated_length.12376)($19) # 91 *movsi_internal/5 [length = 4] b .L110 # 199 jump [length = 4] sw $0,%got_ofst(current_length.12377)($18) # 94 *movsi_internal/5 [length = 4] .set macro .set reorder .end rl_putc_em .align 2 .align 3 .globl rl_getc_em .ent rl_getc_em .type rl_getc_em, @function rl_getc_em: .frame $sp,64,$31 # vars= 0, regs= 7/0, args= 0, gp= 0 .mask 0x901f0000,-16 .fmask 0x00000000,0 .set noreorder .set nomacro daddiu $sp,$sp,-64 # 217 *adddi3/2 [length = 4] sd $28,40($sp) # 219 *movdi_64bit/5 [length = 4] lui $28,%hi(%neg(%gp_rel(rl_getc_em))) # 273 *movdi_64bit/2 [length = 4] daddu $28,$28,$25 # 274 *adddi3/1 [length = 4] daddiu $28,$28,%lo(%neg(%gp_rel(rl_getc_em))) # 275 *lowdi [length = 4] ld $2,%got_disp(stdin)($28) # 216 load_gotdi [length = 4] sd $16,0($sp) # 224 *movdi_64bit/5 [length = 4] sd $31,48($sp) # 218 *movdi_64bit/5 [length = 4] sd $20,32($sp) # 220 *movdi_64bit/5 [length = 4] sd $19,24($sp) # 221 *movdi_64bit/5 [length = 4] sd $18,16($sp) # 222 *movdi_64bit/5 [length = 4] sd $17,8($sp) # 223 *movdi_64bit/5 [length = 4] ld $17,0($2) # 10 *movdi_64bit/4 [length = 4] beq $17,$4,.L144 # 11 *branch_equalitydi [length = 4] move $16,$4 # 3 *movdi_64bit/1 [length = 4] move $4,$16 # 27 *movdi_64bit/1 [length = 4] .L143: ld $25,%got_disp(_IO_getc)($28) # 208 load_gotdi [length = 4] ld $28,40($sp) # 247 *movdi_64bit/4 [length = 4] ld $31,48($sp) # 246 *movdi_64bit/4 [length = 4] ld $20,32($sp) # 248 *movdi_64bit/4 [length = 4] ld $19,24($sp) # 249 *movdi_64bit/4 [length = 4] ld $18,16($sp) # 250 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 251 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 252 *movdi_64bit/4 [length = 4] jr $25 # 116 sibcall_value_internal/1 [length = 4] daddiu $sp,$sp,64 # 253 *adddi3/2 [length = 4] .align 3 .L144: ld $25,%call16(fileno)($28) # 15 load_calldi [length = 4] jal $25 nop # 16 call_value_internal/1 [length = 8] ld $25,%call16(isatty)($28) # 20 load_calldi [length = 4] jal $25 # 21 call_value_internal/1 [length = 4] move $4,$2 # 19 *movdi_64bit/1 [length = 4] beql $2,$0,.L143 # 24 *branch_zerodi [length = 4] move $4,$16 # 27 *movdi_64bit/1 [length = 4] ld $2,%got_page(rl_ungetc_em_char)($28) # 214 load_gotdi [length = 4] li $19,-1 # 0xffffffffffffffff # 38 *movsi_internal/2 [length = 4] lw $18,%got_ofst(rl_ungetc_em_char)($2) # 37 extendsidi2/2 [length = 4] beq $18,$19,.L128 # 39 *branch_equalitysi [length = 4] ld $20,%got_page(line.12405)($28) # 213 load_gotdi [length = 4] sw $19,%got_ofst(rl_ungetc_em_char)($2) # 45 *movsi_internal/5 [length = 4] .L130: move $2,$18 # 172 *movdi_64bit/1 [length = 4] .L148: ld $31,48($sp) # 228 *movdi_64bit/4 [length = 4] ld $28,40($sp) # 229 *movdi_64bit/4 [length = 4] ld $20,32($sp) # 230 *movdi_64bit/4 [length = 4] ld $19,24($sp) # 231 *movdi_64bit/4 [length = 4] ld $18,16($sp) # 232 *movdi_64bit/4 [length = 4] ld $17,8($sp) # 233 *movdi_64bit/4 [length = 4] ld $16,0($sp) # 234 *movdi_64bit/4 [length = 4] j $31 # 236 return_internal [length = 4] daddiu $sp,$sp,64 # 235 *adddi3/2 [length = 4] .L128: ld $2,%got_ofst(line.12405)($20) # 53 *movdi_64bit/4 [length = 4] beq $2,$0,.L145 # 54 *branch_zerodi [length = 4] ld $2,%got_disp(readline_on)($28) # 212 load_gotdi [length = 4] ld $16,%got_page(linepos.12406)($28) # 207 load_gotdi [length = 4] .L149: ld $4,%got_ofst(line.12405)($20) # 126 *movdi_64bit/4 [length = 4] .L150: lw $5,%got_ofst(linepos.12406)($16) # 124 extendsidi2/2 [length = 4] daddu $2,$5,$4 # 127 *adddi3/1 [length = 4] lb $3,0($2) # 128 *extendqidi2/2 [length = 4] bne $3,$0,.L138 # 129 *branch_zerodi [length = 4] ld $25,%call16(free)($28) # 134 load_calldi [length = 4] jal $25 # 135 call_internal/1 [length = 4] li $18,10 # 0xa # 148 *movdi_64bit/2 [length = 4] ld $2,%got_page(line.12405)($28) # 205 load_gotdi [length = 4] sw $0,%got_ofst(linepos.12406)($16) # 141 *movsi_internal/5 [length = 4] sd $0,%got_ofst(line.12405)($2) # 138 *movdi_64bit/5 [length = 4] ld $2,%got_disp(rl_line_buffer)($28) # 206 load_gotdi [length = 4] ld $2,0($2) # 144 *movdi_64bit/4 [length = 4] bnel $2,$0,.L130 # 145 *branch_zerodi [length = 4] sb $0,0($2) # 153 *movqi_internal/4 [length = 4] b .L148 # 276 jump [length = 4] move $2,$18 # 172 *movdi_64bit/1 [length = 4] .L145: li $3,1 # 0x1 # 199 *movsi_internal/2 [length = 4] lw $4,0($2) # 59 extendsidi2/2 [length = 4] beq $4,$3,.L146 # 61 *branch_equalitysi [length = 4] ld $16,%got_disp(stdout)($28) # 210 load_gotdi [length = 4] b .L143 # 278 jump [length = 4] move $4,$17 # 114 *movdi_64bit/1 [length = 4] .L138: addiu $2,$5,1 # 162 *addsi3/2 [length = 4] move $18,$3 # 160 *movdi_64bit/1 [length = 4] b .L130 # 280 jump [length = 4] sw $2,%got_ofst(linepos.12406)($16) # 163 *movsi_internal/5 [length = 4] .L146: ld $25,%call16(_IO_putc)($28) # 69 load_calldi [length = 4] li $4,13 # 0xd # 67 *movdi_64bit/2 [length = 4] jal $25 # 70 call_value_internal/1 [length = 4] ld $5,0($16) # 68 *movdi_64bit/4 [length = 4] ld $2,%got_page(rl_putc_em_line)($28) # 211 load_gotdi [length = 4] ld $25,%call16(readline)($28) # 75 load_calldi [length = 4] jal $25 # 76 call_value_internal/1 [length = 4] ld $4,%got_ofst(rl_putc_em_line)($2) # 74 *movdi_64bit/4 [length = 4] ld $25,%call16(rl_putc_em)($28) # 85 load_calldi [length = 4] ld $5,0($16) # 84 *movdi_64bit/4 [length = 4] li $4,13 # 0xd # 83 *movdi_64bit/2 [length = 4] jal $25 # 86 call_value_internal/1 [length = 4] sd $2,%got_ofst(line.12405)($20) # 79 *movdi_64bit/5 [length = 4] ld $4,%got_ofst(line.12405)($20) # 89 *movdi_64bit/4 [length = 4] beq $4,$0,.L147 # 90 *branch_zerodi [length = 4] ld $2,%got_disp(rl_line_buffer)($28) # 209 load_gotdi [length = 4] lb $2,0($4) # 102 *extendqisi2/2 [length = 4] beql $2,$0,.L150 # 103 *branch_zerosi [length = 4] ld $16,%got_page(linepos.12406)($28) # 207 load_gotdi [length = 4] ld $25,%call16(add_history)($28) # 107 load_calldi [length = 4] jal $25 nop # 108 call_internal/1 [length = 8] b .L149 # 282 jump [length = 4] ld $16,%got_page(linepos.12406)($28) # 207 load_gotdi [length = 4] .L147: ld $3,0($2) # 94 *movdi_64bit/4 [length = 4] b .L130 # 284 jump [length = 4] sb $19,0($3) # 96 *movqi_internal/4 [length = 4] .set macro .set reorder .end rl_getc_em .globl readline_on .section .bss .align 2 .type readline_on, @object .size readline_on, 4 readline_on: .space 4 .local n.12486 .comm n.12486,4,4 .local c.12263 .comm c.12263,8,8 .local pref.12253 .comm pref.12253,8,8 .local wtext.12252 .comm wtext.12252,8,8 .local ftext.12251 .comm ftext.12251,8,8 .local l.12250 .comm l.12250,8,8 .local base.12249 .comm base.12249,8,8 .local tp.12248 .comm tp.12248,8,8 .local use.12247 .comm use.12247,8,8 .local package.12246 .comm package.12246,8,8 .local prefl.12245 .comm prefl.12245,4,4 .local size.12244 .comm size.12244,4,4 .local internal.12243 .comm internal.12243,4,4 .local len.12242 .comm len.12242,4,4 .local i.12241 .comm i.12241,4,4 .data .align 2 .type rl_ungetc_em_char, @object .size rl_ungetc_em_char, 4 rl_ungetc_em_char: .word -1 .local rl_putc_em_line .comm rl_putc_em_line,8,8 .local linepos.12406 .comm linepos.12406,4,4 .local line.12405 .comm line.12405,8,8 .local current_length.12377 .comm current_length.12377,4,4 .local allocated_length.12376 .comm allocated_length.12376,4,4 .comm tf,8,8 .comm kf,8,8 .comm car_or_cdr,8,8 .comm casefun,8,8 .comm sSAreadline_prefixA,8,8 .ident "GCC: (GNU) 4.1.2 (Gentoo 4.1.2)" # objdump -d gcl_readline.o |grep -5 928 objdump -d gcl_readline.o |grep -5 928 914: ffb10008 sd s1,8(sp) 918: dc510000 ld s1,0(v0) 91c: 1224000c beq s1,a0,950 <rl_getc_em+0x68> 920: 0080802d move s0,a0 924: 0200202d move a0,s0 928: df990000 ld t9,0(gp) 92c: dfbc0028 ld gp,40(sp) 930: dfbf0030 ld ra,48(sp) 934: dfb40020 ld s4,32(sp) 938: dfb30018 ld s3,24(sp) 93c: dfb20010 ld s2,16(sp) ... # gcc -v gcc -v Using built-in specs. Target: mips64el-gentoo-linux-gnu Configured with: /opt/sicortex/rootfs/build/var/tmp/portage/sys-devel/gcc-4.1.2/work/gcc-4.1.2/configure --prefix=/usr --bindir=/usr/mips64el-gentoo-linux-gnu/gcc-bin/4.1.2 --includedir=/usr/lib/gcc/mips64el-gentoo-linux-gnu/4.1.2/include --datadir=/usr/share/gcc-data/mips64el-gentoo-linux-gnu/4.1.2 --mandir=/usr/share/gcc-data/mips64el-gentoo-linux-gnu/4.1.2/man --infodir=/usr/share/gcc-data/mips64el-gentoo-linux-gnu/4.1.2/info --with-gxx-include-dir=/usr/lib/gcc/mips64el-gentoo-linux-gnu/4.1.2/include/g++-v4 --host=mips64el-gentoo-linux-gnu --target=mips64el-gentoo-linux-gnu --build=x86_64-pc-linux-gnu --disable-altivec --disable-nls --with-system-zlib --disable-checking --disable-werror --enable-secureplt --disable-libunwind-exceptions --enable-multilib --enable-libmudflap --disable-libssp --disable-libgcj --with-abi=64 --with-arch=5kf --enable-languages=c,c++,fortran --enable-shared --enable-threads=posix --enable-__cxa_atexit --enable-clocale=gnu Thread model: posix gcc version 4.1.2 (Gentoo 4.1.2) ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [Gcl-devel] Re: gdb for mips64 2010-10-29 15:52 ` Camm Maguire @ 2010-10-30 12:39 ` Maciej W. Rozycki 0 siblings, 0 replies; 21+ messages in thread From: Maciej W. Rozycki @ 2010-10-30 12:39 UTC (permalink / raw) To: Camm Maguire; +Cc: David Daney, linux-mips, debian-mips, gcl-devel On Fri, 29 Oct 2010, Camm Maguire wrote: > OK see attachment below. Thanks. This is the piece of code generated (I've snipped out the irrelevant bits: ld $25,%got_disp(_IO_getc)($28) # 208 load_gotdi [length = 4] ld $28,40($sp) # 247 *movdi_64bit/4 [length = 4] [...] jr $25 # 116 sibcall_value_internal/1 [length = 4] daddiu $sp,$sp,64 # 253 *adddi3/2 [length = 4] As you can see this is a sibling (aka tail) call and GCC deliberately requests a GOT rather than a CALL reloc -- %got_disp(_IO_getc) means: "Give me _IO_getc with a R_MIPS_GOT_DISP reloc applied!". I have checked GCC sources and this is legitimate, because with the new ABIs the GOT pointer register ($gp aka $28) is call saved -- as you can see it's restored above to the value coming from the caller. And the stub requires $gp to have been loaded with a pointer to the containing module's GOT and not (possibly) some other one. Here's the relevant comment from GCC: /* If we're generating PIC, and this call is to a global function, try to allow its address to be resolved lazily. This isn't possible for NewABI sibcalls since the value of $gp on entry to the stub would be our caller's gp, not ours. */ As this is something I had not considered before I was not aware of this new ABI limitation until now -- thanks for giving me the opportunity to get enlightened. :) You may not be seeing this with a newer version of GCC, because it may be refraining from emitting the sibling call for some reason -- essentially here we have a tradeoff between a one-time performance penalty at startup coming from the lack of the lazy stub and a per-call penalty coming from an extra return required if this was an ordinary call. GCC may be able to assess the choice based on the likelihood of execution. Just guessing though -- I'm not that much into GCC's internals ;) -- and the explanation may be as simple as -fno-optimize-sibling-calls sneaked in somewhere. ;) > Its simple but rather unconventional. GCL is a lisp system. It loads > compiled object files at runtime into memory, and executes therefrom. > It can then save the expanded memory image to disk via unexec for > later execution on the same or different machines. Compiled code can Ah, that brings memories from the 1990s and the Perl's "undump" facility that allowed one to get executable machine code from otherwise interpreted code. ;) I believe the functionality was lost with the transition from a.out to ELF and never revived -- for a change you seem to be doing the revival for Lisp, at least to some extent. :) > reference symbols in external shared libraries. These must be > directed toward some trampoline in the initial final-linked > executable, as otherwise the address loaded might not be valid in a > later execution. On mips, GCL adds a little stub to load the global > got address from a local got table appended to the .o file, then to > load the contents of this address, and then jump. GCL ensures that > LD_BIND_NOW is set at runtime via pushing the environment and execve() > on startup. On other systems, where .plt entries are available, GCL > sets the address to the .plt which takes care of everything. This is > much cleaner as it requires no little machine-specific assembly. Interesting -- do you actually mean "compiled object files" are final executables (that may or may not have a PLT according to the ABI used) rather than .o files one would normally assume? Note that with current versions of the tools (GCC + binutils) you can get a PLT in MIPS code as an alternative as well (32-bit only; new ABIs are still limited to MIPS stubs only) coming from an ABI modification made for performance gain; I reckon -mplt is the GCC switch to request it. I'm not entirely sure what the exact timeline of these changes was, but GCC 4.4 should most certainly provide it and when it comes to binutils, as noted previously, you are best running the most recent version anyway. Still the use of PLTs would not solve the issue where a PLT would not, for some reason, be generated at all, such as with the LD's "-z now" option, or for a given function call, such as with MIPS new ABI's sibling calls (which I am fairly sure will be subject to the same limitation if ever implemented), would it? > In the cvs version of GCL, such external calls are made through a C > pointer, which is redirected at startup to the correct address via > dlsym(). A little faster, and makes the loader a little simpler. It sounds cleaner to me if I'm getting the overall picture right here. > Thankfully thus far this has not proved necessary. But ia64 and hppa > are the only targets yet unimplemented, so who knows. Hmm, the Itanic sounds like a problem by definition. ;) Is anybody still using it anyway? Can't comment on HP-PA. Maciej ^ permalink raw reply [flat|nested] 21+ messages in thread
end of thread, other threads:[~2010-11-01 18:25 UTC | newest]
Thread overview: 21+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
[not found] <E1OwbkA-0006gv-Bi@localhost.m.enhanced.com>
[not found] ` <4C93993E.7030008@caviumnetworks.com>
[not found] ` <8762y49k1k.fsf@maguirefamily.org>
[not found] ` <4C93D86D.5090201@caviumnetworks.com>
[not found] ` <87fwx4dwu5.fsf@maguirefamily.org>
[not found] ` <4C97D9A1.7050102@caviumnetworks.com>
[not found] ` <87lj6te9t1.fsf@maguirefamily.org>
[not found] ` <4C9A8BC9.1020605@caviumnetworks.com>
[not found] ` <4C9A9699.6080908@caviumnetworks.com>
[not found] ` <87pqvbs7oa.fsf@maguirefamily.org>
[not found] ` <4CB88D2C.8020900@caviumnetworks.com>
[not found] ` <87r5fksxby.fsf_-_@maguirefamily.org>
2010-10-20 16:38 ` recent SIGBUS/SIGSEGV mips kernel bug David Daney
2010-10-20 21:31 ` Camm Maguire
2010-10-21 16:19 ` David Daney
2010-10-21 16:32 ` Camm Maguire
2010-10-21 17:29 ` David Daney
2010-10-21 19:07 ` Camm Maguire
2010-10-25 20:11 ` Camm Maguire
2010-10-25 21:32 ` gdb for mips64 Camm Maguire
2010-10-25 21:45 ` David Daney
2010-10-26 12:47 ` Maciej W. Rozycki
2010-10-26 17:19 ` David Daney
2010-11-01 16:24 ` mips and ADDR_NO_RANDOMIZE Camm Maguire
2010-11-01 18:06 ` David Daney
2010-11-01 18:24 ` Camm Maguire
2010-10-26 14:47 ` gdb for mips64 Camm Maguire
2010-10-26 20:12 ` [Gcl-devel] " Camm Maguire
2010-10-28 10:50 ` Maciej W. Rozycki
2010-10-28 21:28 ` Camm Maguire
2010-10-29 7:47 ` Maciej W. Rozycki
2010-10-29 15:52 ` Camm Maguire
2010-10-30 12:39 ` Maciej W. Rozycki
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.