[uclibc-ng-devel,06/32,ARM,FDPIC] rtld: Add startup code

Message ID 20180704155605.1892-7-christophe.lyon@st.com
State New
Headers show
Series
  • FDPIC ABI for ARM
Related show

Commit Message

Christophe Lyon July 4, 2018, 3:55 p.m.
Implement _start: compute parameters for __self_reloc, and give
control to the user program.

	* ldso/ldso/arm/dl-startup.h: Implement _start for __FDPIC__.

Signed-off-by: Mickaël Guêné <mickael.guene@st.com>
Signed-off-by: Christophe Lyon <christophe.lyon@st.com>

Comments

Thomas Petazzoni July 5, 2018, 8:37 a.m. | #1
Hello Christophe,

On Wed, 4 Jul 2018 17:55:19 +0200, Christophe Lyon wrote:
> Implement _start: compute parameters for __self_reloc, and give
> control to the user program.
> 
> 	* ldso/ldso/arm/dl-startup.h: Implement _start for __FDPIC__.
> 
> Signed-off-by: Mickaël Guêné <mickael.guene@st.com>
> Signed-off-by: Christophe Lyon <christophe.lyon@st.com>

This is very likely me not doing things correctly, but this change
doesn't build, because it uses ARM instructions on Thumb2-only systems.
I'm trying to build a Cortex-M4 FDPIC toolchain with your patches. My
gcc has the following details (it is gcc 8.1.0 on top of which I have
backported your ARM FDPIC patches):

/home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc -v
Using built-in specs.
COLLECT_GCC=/home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc.br_real
COLLECT_LTO_WRAPPER=/home/test/outputs/arm-fdpic/host/libexec/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/lto-wrapper
Target: arm-buildroot-uclinuxfdpiceabi
Configured with: ./configure --prefix=/home/test/outputs/arm-fdpic/host --sysconfdir=/home/test/outputs/arm-fdpic/host/etc --localstatedir=/home/test/outputs/arm-fdpic/host/var --enable-shared --disable-static --disable-gtk-doc --disable-gtk-doc-html --disable-doc --disable-docs --disable-documentation --disable-debug --with-xmlto=no --with-fop=no --disable-dependency-tracking --target=arm-buildroot-uclinuxfdpiceabi --with-sysroot=/home/test/outputs/arm-fdpic/host/arm-buildroot-uclinuxfdpiceabi/sysroot --disable-__cxa_atexit --with-gnu-ld --disable-libssp --disable-multilib --with-gmp=/home/test/outputs/arm-fdpic/host --with-mpc=/home/test/outputs/arm-fdpic/host --with-mpfr=/home/test/outputs/arm-fdpic/host --with-pkgversion='Buildroot 2018.08-git-00602-g3ecd583' --with-bugurl=http://bugs.buildroot.net/ --disable-libquadmath --disable-libsanitizer --disable-tls --disable-libmudflap --enable-threads --without-isl --without-cloog --with-float=soft --disable-decimal-float --with-abi=aapcs-linux --with-cpu=cortex-m4 --with-float=soft --with-mode=thumb --enable-languages=c --disable-shared --without-headers --disable-threads --with-newlib --disable-largefile --disable-nls
Thread model: single
gcc version 8.1.0 (Buildroot 2018.08-git-00602-g3ecd583) 

I.e, it generates code for Cortex-M4, soft-float, Thumb by default.

The dl-startup code fails to build with:

/home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc -c ldso/ldso/ldso.c -o ldso/ldso/ldso.oS -Wall -Wstrict-prototypes -Wstrict-aliasing -Wno-nonnull-compare -funsigned-char -fno-builtin -fno-asm -fmerge-all-constants -msoft-float -st
d=gnu99 -mlittle-endian -fno-stack-protector -nostdinc -I./include -I./include -include libc-symbols.h -I./libc/sysdeps/linux/arm -I./libc/sysdeps/linux -I./ldso/ldso/arm -I./ldso/include -I. -Os -fstrict-aliasing -I./libpthread/linuxthreads/sysdeps/unix/
sysv/linux/arm -I./libpthread/linuxthreads/sysdeps/arm -I./libpthread/linuxthreads/sysdeps/unix/sysv/linux -I./libpthread/linuxthreads/sysdeps/pthread -I./libpthread/linuxthreads -I./libpthread -I./libc/sysdeps/linux/common -isystem /home/test/outputs/arm
-fdpic/host/lib/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/include-fixed -isystem /home/test/outputs/arm-fdpic/host/lib/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/include -I/home/test/outputs/arm-fdpic/build/linux-headers-4.17.4/usr/include/ -DNDEBUG -DNOT_IN
_libc -DIS_IN_rtld -fno-stack-protector -fno-omit-frame-pointer -fno-unwind-tables -fno-asynchronous-unwind-tables -I./ldso/ldso/arm -I./ldso/include -I./ldso/ldso -DUCLIBC_RUNTIME_PREFIX=\"/\" -DUCLIBC_LDSO=\"ld-uClibc.so.1\" -DIN_LIB=rtld -mfdpic -DSHAR
ED -DLDSO_ELFINTERP=\"arm/elfinterp.c\" -DLDSO_MULTILIB_DIR=\"lib/\" -MT ldso/ldso/ldso.oS -MD -MP -MF ldso/ldso/.ldso.oS.dep
In file included from ./include/bits/waitstatus.h:72,
                 from ./include/stdlib.h:44,
                 from ./ldso/include/ldso.h:33,
                 from ldso/ldso/ldso.c:32:
./ldso/include/dl-syscall.h: In function '_dl_pread':
./ldso/include/dl-syscall.h:169:69: warning: right shift count >= width of type [-Wshift-count-overflow]
  return __syscall_pread(fd, buf, count, 0, __LONG_LONG_PAIR((offset >> 32), (offset & 0xffffffff)));
                                                                     ^~
./include/endian.h:52:39: note: in definition of macro '__LONG_LONG_PAIR'
 # define __LONG_LONG_PAIR(HI, LO) LO, HI
                                       ^~
In file included from ./ldso/ldso/arm/dl-inlines.h:1,
                 from ./ldso/include/ldso.h:183,
                 from ldso/ldso/ldso.c:32:
./ldso/ldso/arm/../fdpic/dl-inlines.h: In function '_dl_funcdesc_for':
./ldso/ldso/arm/../fdpic/dl-inlines.h:180:8: warning: assignment to 'struct funcdesc_value **' from incompatible pointer type 'void **' [-Wincompatible-pointer-types]
  entry = htab_find_slot(ht, entry_point, 1, hash_pointer, eq_pointer);
        ^
In file included from ldso/ldso/ldso.c:45:
ldso/ldso/arm/elfinterp.c: In function '_dl_linux_resolver':
ldso/ldso/arm/elfinterp.c:95:9: warning: returning 'volatile struct funcdesc_value *' from a function with return type 'long unsigned int' makes integer from pointer without a cast [-Wint-conversion]
  return got_entry;
         ^~~~~~~~~
ldso/ldso/arm/elfinterp.c: In function '_dl_do_reloc':
ldso/ldso/arm/elfinterp.c:364:65: warning: passing argument 1 of '_dl_funcdesc_for' makes pointer from integer without a cast [-Wint-conversion]
      reloc_value = (unsigned long) _dl_funcdesc_for(symbol_addr + reloc_value, sym_ref.tpnt->loadaddr.got_value);
                                                     ~~~~~~~~~~~~^~~~~~~~~~~~~
In file included from ./ldso/ldso/arm/dl-inlines.h:1,
                 from ./ldso/include/ldso.h:183,
                 from ldso/ldso/ldso.c:32:
./ldso/ldso/arm/../fdpic/dl-inlines.h:165:25: note: expected 'void *' but argument is of type 'long unsigned int'
 _dl_funcdesc_for (void *entry_point, void *got_value)
                   ~~~~~~^~~~~~~~~~~
In file included from ldso/ldso/ldso.c:45:
ldso/ldso/arm/elfinterp.c: In function '_dl_do_lazy_reloc':
ldso/ldso/arm/elfinterp.c:429:23: warning: assignment to 'void *' from 'unsigned int' makes pointer from integer without a cast [-Wint-conversion]
      dst->entry_point = DL_RELOC_ADDR(tpnt->loadaddr, dst->entry_point);
                       ^
In file included from ldso/ldso/ldso.c:86:
ldso/ldso/dl-startup.c: In function '_dl_start':
ldso/ldso/dl-startup.c:313:13: warning: variable 'strtab' set but not used [-Wunused-but-set-variable]
       char *strtab;
             ^~~~~~
ldso/ldso/dl-startup.c:125:13: warning: variable 'got' set but not used [-Wunused-but-set-variable]
  ElfW(Addr) got;
             ^~~
In file included from ./ldso/ldso/arm/dl-sysdep.h:135,
                 from ./ldso/include/dl-defs.h:77,
                 from ./ldso/include/dl-string.h:15,
                 from ./ldso/include/ldso.h:53,
...skipping...
In file included from ./ldso/ldso/arm/dl-inlines.h:1,
                 from ./ldso/include/ldso.h:183,
                 from ldso/ldso/ldso.c:32:
./ldso/ldso/arm/../fdpic/dl-inlines.h:165:25: note: expected 'void *' but argument is of type 'long unsigned int'
 _dl_funcdesc_for (void *entry_point, void *got_value)
                   ~~~~~~^~~~~~~~~~~
In file included from ldso/ldso/ldso.c:45:
ldso/ldso/arm/elfinterp.c: In function '_dl_do_lazy_reloc':
ldso/ldso/arm/elfinterp.c:429:23: warning: assignment to 'void *' from 'unsigned int' makes pointer from integer without a cast [-Wint-conversion]
      dst->entry_point = DL_RELOC_ADDR(tpnt->loadaddr, dst->entry_point);
                       ^
In file included from ldso/ldso/ldso.c:86:
ldso/ldso/dl-startup.c: In function '_dl_start':
ldso/ldso/dl-startup.c:313:13: warning: variable 'strtab' set but not used [-Wunused-but-set-variable]
       char *strtab;
             ^~~~~~
ldso/ldso/dl-startup.c:125:13: warning: variable 'got' set but not used [-Wunused-but-set-variable]
  ElfW(Addr) got;
             ^~~
In file included from ./ldso/ldso/arm/dl-sysdep.h:135,
                 from ./ldso/include/dl-defs.h:77,
                 from ./ldso/include/dl-string.h:15,
                 from ./ldso/include/ldso.h:53,
                 from ldso/ldso/ldso.c:32:
ldso/ldso/dl-hash.c: In function '_dl_find_hash':
./ldso/ldso/arm/../fdpic/dl-sysdep.h:111:4: warning: pointer/integer type mismatch in conditional expression
    : DL_RELOC_ADDR ((TPNT)->loadaddr, (SYM)->st_value))
    ^
ldso/ldso/dl-hash.c:384:20: note: in expansion of macro 'DL_FIND_HASH_VALUE'
     return (char *)DL_FIND_HASH_VALUE(tpnt, type_class, sym);
                    ^~~~~~~~~~~~~~~~~~
/tmp/cceTVltl.s: Assembler messages:
/tmp/cceTVltl.s:14: Error: selected processor does not support ARM opcodes
/tmp/cceTVltl.s:19: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r4,pc,#8'
/tmp/cceTVltl.s:20: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r1,.L__ROFIXUP_LIST__'
/tmp/cceTVltl.s:21: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r1,r1,r4'
/tmp/cceTVltl.s:22: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r2,.L__ROFIXUP_END__'
/tmp/cceTVltl.s:23: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r2,r2,r4'
/tmp/cceTVltl.s:24: Error: attempt to use an ARM instruction on a Thumb-only processor -- `movs r0,r8'
/tmp/cceTVltl.s:25: Error: attempt to use an ARM instruction on a Thumb-only processor -- `moveq r0,r7'
/tmp/cceTVltl.s:26: Error: attempt to use an ARM instruction on a Thumb-only processor -- `push {r7,r8,r9,r10}'
/tmp/cceTVltl.s:27: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl __self_reloc'
/tmp/cceTVltl.s:28: Error: attempt to use an ARM instruction on a Thumb-only processor -- `pop {r7,r8,r9,r10}'
/tmp/cceTVltl.s:29: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r1,r7'
/tmp/cceTVltl.s:30: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r2,r8'
/tmp/cceTVltl.s:31: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r3,r9'
/tmp/cceTVltl.s:32: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,sp'
/tmp/cceTVltl.s:33: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r5,sp,#8'
/tmp/cceTVltl.s:34: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub sp,sp,#16'
/tmp/cceTVltl.s:35: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r4,[sp,#4]'
/tmp/cceTVltl.s:36: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r5,[sp,#0]'
/tmp/cceTVltl.s:37: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r9,r0'
/tmp/cceTVltl.s:38: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,r9'
/tmp/cceTVltl.s:39: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl _dl_start'
/tmp/cceTVltl.s:40: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r10,.L_dl_fini_gotofffuncdesc'
/tmp/cceTVltl.s:41: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r10,r10,r4'
/tmp/cceTVltl.s:42: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r5,[sp,#8]'
/tmp/cceTVltl.s:43: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r9,[sp,#12]'
/tmp/cceTVltl.s:44: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add sp,sp,#16'
/tmp/cceTVltl.s:45: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bx r5'
/tmp/cceTVltl.s:47: Error: attempt to use an ARM instruction on a Thumb-only processor -- `b .loopforever'
make[2]: *** [ldso/ldso/ldso.oS] Error 1
make[1]: *** [/home/test/outputs/arm-fdpic/build/uclibc-1.0.30/.stamp_built] Error 2
make: *** [_all] Error 2

Any idea ?

Best regards,

Thomas Petazzoni
Christophe Lyon July 5, 2018, 8:55 a.m. | #2
On Thu, 5 Jul 2018 at 10:37, Thomas Petazzoni
<thomas.petazzoni@bootlin.com> wrote:
>
> Hello Christophe,
>
> On Wed, 4 Jul 2018 17:55:19 +0200, Christophe Lyon wrote:
> > Implement _start: compute parameters for __self_reloc, and give
> > control to the user program.
> >
> >       * ldso/ldso/arm/dl-startup.h: Implement _start for __FDPIC__.
> >
> > Signed-off-by: Mickaël Guêné <mickael.guene@st.com>
> > Signed-off-by: Christophe Lyon <christophe.lyon@st.com>
>
> This is very likely me not doing things correctly, but this change
> doesn't build, because it uses ARM instructions on Thumb2-only systems.
> I'm trying to build a Cortex-M4 FDPIC toolchain with your patches. My
> gcc has the following details (it is gcc 8.1.0 on top of which I have
> backported your ARM FDPIC patches):
>
> /home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc -v
> Using built-in specs.
> COLLECT_GCC=/home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc.br_real
> COLLECT_LTO_WRAPPER=/home/test/outputs/arm-fdpic/host/libexec/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/lto-wrapper
> Target: arm-buildroot-uclinuxfdpiceabi
> Configured with: ./configure --prefix=/home/test/outputs/arm-fdpic/host --sysconfdir=/home/test/outputs/arm-fdpic/host/etc --localstatedir=/home/test/outputs/arm-fdpic/host/var --enable-shared --disable-static --disable-gtk-doc --disable-gtk-doc-html --disable-doc --disable-docs --disable-documentation --disable-debug --with-xmlto=no --with-fop=no --disable-dependency-tracking --target=arm-buildroot-uclinuxfdpiceabi --with-sysroot=/home/test/outputs/arm-fdpic/host/arm-buildroot-uclinuxfdpiceabi/sysroot --disable-__cxa_atexit --with-gnu-ld --disable-libssp --disable-multilib --with-gmp=/home/test/outputs/arm-fdpic/host --with-mpc=/home/test/outputs/arm-fdpic/host --with-mpfr=/home/test/outputs/arm-fdpic/host --with-pkgversion='Buildroot 2018.08-git-00602-g3ecd583' --with-bugurl=http://bugs.buildroot.net/ --disable-libquadmath --disable-libsanitizer --disable-tls --disable-libmudflap --enable-threads --without-isl --without-cloog --with-float=soft --disable-decimal-float --with-abi=aapcs-linux --with-cpu=cortex-m4 --with-float=soft --with-mode=thumb --enable-languages=c --disable-shared --without-headers --disable-threads --with-newlib --disable-largefile --disable-nls
> Thread model: single
> gcc version 8.1.0 (Buildroot 2018.08-git-00602-g3ecd583)
>
> I.e, it generates code for Cortex-M4, soft-float, Thumb by default.
>
> The dl-startup code fails to build with:
>
> /home/test/outputs/arm-fdpic/host/bin/arm-buildroot-uclinuxfdpiceabi-gcc -c ldso/ldso/ldso.c -o ldso/ldso/ldso.oS -Wall -Wstrict-prototypes -Wstrict-aliasing -Wno-nonnull-compare -funsigned-char -fno-builtin -fno-asm -fmerge-all-constants -msoft-float -st
> d=gnu99 -mlittle-endian -fno-stack-protector -nostdinc -I./include -I./include -include libc-symbols.h -I./libc/sysdeps/linux/arm -I./libc/sysdeps/linux -I./ldso/ldso/arm -I./ldso/include -I. -Os -fstrict-aliasing -I./libpthread/linuxthreads/sysdeps/unix/
> sysv/linux/arm -I./libpthread/linuxthreads/sysdeps/arm -I./libpthread/linuxthreads/sysdeps/unix/sysv/linux -I./libpthread/linuxthreads/sysdeps/pthread -I./libpthread/linuxthreads -I./libpthread -I./libc/sysdeps/linux/common -isystem /home/test/outputs/arm
> -fdpic/host/lib/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/include-fixed -isystem /home/test/outputs/arm-fdpic/host/lib/gcc/arm-buildroot-uclinuxfdpiceabi/8.1.0/include -I/home/test/outputs/arm-fdpic/build/linux-headers-4.17.4/usr/include/ -DNDEBUG -DNOT_IN
> _libc -DIS_IN_rtld -fno-stack-protector -fno-omit-frame-pointer -fno-unwind-tables -fno-asynchronous-unwind-tables -I./ldso/ldso/arm -I./ldso/include -I./ldso/ldso -DUCLIBC_RUNTIME_PREFIX=\"/\" -DUCLIBC_LDSO=\"ld-uClibc.so.1\" -DIN_LIB=rtld -mfdpic -DSHAR
> ED -DLDSO_ELFINTERP=\"arm/elfinterp.c\" -DLDSO_MULTILIB_DIR=\"lib/\" -MT ldso/ldso/ldso.oS -MD -MP -MF ldso/ldso/.ldso.oS.dep
> In file included from ./include/bits/waitstatus.h:72,
>                  from ./include/stdlib.h:44,
>                  from ./ldso/include/ldso.h:33,
>                  from ldso/ldso/ldso.c:32:
> ./ldso/include/dl-syscall.h: In function '_dl_pread':
> ./ldso/include/dl-syscall.h:169:69: warning: right shift count >= width of type [-Wshift-count-overflow]
>   return __syscall_pread(fd, buf, count, 0, __LONG_LONG_PAIR((offset >> 32), (offset & 0xffffffff)));
>                                                                      ^~
> ./include/endian.h:52:39: note: in definition of macro '__LONG_LONG_PAIR'
>  # define __LONG_LONG_PAIR(HI, LO) LO, HI
>                                        ^~
> In file included from ./ldso/ldso/arm/dl-inlines.h:1,
>                  from ./ldso/include/ldso.h:183,
>                  from ldso/ldso/ldso.c:32:
> ./ldso/ldso/arm/../fdpic/dl-inlines.h: In function '_dl_funcdesc_for':
> ./ldso/ldso/arm/../fdpic/dl-inlines.h:180:8: warning: assignment to 'struct funcdesc_value **' from incompatible pointer type 'void **' [-Wincompatible-pointer-types]
>   entry = htab_find_slot(ht, entry_point, 1, hash_pointer, eq_pointer);
>         ^
> In file included from ldso/ldso/ldso.c:45:
> ldso/ldso/arm/elfinterp.c: In function '_dl_linux_resolver':
> ldso/ldso/arm/elfinterp.c:95:9: warning: returning 'volatile struct funcdesc_value *' from a function with return type 'long unsigned int' makes integer from pointer without a cast [-Wint-conversion]
>   return got_entry;
>          ^~~~~~~~~
> ldso/ldso/arm/elfinterp.c: In function '_dl_do_reloc':
> ldso/ldso/arm/elfinterp.c:364:65: warning: passing argument 1 of '_dl_funcdesc_for' makes pointer from integer without a cast [-Wint-conversion]
>       reloc_value = (unsigned long) _dl_funcdesc_for(symbol_addr + reloc_value, sym_ref.tpnt->loadaddr.got_value);
>                                                      ~~~~~~~~~~~~^~~~~~~~~~~~~
> In file included from ./ldso/ldso/arm/dl-inlines.h:1,
>                  from ./ldso/include/ldso.h:183,
>                  from ldso/ldso/ldso.c:32:
> ./ldso/ldso/arm/../fdpic/dl-inlines.h:165:25: note: expected 'void *' but argument is of type 'long unsigned int'
>  _dl_funcdesc_for (void *entry_point, void *got_value)
>                    ~~~~~~^~~~~~~~~~~
> In file included from ldso/ldso/ldso.c:45:
> ldso/ldso/arm/elfinterp.c: In function '_dl_do_lazy_reloc':
> ldso/ldso/arm/elfinterp.c:429:23: warning: assignment to 'void *' from 'unsigned int' makes pointer from integer without a cast [-Wint-conversion]
>       dst->entry_point = DL_RELOC_ADDR(tpnt->loadaddr, dst->entry_point);
>                        ^
> In file included from ldso/ldso/ldso.c:86:
> ldso/ldso/dl-startup.c: In function '_dl_start':
> ldso/ldso/dl-startup.c:313:13: warning: variable 'strtab' set but not used [-Wunused-but-set-variable]
>        char *strtab;
>              ^~~~~~
> ldso/ldso/dl-startup.c:125:13: warning: variable 'got' set but not used [-Wunused-but-set-variable]
>   ElfW(Addr) got;
>              ^~~
> In file included from ./ldso/ldso/arm/dl-sysdep.h:135,
>                  from ./ldso/include/dl-defs.h:77,
>                  from ./ldso/include/dl-string.h:15,
>                  from ./ldso/include/ldso.h:53,
> ...skipping...
> In file included from ./ldso/ldso/arm/dl-inlines.h:1,
>                  from ./ldso/include/ldso.h:183,
>                  from ldso/ldso/ldso.c:32:
> ./ldso/ldso/arm/../fdpic/dl-inlines.h:165:25: note: expected 'void *' but argument is of type 'long unsigned int'
>  _dl_funcdesc_for (void *entry_point, void *got_value)
>                    ~~~~~~^~~~~~~~~~~
> In file included from ldso/ldso/ldso.c:45:
> ldso/ldso/arm/elfinterp.c: In function '_dl_do_lazy_reloc':
> ldso/ldso/arm/elfinterp.c:429:23: warning: assignment to 'void *' from 'unsigned int' makes pointer from integer without a cast [-Wint-conversion]
>       dst->entry_point = DL_RELOC_ADDR(tpnt->loadaddr, dst->entry_point);
>                        ^
> In file included from ldso/ldso/ldso.c:86:
> ldso/ldso/dl-startup.c: In function '_dl_start':
> ldso/ldso/dl-startup.c:313:13: warning: variable 'strtab' set but not used [-Wunused-but-set-variable]
>        char *strtab;
>              ^~~~~~
> ldso/ldso/dl-startup.c:125:13: warning: variable 'got' set but not used [-Wunused-but-set-variable]
>   ElfW(Addr) got;
>              ^~~
> In file included from ./ldso/ldso/arm/dl-sysdep.h:135,
>                  from ./ldso/include/dl-defs.h:77,
>                  from ./ldso/include/dl-string.h:15,
>                  from ./ldso/include/ldso.h:53,
>                  from ldso/ldso/ldso.c:32:
> ldso/ldso/dl-hash.c: In function '_dl_find_hash':
> ./ldso/ldso/arm/../fdpic/dl-sysdep.h:111:4: warning: pointer/integer type mismatch in conditional expression
>     : DL_RELOC_ADDR ((TPNT)->loadaddr, (SYM)->st_value))
>     ^
> ldso/ldso/dl-hash.c:384:20: note: in expansion of macro 'DL_FIND_HASH_VALUE'
>      return (char *)DL_FIND_HASH_VALUE(tpnt, type_class, sym);
>                     ^~~~~~~~~~~~~~~~~~
> /tmp/cceTVltl.s: Assembler messages:
> /tmp/cceTVltl.s:14: Error: selected processor does not support ARM opcodes
> /tmp/cceTVltl.s:19: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r4,pc,#8'
> /tmp/cceTVltl.s:20: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r1,.L__ROFIXUP_LIST__'
> /tmp/cceTVltl.s:21: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r1,r1,r4'
> /tmp/cceTVltl.s:22: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r2,.L__ROFIXUP_END__'
> /tmp/cceTVltl.s:23: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r2,r2,r4'
> /tmp/cceTVltl.s:24: Error: attempt to use an ARM instruction on a Thumb-only processor -- `movs r0,r8'
> /tmp/cceTVltl.s:25: Error: attempt to use an ARM instruction on a Thumb-only processor -- `moveq r0,r7'
> /tmp/cceTVltl.s:26: Error: attempt to use an ARM instruction on a Thumb-only processor -- `push {r7,r8,r9,r10}'
> /tmp/cceTVltl.s:27: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl __self_reloc'
> /tmp/cceTVltl.s:28: Error: attempt to use an ARM instruction on a Thumb-only processor -- `pop {r7,r8,r9,r10}'
> /tmp/cceTVltl.s:29: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r1,r7'
> /tmp/cceTVltl.s:30: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r2,r8'
> /tmp/cceTVltl.s:31: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r3,r9'
> /tmp/cceTVltl.s:32: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,sp'
> /tmp/cceTVltl.s:33: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r5,sp,#8'
> /tmp/cceTVltl.s:34: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub sp,sp,#16'
> /tmp/cceTVltl.s:35: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r4,[sp,#4]'
> /tmp/cceTVltl.s:36: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r5,[sp,#0]'
> /tmp/cceTVltl.s:37: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r9,r0'
> /tmp/cceTVltl.s:38: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,r9'
> /tmp/cceTVltl.s:39: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl _dl_start'
> /tmp/cceTVltl.s:40: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r10,.L_dl_fini_gotofffuncdesc'
> /tmp/cceTVltl.s:41: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r10,r10,r4'
> /tmp/cceTVltl.s:42: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r5,[sp,#8]'
> /tmp/cceTVltl.s:43: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r9,[sp,#12]'
> /tmp/cceTVltl.s:44: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add sp,sp,#16'
> /tmp/cceTVltl.s:45: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bx r5'
> /tmp/cceTVltl.s:47: Error: attempt to use an ARM instruction on a Thumb-only processor -- `b .loopforever'
> make[2]: *** [ldso/ldso/ldso.oS] Error 1
> make[1]: *** [/home/test/outputs/arm-fdpic/build/uclibc-1.0.30/.stamp_built] Error 2
> make: *** [_all] Error 2
>
> Any idea ?
>

Thanks for checking that. I did build with a GCC defaulting to Thumb
mode, but it still uses a CPU that supports ARM mode, so I missed
these problems.


> Best regards,
>
> Thomas Petazzoni
> --
> Thomas Petazzoni, CTO, Bootlin (formerly Free Electrons)
> Embedded Linux and Kernel engineering
> https://bootlin.com
Thomas Petazzoni July 5, 2018, 8:59 a.m. | #3
Hello,

On Thu, 5 Jul 2018 10:55:26 +0200, Christophe Lyon wrote:

> > /tmp/cceTVltl.s: Assembler messages:
> > /tmp/cceTVltl.s:14: Error: selected processor does not support ARM opcodes
> > /tmp/cceTVltl.s:19: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r4,pc,#8'
> > /tmp/cceTVltl.s:20: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r1,.L__ROFIXUP_LIST__'
> > /tmp/cceTVltl.s:21: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r1,r1,r4'
> > /tmp/cceTVltl.s:22: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r2,.L__ROFIXUP_END__'
> > /tmp/cceTVltl.s:23: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r2,r2,r4'
> > /tmp/cceTVltl.s:24: Error: attempt to use an ARM instruction on a Thumb-only processor -- `movs r0,r8'
> > /tmp/cceTVltl.s:25: Error: attempt to use an ARM instruction on a Thumb-only processor -- `moveq r0,r7'
> > /tmp/cceTVltl.s:26: Error: attempt to use an ARM instruction on a Thumb-only processor -- `push {r7,r8,r9,r10}'
> > /tmp/cceTVltl.s:27: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl __self_reloc'
> > /tmp/cceTVltl.s:28: Error: attempt to use an ARM instruction on a Thumb-only processor -- `pop {r7,r8,r9,r10}'
> > /tmp/cceTVltl.s:29: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r1,r7'
> > /tmp/cceTVltl.s:30: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r2,r8'
> > /tmp/cceTVltl.s:31: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r3,r9'
> > /tmp/cceTVltl.s:32: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,sp'
> > /tmp/cceTVltl.s:33: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r5,sp,#8'
> > /tmp/cceTVltl.s:34: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub sp,sp,#16'
> > /tmp/cceTVltl.s:35: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r4,[sp,#4]'
> > /tmp/cceTVltl.s:36: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r5,[sp,#0]'
> > /tmp/cceTVltl.s:37: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r9,r0'
> > /tmp/cceTVltl.s:38: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,r9'
> > /tmp/cceTVltl.s:39: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl _dl_start'
> > /tmp/cceTVltl.s:40: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r10,.L_dl_fini_gotofffuncdesc'
> > /tmp/cceTVltl.s:41: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r10,r10,r4'
> > /tmp/cceTVltl.s:42: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r5,[sp,#8]'
> > /tmp/cceTVltl.s:43: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r9,[sp,#12]'
> > /tmp/cceTVltl.s:44: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add sp,sp,#16'
> > /tmp/cceTVltl.s:45: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bx r5'
> > /tmp/cceTVltl.s:47: Error: attempt to use an ARM instruction on a Thumb-only processor -- `b .loopforever'
> > make[2]: *** [ldso/ldso/ldso.oS] Error 1
> > make[1]: *** [/home/test/outputs/arm-fdpic/build/uclibc-1.0.30/.stamp_built] Error 2
> > make: *** [_all] Error 2
> >
> > Any idea ?
> >  
> 
> Thanks for checking that. I did build with a GCC defaulting to Thumb
> mode, but it still uses a CPU that supports ARM mode, so I missed
> these problems.

Thanks for your quick feedback.

So you mean that you tested building for a Cortex-A platform and not
Cortex-M ?

Since this FDPIC work is mainly intended for noMMU platforms, my first
test was to build a toolchain targeting Cortex-M, which only support
Thumb 2.

Best regards,

Thomas
Christophe Lyon July 5, 2018, 9:02 a.m. | #4
On Thu, 5 Jul 2018 at 10:59, Thomas Petazzoni
<thomas.petazzoni@bootlin.com> wrote:
>
> Hello,
>
> On Thu, 5 Jul 2018 10:55:26 +0200, Christophe Lyon wrote:
>
> > > /tmp/cceTVltl.s: Assembler messages:
> > > /tmp/cceTVltl.s:14: Error: selected processor does not support ARM opcodes
> > > /tmp/cceTVltl.s:19: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r4,pc,#8'
> > > /tmp/cceTVltl.s:20: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r1,.L__ROFIXUP_LIST__'
> > > /tmp/cceTVltl.s:21: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r1,r1,r4'
> > > /tmp/cceTVltl.s:22: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r2,.L__ROFIXUP_END__'
> > > /tmp/cceTVltl.s:23: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r2,r2,r4'
> > > /tmp/cceTVltl.s:24: Error: attempt to use an ARM instruction on a Thumb-only processor -- `movs r0,r8'
> > > /tmp/cceTVltl.s:25: Error: attempt to use an ARM instruction on a Thumb-only processor -- `moveq r0,r7'
> > > /tmp/cceTVltl.s:26: Error: attempt to use an ARM instruction on a Thumb-only processor -- `push {r7,r8,r9,r10}'
> > > /tmp/cceTVltl.s:27: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl __self_reloc'
> > > /tmp/cceTVltl.s:28: Error: attempt to use an ARM instruction on a Thumb-only processor -- `pop {r7,r8,r9,r10}'
> > > /tmp/cceTVltl.s:29: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r1,r7'
> > > /tmp/cceTVltl.s:30: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r2,r8'
> > > /tmp/cceTVltl.s:31: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r3,r9'
> > > /tmp/cceTVltl.s:32: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,sp'
> > > /tmp/cceTVltl.s:33: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub r5,sp,#8'
> > > /tmp/cceTVltl.s:34: Error: attempt to use an ARM instruction on a Thumb-only processor -- `sub sp,sp,#16'
> > > /tmp/cceTVltl.s:35: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r4,[sp,#4]'
> > > /tmp/cceTVltl.s:36: Error: attempt to use an ARM instruction on a Thumb-only processor -- `str r5,[sp,#0]'
> > > /tmp/cceTVltl.s:37: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r9,r0'
> > > /tmp/cceTVltl.s:38: Error: attempt to use an ARM instruction on a Thumb-only processor -- `mov r4,r9'
> > > /tmp/cceTVltl.s:39: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bl _dl_start'
> > > /tmp/cceTVltl.s:40: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r10,.L_dl_fini_gotofffuncdesc'
> > > /tmp/cceTVltl.s:41: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add r10,r10,r4'
> > > /tmp/cceTVltl.s:42: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r5,[sp,#8]'
> > > /tmp/cceTVltl.s:43: Error: attempt to use an ARM instruction on a Thumb-only processor -- `ldr r9,[sp,#12]'
> > > /tmp/cceTVltl.s:44: Error: attempt to use an ARM instruction on a Thumb-only processor -- `add sp,sp,#16'
> > > /tmp/cceTVltl.s:45: Error: attempt to use an ARM instruction on a Thumb-only processor -- `bx r5'
> > > /tmp/cceTVltl.s:47: Error: attempt to use an ARM instruction on a Thumb-only processor -- `b .loopforever'
> > > make[2]: *** [ldso/ldso/ldso.oS] Error 1
> > > make[1]: *** [/home/test/outputs/arm-fdpic/build/uclibc-1.0.30/.stamp_built] Error 2
> > > make: *** [_all] Error 2
> > >
> > > Any idea ?
> > >
> >
> > Thanks for checking that. I did build with a GCC defaulting to Thumb
> > mode, but it still uses a CPU that supports ARM mode, so I missed
> > these problems.
>
> Thanks for your quick feedback.
>
> So you mean that you tested building for a Cortex-A platform and not
> Cortex-M ?
>
Yes, the original work was actually for Cortex-R.

> Since this FDPIC work is mainly intended for noMMU platforms, my first
> test was to build a toolchain targeting Cortex-M, which only support
> Thumb 2.
That was a good thing to do :)

> Best regards,
>
> Thomas
> --
> Thomas Petazzoni, CTO, Bootlin (formerly Free Electrons)
> Embedded Linux and Kernel engineering
> https://bootlin.com

Patch

diff --git a/ldso/ldso/arm/dl-startup.h b/ldso/ldso/arm/dl-startup.h
index d15264f..b5f7d73 100644
--- a/ldso/ldso/arm/dl-startup.h
+++ b/ldso/ldso/arm/dl-startup.h
@@ -8,6 +8,71 @@ 
 #include <features.h>
 #include <bits/arm_bx.h>
 
+#if defined(__FDPIC__)
+#if !defined(__thumb__) || defined(__thumb2__)
+__asm__(
+	"	.arm\n"
+	"	.text\n"
+	"	.globl  _start\n"
+	"	.type   _start,%function\n"
+	"_start:\n"
+	/* We compute the parameters for __self_reloc:
+	   - r0 is a pointer to the loadmap (either from r8 or r7 if rtld is
+	   lauched in standalone mode)
+	   - r1 is a pointer to the start of .rofixup section
+	   - r2 is a pointer to the last word of .rofixup section
+
+	   __self_reloc will fix indirect addresses in .rofixup
+	   section and will return the relocated GOT value.
+	*/
+	"	sub	r4, pc, #8\n"
+	"	ldr	r1, .L__ROFIXUP_LIST__\n"
+	"	add	r1, r1, r4\n"
+	"	ldr	r2, .L__ROFIXUP_END__\n"
+	"	add	r2, r2, r4\n"
+	"	movs	r0, r8\n"
+	"	moveq	r0, r7\n"
+	"	push	{r7, r8, r9, r10}\n"
+	"	bl	__self_reloc;\n"
+	"	pop	{r7, r8, r9, r10}\n"
+	/* We compute the parameters for dl_start(). See DL_START()
+	   macro below.  The address of the user entry point is
+	   returned in dl_main_funcdesc (on stack).  */
+	"	mov	r1, r7\n"
+	"	mov	r2, r8\n"
+	"	mov	r3, r9\n"
+	"	mov	r4, sp\n"
+	"	sub	r5, sp, #8\n"
+	"	sub sp, sp, #16\n"
+	"	str	r4, [sp, #4]\n"
+	"	str	r5, [sp, #0]\n"
+	"	mov	r9, r0\n"
+	/* Save r9 into r4, to preserve the GOT pointer.  */
+	"	mov	r4, r9\n"
+	"	bl _dl_start;\n"
+	/* Now compute parameters for entry point according to FDPIC ABI.  */
+	"	ldr	r10, .L_dl_fini_gotofffuncdesc\n"
+	/* Save GOT value from r4.  */
+	"	add	r10, r10, r4\n"
+	"	ldr	r5, [sp, #8]\n"
+	"	ldr	r9, [sp, #12]\n"
+	"	add sp, sp, #16\n"
+	"	bx	r5\n"
+	".loopforever:\n"
+	"	b	.loopforever\n"
+	".L__ROFIXUP_LIST__:\n"
+	"	.word	__ROFIXUP_LIST__ - _start\n"
+	".L__ROFIXUP_END__:\n"
+	"	.word	__ROFIXUP_END__ - _start\n"
+	".L_dl_fini_gotofffuncdesc:\n"
+	"	.word	_dl_fini(GOTOFFFUNCDESC)\n"
+	"	.size	_start,.-_start\n"
+	"	.previous\n"
+);
+#else /* !defined(__thumb__) */
+#error Thumb-1 is not supported
+#endif /* !defined(__thumb__) */
+#else /* defined(__FDPIC__) */
 #if !defined(__thumb__)
 __asm__(
     "	.text\n"
@@ -121,7 +186,7 @@  __asm__(
 	".previous\n"
 );
 #endif
-
+#endif /* defined(__FDPIC__) */
 
 /* Get a pointer to the argv array.  On many platforms this can be just
  * the address of the first argument, on other platforms we need to