This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Compiling libgcc not optimized

Good moorning,

I am trying to compile libgcc for arm-none-eabi target from scratch, since I need to compare Floating Point SW emulation on an ARM Cortex-M4 and Risc-V based processors. The problem is that by default GCC includes the optimized version of FP SW emulation functions which is ieee754-sf.S. 

Does anyone knows how to exclude ieee754-sf.S in the libgcc compilation process? In particular how to configure GCC?

Thanks,

Parents
  • Cloning GCC 11.0.0 repository

    How old is the toolchain's compiler? Trying to build libgcc.a from gcc-11.0.0 using gcc-7.3.1 might not work. The arm-none-eabi-gcc version 7.3.1 doesn't understand:

    -Wno-error=format-diag
    #pragma GCC target ("general-regs-only")

    etc. that are in the gcc-10.2.0 source. The build fails.


    Even though CC_FOR_TARGET is specified, the configuration insists on building the compiler and using this in-tree, freshly built compiler for building libgcc.a

    That can be seen in the configuration messages:

    checking where to find the target as... pre-installed
    checking where to find the target cc... just compiled
    checking where to find the target gcc... just compiled

    and inside the gcc/configure script:

      if test $ok = yes; then
        # An in-tree tool is available and we can use it
        CC_FOR_TARGET='$$r/$(HOST_SUBDIR)/gcc/xgcc -B$$r/$(HOST_SUBDIR)/gcc/'
        { $as_echo "$as_me:${as_lineno-$LINENO}: result: just compiled" >&5
    $as_echo "just compiled" >&6; }


    It seems that libgcc.a wants to be built with the in-tree compiler.

    If you allow that, then libgcc.a from gcc-11.0.0 can be built using the in-tree gcc-11.0.0 compiler (which the build process first builds).

    If you don't allow that, then ensure that the source code corresponds to the prebuilt toolchain version you want to use. This resolves the errors about unsupported code fragments.

    But it still compiles libgcc.a using the in-tree compiler and not using the prebuilt toolchain's compiler. To achieve that, a change must be made inside gcc/configure file; that change is shown some lines below.


    st couldn't download st-stm32cubeide_1-5-0_8698_20201117_1050_amd64_sh.zip for me; threw a 504 Gateway timeout.

    So decided to use "GNU Arm Embedded Toolchain: Version 7-2018-q2-update" from Arm instead, which seems to be the one on which the st's toolchain is based:

    gcc-arm-none-eabi-7-2018-q2-update-linux.tar.bz2
    gcc-arm-none-eabi-7-2018-q2-update-src.tar.bz2


    Test with unmodified prebuilt toolchain:

    # Extract the prebuilt toolchain as /home/user/prebuilt
    
    arm-none-eabi-gcc -nostdlib -mcpu=cortex-m4 -mthumb -mfloat-abi=soft a.c -lgcc -Wl,-cref
    
    Cross Reference Table
    
    Symbol          File
    __adddf3		/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_dadd	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
                    /tmp/cc6LutZe.o
    __aeabi_ddiv	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
                    /tmp/cc6LutZe.o
    __aeabi_dmul	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __aeabi_drsub   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_dsub    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_f2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_i2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_l2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_ui2d    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_ul2d    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __divdf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __extendsfdf2   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatdidf     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatsidf     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatundidf   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatunsidf   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __muldf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __subdf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    _start          /tmp/cc6LutZe.o
    
    
    strings -a a.out | grep GCC:
    GCC: (GNU Tools for Arm Embedded Processors 7-2018-q2-update) 7.3.1 20180622 (release) [ARM/embedded-7-branch revision 261907]
    
    
    # Dissasembly snippets. You can confirm that these are optimized by
    # comparing them with the ieee754-df.S file
    00008000 <_start>:
        8022:	f000 f819 	bl	8058 <__adddf3>
        8036:	f000 faef 	bl	8618 <__aeabi_ddiv>
    00008058 <__adddf3>:
        8082:	ea4f 5454 	mov.w	r4, r4, lsr #21
        8086:	ebd4 5555 	rsbs	r5, r4, r5, lsr #21
        808a:	bfb8      	it	lt
        808c:	426d      	neglt	r5, r5
        808e:	dd0c      	ble.n	80aa <__adddf3+0x52>
        8090:	442c      	add	r4, r5
        8092:	ea80 0202 	eor.w	r2, r0, r2
        8096:	ea81 0303 	eor.w	r3, r1, r3
        809a:	ea82 0000 	eor.w	r0, r2, r0
        809e:	ea83 0101 	eor.w	r1, r3, r1
        80a2:	ea80 0202 	eor.w	r2, r0, r2
        80a6:	ea81 0303 	eor.w	r3, r1, r3
    00008618 <__aeabi_ddiv>:
        864c:	ea4f 3303 	mov.w	r3, r3, lsl #12
        8650:	f04f 5580 	mov.w	r5, #268435456	; 0x10000000
        8654:	ea45 1313 	orr.w	r3, r5, r3, lsr #4
        8658:	ea43 6312 	orr.w	r3, r3, r2, lsr #24
        865c:	ea4f 2202 	mov.w	r2, r2, lsl #8
        8660:	ea45 1511 	orr.w	r5, r5, r1, lsr #4
        8664:	ea45 6510 	orr.w	r5, r5, r0, lsr #24
        8668:	ea4f 2600 	mov.w	r6, r0, lsl #8


    Build libgcc.a

    # gcc has the source of the compiler included in the toolchain
    
    cd gcc
    ./contrib/download_prerequisites
    
    # Now apply the diff/patch to libgcc files
    
    # Modify gcc/configure.
    
    $as_echo_n "checking where to find the target cc... " >&6; }
    ...
    else
      ok=yes # <----- change this to no
      case " ${configdirs} " in
    ...
    $as_echo_n "checking where to find the target gcc... " >&6; }
    ...
    else
      ok=yes # <----- change this to no
      case " ${configdirs} " in
    ...
    
    # If this change isn't made, the libgcc.a will be built with the freshly
    # built compiler, not with the one shipped with the prebuilt toolchain.
    # That may not create problems, so this is another option available if
    # it is okay to build libgcc.a with the freshly built complier, given that
    # the gcc source used corresponds to the toolchain.
    
    # With this change, the in-tree gcc compiler will still be
    # built (so some time is wasted on it), but libgcc.a will be built using
    # the compiler shipped with the prebuilt toolchain.
    
    
    export PATH=$PATH:/home/user/prebuilt/bin
    mkdir ./build
    cd ./build
    
    ../gcc/configure \
    CC_FOR_TARGET=arm-none-eabi-gcc \
    GCC_FOR_TARGET=arm-none-eabi-gcc \
    --target=arm-none-eabi --prefix=/home/user/cross \
    --with-multilib --with-multilib-list=rmprofile --enable-languages=c
    
    make all-target-libgcc && make install-strip-target-libgcc
    
    # The build will still make a fresh gcc, but it will use the prebuilt's
    # gcc when building the libgcc.a. Confirm that by reading the build output/
    # config logs. The prefix/installation directory contains only the lib
    # directory and no binaries.


    Test the new libgcc.a

    # Copy
    # /home/user/cross/lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a
    # to
    # /home/user/prebuilt/lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a
    
    # Build the sample again with prebuilt's compiler
    arm-none-eabi-gcc -nostdlib -mcpu=cortex-m4 -mthumb -mfloat-abi=soft a.c -lgcc -Wl,-cref
    Cross Reference Table
    
    Symbol          File
    __aeabi_dadd    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(adddf3.o)
                    /tmp/ccF8QeNy.o
    __aeabi_ddiv    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(divdf3.o)
                    /tmp/ccF8QeNy.o
    _start          /tmp/ccF8QeNy.o
    
    strings -a a.out | grep GCC:
    GCC: (GNU Tools for Arm Embedded Processors 7-2018-q2-update) 7.3.1 20180622 (release) [ARM/embedded-7-branch revision 261907]
    
    # Dissasembly snippets. Not the same as optimized ones above.
    00008000 <_start>:
        8022:	f000 f813 	bl	804c <__aeabi_dadd>
        8036:	f000 fb1b 	bl	8670 <__aeabi_ddiv>
    0000804c <__aeabi_dadd>:
        804c:	e92d 43f0 	stmdb	sp!, {r4, r5, r6, r7, r8, r9, lr}
        8050:	0fcf      	lsrs	r7, r1, #31
        8052:	ea4f 7ed3 	mov.w	lr, r3, lsr #31
        8056:	f3c1 0513 	ubfx	r5, r1, #0, #20
    00008670 <__aeabi_ddiv>:
        8670:	e92d 4ff0 	stmdb	sp!, {r4, r5, r6, r7, r8, r9, sl, fp, lr}
        8674:	f3c1 560a 	ubfx	r6, r1, #20, #11
        8678:	f3c1 0413 	ubfx	r4, r1, #0, #20
        867c:	4605      	mov	r5, r0

Reply
  • Cloning GCC 11.0.0 repository

    How old is the toolchain's compiler? Trying to build libgcc.a from gcc-11.0.0 using gcc-7.3.1 might not work. The arm-none-eabi-gcc version 7.3.1 doesn't understand:

    -Wno-error=format-diag
    #pragma GCC target ("general-regs-only")

    etc. that are in the gcc-10.2.0 source. The build fails.


    Even though CC_FOR_TARGET is specified, the configuration insists on building the compiler and using this in-tree, freshly built compiler for building libgcc.a

    That can be seen in the configuration messages:

    checking where to find the target as... pre-installed
    checking where to find the target cc... just compiled
    checking where to find the target gcc... just compiled

    and inside the gcc/configure script:

      if test $ok = yes; then
        # An in-tree tool is available and we can use it
        CC_FOR_TARGET='$$r/$(HOST_SUBDIR)/gcc/xgcc -B$$r/$(HOST_SUBDIR)/gcc/'
        { $as_echo "$as_me:${as_lineno-$LINENO}: result: just compiled" >&5
    $as_echo "just compiled" >&6; }


    It seems that libgcc.a wants to be built with the in-tree compiler.

    If you allow that, then libgcc.a from gcc-11.0.0 can be built using the in-tree gcc-11.0.0 compiler (which the build process first builds).

    If you don't allow that, then ensure that the source code corresponds to the prebuilt toolchain version you want to use. This resolves the errors about unsupported code fragments.

    But it still compiles libgcc.a using the in-tree compiler and not using the prebuilt toolchain's compiler. To achieve that, a change must be made inside gcc/configure file; that change is shown some lines below.


    st couldn't download st-stm32cubeide_1-5-0_8698_20201117_1050_amd64_sh.zip for me; threw a 504 Gateway timeout.

    So decided to use "GNU Arm Embedded Toolchain: Version 7-2018-q2-update" from Arm instead, which seems to be the one on which the st's toolchain is based:

    gcc-arm-none-eabi-7-2018-q2-update-linux.tar.bz2
    gcc-arm-none-eabi-7-2018-q2-update-src.tar.bz2


    Test with unmodified prebuilt toolchain:

    # Extract the prebuilt toolchain as /home/user/prebuilt
    
    arm-none-eabi-gcc -nostdlib -mcpu=cortex-m4 -mthumb -mfloat-abi=soft a.c -lgcc -Wl,-cref
    
    Cross Reference Table
    
    Symbol          File
    __adddf3		/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_dadd	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
                    /tmp/cc6LutZe.o
    __aeabi_ddiv	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
                    /tmp/cc6LutZe.o
    __aeabi_dmul	/home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __aeabi_drsub   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_dsub    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_f2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_i2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_l2d     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_ui2d    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __aeabi_ul2d    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __divdf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __extendsfdf2   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatdidf     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatsidf     /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatundidf   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __floatunsidf   /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    __muldf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_muldivdf3.o)
    __subdf3        /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(_arm_addsubdf3.o)
    _start          /tmp/cc6LutZe.o
    
    
    strings -a a.out | grep GCC:
    GCC: (GNU Tools for Arm Embedded Processors 7-2018-q2-update) 7.3.1 20180622 (release) [ARM/embedded-7-branch revision 261907]
    
    
    # Dissasembly snippets. You can confirm that these are optimized by
    # comparing them with the ieee754-df.S file
    00008000 <_start>:
        8022:	f000 f819 	bl	8058 <__adddf3>
        8036:	f000 faef 	bl	8618 <__aeabi_ddiv>
    00008058 <__adddf3>:
        8082:	ea4f 5454 	mov.w	r4, r4, lsr #21
        8086:	ebd4 5555 	rsbs	r5, r4, r5, lsr #21
        808a:	bfb8      	it	lt
        808c:	426d      	neglt	r5, r5
        808e:	dd0c      	ble.n	80aa <__adddf3+0x52>
        8090:	442c      	add	r4, r5
        8092:	ea80 0202 	eor.w	r2, r0, r2
        8096:	ea81 0303 	eor.w	r3, r1, r3
        809a:	ea82 0000 	eor.w	r0, r2, r0
        809e:	ea83 0101 	eor.w	r1, r3, r1
        80a2:	ea80 0202 	eor.w	r2, r0, r2
        80a6:	ea81 0303 	eor.w	r3, r1, r3
    00008618 <__aeabi_ddiv>:
        864c:	ea4f 3303 	mov.w	r3, r3, lsl #12
        8650:	f04f 5580 	mov.w	r5, #268435456	; 0x10000000
        8654:	ea45 1313 	orr.w	r3, r5, r3, lsr #4
        8658:	ea43 6312 	orr.w	r3, r3, r2, lsr #24
        865c:	ea4f 2202 	mov.w	r2, r2, lsl #8
        8660:	ea45 1511 	orr.w	r5, r5, r1, lsr #4
        8664:	ea45 6510 	orr.w	r5, r5, r0, lsr #24
        8668:	ea4f 2600 	mov.w	r6, r0, lsl #8


    Build libgcc.a

    # gcc has the source of the compiler included in the toolchain
    
    cd gcc
    ./contrib/download_prerequisites
    
    # Now apply the diff/patch to libgcc files
    
    # Modify gcc/configure.
    
    $as_echo_n "checking where to find the target cc... " >&6; }
    ...
    else
      ok=yes # <----- change this to no
      case " ${configdirs} " in
    ...
    $as_echo_n "checking where to find the target gcc... " >&6; }
    ...
    else
      ok=yes # <----- change this to no
      case " ${configdirs} " in
    ...
    
    # If this change isn't made, the libgcc.a will be built with the freshly
    # built compiler, not with the one shipped with the prebuilt toolchain.
    # That may not create problems, so this is another option available if
    # it is okay to build libgcc.a with the freshly built complier, given that
    # the gcc source used corresponds to the toolchain.
    
    # With this change, the in-tree gcc compiler will still be
    # built (so some time is wasted on it), but libgcc.a will be built using
    # the compiler shipped with the prebuilt toolchain.
    
    
    export PATH=$PATH:/home/user/prebuilt/bin
    mkdir ./build
    cd ./build
    
    ../gcc/configure \
    CC_FOR_TARGET=arm-none-eabi-gcc \
    GCC_FOR_TARGET=arm-none-eabi-gcc \
    --target=arm-none-eabi --prefix=/home/user/cross \
    --with-multilib --with-multilib-list=rmprofile --enable-languages=c
    
    make all-target-libgcc && make install-strip-target-libgcc
    
    # The build will still make a fresh gcc, but it will use the prebuilt's
    # gcc when building the libgcc.a. Confirm that by reading the build output/
    # config logs. The prefix/installation directory contains only the lib
    # directory and no binaries.


    Test the new libgcc.a

    # Copy
    # /home/user/cross/lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a
    # to
    # /home/user/prebuilt/lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a
    
    # Build the sample again with prebuilt's compiler
    arm-none-eabi-gcc -nostdlib -mcpu=cortex-m4 -mthumb -mfloat-abi=soft a.c -lgcc -Wl,-cref
    Cross Reference Table
    
    Symbol          File
    __aeabi_dadd    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(adddf3.o)
                    /tmp/ccF8QeNy.o
    __aeabi_ddiv    /home/user/prebuilt/bin/../lib/gcc/arm-none-eabi/7.3.1/thumb/v7e-m/libgcc.a(divdf3.o)
                    /tmp/ccF8QeNy.o
    _start          /tmp/ccF8QeNy.o
    
    strings -a a.out | grep GCC:
    GCC: (GNU Tools for Arm Embedded Processors 7-2018-q2-update) 7.3.1 20180622 (release) [ARM/embedded-7-branch revision 261907]
    
    # Dissasembly snippets. Not the same as optimized ones above.
    00008000 <_start>:
        8022:	f000 f813 	bl	804c <__aeabi_dadd>
        8036:	f000 fb1b 	bl	8670 <__aeabi_ddiv>
    0000804c <__aeabi_dadd>:
        804c:	e92d 43f0 	stmdb	sp!, {r4, r5, r6, r7, r8, r9, lr}
        8050:	0fcf      	lsrs	r7, r1, #31
        8052:	ea4f 7ed3 	mov.w	lr, r3, lsr #31
        8056:	f3c1 0513 	ubfx	r5, r1, #0, #20
    00008670 <__aeabi_ddiv>:
        8670:	e92d 4ff0 	stmdb	sp!, {r4, r5, r6, r7, r8, r9, sl, fp, lr}
        8674:	f3c1 560a 	ubfx	r6, r1, #20, #11
        8678:	f3c1 0413 	ubfx	r4, r1, #0, #20
        867c:	4605      	mov	r5, r0

Children
No data