On Monday 28 December 2009 18:37, matthieu castet wrote:
> Hi,
>
> gcc with the -fpic option optimize code like :
> __attribute__ ((visibility ("hidden")))
> # define weak_function __attribute__ ((weak))
>
> extern void weak_function _stdio_init(void) attribute_hidden;
>
>
> int main()
> {
> if (_stdio_init)
> _stdio_init();
>
> return 0;
> }
>
>
> to
>
> __attribute__ ((visibility ("hidden")))
> # define weak_function __attribute__ ((weak))
>
> extern void weak_function _stdio_init(void) attribute_hidden;
>
>
> int main()
> {
> _stdio_init();
>
> return 0;
> }
>
> This crash if _stdio_init is null (because the linker didn't put it)
> Without this patch, it is impossible to static link default config uClibc on
> x86.
Well yeah, the problem is real, but the patch is wrong.
We do want these symbols to be hidden.
It's good that you have a config/gcc combo where it easily triggers.
Let's nail it.
The problem is, C/C++ says that function's address is never NULL,
and gcc uses this.
How about using asm() to prevent gcc from understanding that the pointer
is a function pointer?
Test program:
extern void g1(void);
extern void g2(void);
static inline __attribute__ ((__always_inline__)) int not_null(const void *p)
{
const void *q;
asm (""
: "=r" (q) /* output */
: "0" (p) /* input */
);
return q != 0;
}
void f1()
{
if (g1) g1();
}
void f2()
{
if (not_null(g2)) g2();
}
Resulting code:
# gcc -Os -fomit-frame-pointer -S t.c
# cat t.s
.file "t.c"
.text
.globl f2
.type f2, @function
f2:
movl $g2, %eax
testl %eax, %eax
je .L4
jmp g2
.L4:
ret
.size f2, .-f2
.globl f1
.type f1, @function
f1:
jmp g1
.size f1, .-f1
.ident "GCC: (GNU) 4.2.1"
.section .note.GNU-stack,"",@progbits
Care to remake the patch to use such not_null() wrapper?
Please also add a comment above it with explanation
why it is needed.
--
vda
_______________________________________________
uClibc mailing list
[email protected]
http://lists.busybox.net/mailman/listinfo/uclibc