Unlike Bug #29159 and Bug #17402, this one involves -ffreestanding. The results are not really different. Basically, gcc is unable to correctly compile anything significant with -fwhole-program. With or without the -ffreestanding option, gcc will leave undefined references to various string.h things. It does not matter if the program provides these functions in *.c files.
Note that -ffreestanding is illogical. I do have a C library, even including the various libgcc things. I added -ffreestanding just now because a comment in Bug #17402 incorrectly suggests this as a fix for the problem. Note that -ffreestanding is probably undesirable even if would work, because I provide a runtime and I expect gcc to take advantage of that runtime. So anyway... I have a number of *.c files, including a bit of inline assembly, which form the entire program. ("program" being a shared object which gets executed via the _init function) There are no other source libraries. I have a memset.c containing the obvious function. This is based on klibc (bare-bones Linux C library) with the assembly files replaced with *.c files. No matter what attributes I place on the functions, either in the *.c or *.h files, the compiler produces an undefined reference to memset. Though gcc certainly compiles the function, it seems to forget this. I don't think an undefined reference should even be possible with the -fwhole-program option; this supposedly tells the compiler that I'm giving the WHOLE program. The gcc version: $ gcc -v Using built-in specs. Target: x86_64-redhat-linux Configured with: ../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --enable-shared --enable-threads=posix --enable-checking=release --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-libgcj-multifile --enable-languages=c,c++,objc,obj-c++,java,fortran,ada --enable-java-awt=gtk --disable-dssi --enable-plugin --with-java-home=/usr/lib/jvm/java-1.4.2-gcj-1.4.2.0/jre --with-cpu=generic --host=x86_64-redhat-linux Thread model: posix gcc version 4.1.1 20060828 (Red Hat 4.1.1-20) The compile command line, with numerous unrelated *.c files chopped out of the middle: gcc -m32 -std=gnu99 -nostdinc -isystem /usr/lib/gcc/x86_64-redhat-linux/4.1.1/include -D__KLIBC__ -Iinclude -Iinclude/bits32 -Iinclude/arch/i386 -mregparm=3 -D_REGPARM=3 -Wstrict-prototypes -Wmissing-prototypes -msoft-float -fPIC -fomit-frame-pointer -march=pentium2 -Os -fno-defer-pop -fno-common -mtune=nocona -Wstrict-aliasing=2 -fvisibility=hidden -W -Wall -Wshadow -g3 -ffreestanding -fwhole-program --combine -c buffer.c testlib.c klibc/strcmp.c klibc/strcpy.c klibc/strncpy.c klibc/memcpy.c klibc/memset.c klibc/strlen.c klibc/strspn.c klibc/strxspn.c klibc/malloc.c klibc/mmap.c klibc/pause.c klibc/raise.c klibc/sleep.c klibc/sigaction.c klibc/libgcc/__udivdi3.c klibc/libgcc/__umoddi3.c klibc/libgcc/__udivmoddi4.c -o bigblob.pic The link command line: gcc -m32 -shared -Wl,-O9 -Wl,-warn-common -Wl,-soname,libfoo.so.1 -Wl,-z,initfirst -nostartfiles -nodefaultlibs -nostdlib -o tmp.so bigblob.pic Examining the result: nm tmp.so | grep -i ' u ' U memcpy I have tried the memcpy function with and without various attributes including: externally_visible, unused, noinline, regparm(0) Last of all, here is the memcpy function itself. ///////////////////////////////////////////////////////// #include <string.h> #include <stdint.h> void *memcpy(void *restrict dst, const void *restrict src, size_t n) { const char *p = src; char *q = dst; #if defined(__i386__) size_t nl = n >> 2; asm volatile ("cld ; rep ; movsl ; movl %3,%0 ; rep ; movsb":"+c" (nl), "+S"(p), "+D"(q) :"r"(n & 3)); #elif defined(__x86_64__) size_t nq = n >> 3; asm volatile ("cld ; rep ; movsq ; movl %3,%%ecx ; rep ; movsb":"+c" (nq), "+S"(p), "+D"(q) :"r"((uint32_t) (n & 7))); #else while (n--) { *q++ = *p++; } #endif return dst; } -- Summary: forgotten memcpy with -ffreestanding -fwhole-program -- combine Product: gcc Version: 4.1.1 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c AssignedTo: unassigned at gcc dot gnu dot org ReportedBy: acahalan at gmail dot com http://gcc.gnu.org/bugzilla/show_bug.cgi?id=29171