https://gcc.gnu.org/bugzilla/show_bug.cgi?id=91287

--- Comment #21 from Xiong Hu XS Luo <luoxhu at cn dot ibm.com> ---
(In reply to H.J. Lu from comment #19)
> (In reply to Richard Biener from comment #17)
> > (In reply to Richard Biener from comment #16)
> > > (In reply to Richard Biener from comment #15)
> > > > Honza probably knows where we output the LTO symtab and why we do not 
> > > > put
> > > > undefs for builtins there.
> > > 
> > > #include <math.h>
> > > double y, z;
> > > void foo ();
> > > int main()
> > > {
> > >   volatile double x = atan2 (y, z);
> > >   foo ();
> > > }
> > > 
> > > > gcc-8 -c t.c -flto
> > > > gcc-nm t.o
> > >          U foo
> > > 00000000 T main
> > > 00000000 C y
> > > 00000000 C z
> > > 
> > > where's the
> > > 
> > >          U atan2
> > > 
> > > ?
> > 
> > For
> > 
> > double atan2 (double x, double y) { return x + y; }
> > 
> > it doesn't appear either, this CU has an empty symbol table...
> > 
> > I do remember quite some "funs" with builtin handling though, so the
> > current handling may be the least bad of all choices...
> 
> [hjl@gnu-cfl-1 pr91287]$ cat foo1.c
> #include <stdlib.h>
> 
> float
> atan2f (float x, float y)
> {
>   abort ();
>   return x * y;
> }
> [hjl@gnu-cfl-1 pr91287]$ cat foo.c
> float
> atan2f (float x, float y)
> {
>   return x * y;
> }
> [hjl@gnu-cfl-1 pr91287]$ cat bar.c
> #include <math.h>
> 
> extern float x, y, z;
> 
> void
> bar (void)
> {
>   x = atan2f (y, z);
> }
> [hjl@gnu-cfl-1 pr91287]$ cat main.c 
> #include <math.h>
> 
> extern void bar (void);
> 
> float x, y = 1, z =1;
> 
> int
> main (void)
> {
>   x = atan2f (y, z);
>   bar ();
>   return 0;
> }
> [hjl@gnu-cfl-1 pr91287]$ make
> cc -O3   -c -o foo.o foo.c
> ar rc libfoo.a foo.o
> cc -O3 -fpic   -c -o bar.o bar.c
> cc -O3 -fpic   -c -o foo1.o foo1.c
> ld -shared -o libfoo1.so foo1.o # --version-script foo1.v
> ld -shared -o libbar.so bar.o libfoo1.so
> cc -flto -O3 -o x main.c libfoo.a libbar.so libfoo1.so -Wl,-R,.
> cc -O3 -o y main.c libfoo.a libbar.so libfoo1.so -Wl,-R,.
> ./y
> ./x
> make: *** [Makefile:9: all] Aborted
> [hjl@gnu-cfl-1 pr91287]$ 
> 
> Since atan2f isn't referenced in IR, linker doesn't extract atan2f from
> libfoo.a.  atan2f is resolved to definition in libfoo1.so later.
Thanks for your test case.
If remove the libfoo1.so when build x, it will link libfoo.a. And run x will
not abort.  

luoxhu@genoa pr91287 $ ~/local/gcc_t/bin/gcc -flto -O3 -o x main.c libfoo.a
libbar.so  -Wl,-R,.
luoxhu@genoa pr91287 $ ./x

Since x can link the libfoo.a if libfoo1.so not exists, not quite understand
why "atan2f isn't referenced in IR"?

Acutually my test case shows that binary built with LTO can link libmass.a
first when use gcc, but failed to link libmass.a if use gfortran(link libm.so
finally).

PS: My test case (gcc LTO link libmass.a first) doesn't match with your case
result(gcc LTO link libfoo1.so instead of libfoo.a).

Reply via email to