* ARM thumb-interwork libgcc asm functions have no bx
@ 2000-08-04 2:17 Giuliano Procida
0 siblings, 0 replies; 5+ messages in thread
From: Giuliano Procida @ 2000-08-04 2:17 UTC (permalink / raw)
To: gcc; +Cc: Simon Gooch
With:
../egcs-20000619/configure
--with-gcc-version-trigger=/u/gprocida/lad-tools/egcs-20000619/gcc/version.c
--host=i686-pc-linux --srcdir=../egcs-20000619 --target=arm-elf
--with-headers=../newlib-1.8.2/newlib/libc/include --enable-multilib
--without-fp --with-cpu=arm7tdmi --norecursion
and the config/arm/t-arm-elf file edited to produce normal and interworking
libgcc variants (only).
Some of the gcc/libgcc/interwork/*.o use BX, some don't (rm-elf-objdump -d
$i | grep -q bx && echo $i). The ones that do not use BX seem to all come
from:
../egcs-20000619/gcc/config/arm/lib1funcs.asm
In any case, returning from __udivsi3 to thumb code is broken. Example:
bar.c, compiled with -mthumb -mthumb-interwork
int main () {
volatile unsigned x = 20;
volatile unsigned y = 35;
unsigned z = y / x;
}
Relevant bits of objdump -d output:
bar: file format elf32-littlearm
Disassembly of section .text:
000080e0 <main>:
80e0: b590 push {r4, r7, lr}
80e2: 466f mov r7, sp
80e4: b083 sub sp, #12
80e6: ff95f002 bl b014 <____gccmain_from_thumb>
80ea: 46bc mov ip, r7
80ec: 1f3a sub r2, r7, #4
80ee: 2314 mov r3, #20
80f0: 6013 str r3, [r2, #0]
80f2: 46bc mov ip, r7
80f4: 1c3a mov r2, r7 (add r2, r7, #0)
80f6: 3a08 sub r2, #8
80f8: 2323 mov r3, #35
80fa: 6013 str r3, [r2, #0]
80fc: 46bc mov ip, r7
80fe: 1c3c mov r4, r7 (add r4, r7, #0)
8100: 3c0c sub r4, #12
8102: 46bc mov ip, r7
8104: 1c3a mov r2, r7 (add r2, r7, #0)
8106: 3a08 sub r2, #8
8108: 46bc mov ip, r7
810a: 1f3b sub r3, r7, #4
810c: 6810 ldr r0, [r2, #0]
810e: 6819 ldr r1, [r3, #0]
8110: ff84f002 bl b01c <____udivsi3_from_thumb>
8114: 1c03 mov r3, r0 (add r3, r0, #0)
8116: 1c03 mov r3, r0 (add r3, r0, #0)
8118: 6023 str r3, [r4, #0]
811a: 2000 mov r0, #0
811c: 46bd mov sp, r7
811e: bc90 pop {r4, r7}
8120: bc02 pop {r1}
8122: 4708 bx r1
00008124 <__udivsi3>:
8124: e3510000 cmp r1, #0 ; 0x0
8128: 0a00001f beq 81ac <Ldiv0>
812c: e3a03001 mov r3, #1 ; 0x1
8130: e3a02000 mov r2, #0 ; 0x0
8134: e1500001 cmp r0, r1
8138: 3a000019 bcc 81a4 <Lgot_result>
000081a4 <Lgot_result>:
81a4: e1a00002 mov r0, r2
81a8: e1a0f00e mov pc, lr
000081ac <Ldiv0>:
81ac: e52de004 str lr, [sp, -#4]!
81b0: eb000001 bl 81bc <__div0>
81b4: e3a00000 mov r0, #0 ; 0x0
81b8: e8bd8000 ldmia sp!, {pc}
000081bc <__div0>:
81bc: e1a0f00e mov pc, lr
0000b01c <____udivsi3_from_thumb>:
b01c: 4778 bx pc
b01e: 46c0 nop (mov r8,r8)
0000b020 <____udivsi3_change_to_arm>:
b020: eafff43f b 8124 <__udivsi3>
I hope this is pretty clear.
Giuliano.
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: ARM thumb-interwork libgcc asm functions have no bx
2000-08-08 2:25 Giuliano Procida
@ 2000-08-08 4:09 ` Richard Earnshaw
0 siblings, 0 replies; 5+ messages in thread
From: Richard Earnshaw @ 2000-08-08 4:09 UTC (permalink / raw)
To: Giuliano Procida; +Cc: rearnsha
Giuliano,
Can you please try the following patch. You will need to rebuild the
compiler and (at the very least) the interworking versions of libgcc.a
Richard.
* arm.h (CPP_SPEC): Use sub-spec cpp_interwork.
(CPP_INTERWORK_SPEC, CPP_INTEWORK_DEFAULT_SPC): New sub-specs.
(EXTRA_SPECS): Add them.
* arm/lib1funcs.asm: Support builds for interworking.
^ permalink raw reply [flat|nested] 5+ messages in thread
* RE: ARM thumb-interwork libgcc asm functions have no bx
@ 2000-08-08 2:25 Giuliano Procida
2000-08-08 4:09 ` Richard Earnshaw
0 siblings, 1 reply; 5+ messages in thread
From: Giuliano Procida @ 2000-08-08 2:25 UTC (permalink / raw)
To: 'Nick Clifton'; +Cc: gcc, Simon Gooch, gcc-bugs, rearnsha
Nick Clifton wrote:
> It sounds like you have a broken build of libgcc.a.
> All the functions in lib1funcs.asm come in two varieties, an ARM
> encoded version and a Thumb encoded version.
Agreed.
> The versions in your
> gcc/libgcc/interwork/*.o should all be the Thumb encoded versions not
> the ARM encoded ones.
[omitted discussion about possible (non-)interworking/Thumb/ARM libgccs]
In any case, libgcc has been compiled for ARM with thumb-interwork and this
has produced a bad library. It should be possible to either compile both ARM
(interworking) and Thumb (interworking) libgccs, or the former should be
detected as a configuration error.
> The building of the Thumb version of the lib1funcs.asm functions is
> controlled by the presence of the __thumb__ define when the library is
> built. I would guess that this value is not being defined for some
> reason.
I would imagine so.
> The definition of __thumb__ is normally controlled by the
> CPP_ISA_SPEC macro in gcc/config/arm/arm.h which gets added into the
> EXTRA_SPECS macro. I would check your spec strings to see if this is
> being defined properly.
This was a basically unmodified snapshot with the configuration I gave. I
have checked the file you mention and it seems to do the right thing for
CPP_ISA_SPEC. The problem is that xgcc is not being invoked with -mthumb
(this is removing one of the .o files, then remaking):
make GCC_FOR_TARGET="/omitted/build-gcc/gcc/xgcc -B/omitted/build-gcc/gcc/
-B/usr/local/arm-elf/bin/ -I/usr/local/arm-elf/include" \
HOST_PREFIX="" HOST_PREFIX_1="loser-" \
AR_FOR_TARGET="arm-elf-ar" \
AR_CREATE_FOR_TARGET="arm-elf-ar rc" \
AR_FLAGS_FOR_TARGET="" \
OLDCC="cc" CCLIBFLAGS="-O" CFLAGS="-g -O2" \
RANLIB_FOR_TARGET="arm-elf-ranlib" \
RANLIB_TEST_FOR_TARGET="[ -f arm-elf-ranlib ] || ( [ "i686-pc-linux-gnu" =
"arm-unknown-elf" ] && [ -f /usr/bin/ranlib -o -f /bin/ranlib ] )" \
LIBGCC2_CFLAGS="-O2 -DCROSS_COMPILE -DIN_GCC `echo -g -O2|sed -e
's/-pedantic//g' -e 's/-Wtraditional//g'` -isystem ./include -Dinhibit_libc
-fno-inline -g1 -DIN_LIBGCC2 -D__GCC_FLOAT_NOT_NEEDED " \
INCLUDES="-I. -I../../egcs-20000619/gcc -I../../egcs-20000619/gcc/config
-I../
../egcs-20000619/gcc/../include" MAYBE_USE_COLLECT2="" \
CONFIG_H="" MACHMODE_H="machmode.h machmode.def" \
LIB1ASMSRC='arm/lib1funcs.asm' \
-f libgcc.mk all
make[2]: Entering directory `/omitted/build-gcc/gcc'
for d in libgcc interwork libgcc/interwork; do \
if [ -d $d ]; then true; else mkdir $d; fi \
done
if [ -f stmp-dirs ]; then true; else touch stmp-dirs; fi
/omitted/build-gcc/gcc/xgcc -B/omitted/build-gcc/gcc/
-B/usr/local/arm-elf/bin/ -I/usr/local/arm-elf/include -O2 -DCROSS_COMPILE
-DIN_GCC -g -O2 -isystem ./include -Dinhibit_libc -fno-inline -g1
-DIN_LIBGCC2 -D__GCC_FLOAT_NOT_NEEDED -I. -I../../egcs-20000619/gcc
-I../../egcs-20000619/gc
c/config -I../../egcs-20000619/gcc/../include -mthumb-interwork -DL_udivsi3
-xassembler-with-cpp -c ../../egcs-20000619/gcc/config/arm/lib1funcs.asm -o
libgcc/interwork/_udivsi3.o
cpp: -lang-asm: linker input file unused since linking not done
rm -rf interwork/libgcc.a
[snip]
Note the lack of -mthumb! By the way. is this t-arm-elf incorrect?
CROSS_LIBGCC1 = libgcc1-asm.a
LIB1ASMSRC = arm/lib1funcs.asm
LIB1ASMFUNCS = _udivsi3 _divsi3 _umodsi3 _modsi3 _dvmd_tls _bb_init_func
_call_via_rX _interwork_call_via_rX
FPBIT = fp-bit.c
DPBIT = dp-bit.c
fp-bit.c: $(srcdir)/config/fp-bit.c
echo '#define FLOAT' > fp-bit.c
echo '#ifndef __ARMEB__' >> fp-bit.c
echo '#define FLOAT_BIT_ORDER_MISMATCH' >> fp-bit.c
echo '#endif' >> fp-bit.c
cat $(srcdir)/config/fp-bit.c >> fp-bit.c
dp-bit.c: $(srcdir)/config/fp-bit.c
echo '#ifndef __ARMEB__' > dp-bit.c
echo '#define FLOAT_BIT_ORDER_MISMATCH' >> dp-bit.c
echo '#define FLOAT_WORD_ORDER_MISMATCH' >> dp-bit.c
echo '#endif' >> dp-bit.c
cat $(srcdir)/config/fp-bit.c >> dp-bit.c
# these lines added
MULTILIB_OPTIONS += mno-thumb-interwork/mthumb-interwork
MULTILIB_DIRNAMES += normal interwork
MULTILIB_EXCEPTIONS += *mapcs-26/*mthumb-interwork*
MULTILIB_MATCHES = mbig-endian=mbe mlittle-endian=mle
EXTRA_MULTILIB_PARTS = crtbegin.o crtend.o
LIBGCC = stmp-multilib
INSTALL_LIBGCC = install-multilib
TARGET_LIBGCC2_CFLAGS = -Dinhibit_libc -fno-inline
> I hope that this help syou to track down your problem.
Well, I just need to work out what to do to get libgcc built with -mthumb.
Giuliano.
ps apologies for the long cc: list
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: ARM thumb-interwork libgcc asm functions have no bx
2000-08-04 15:16 Nick Clifton
@ 2000-08-07 2:58 ` Richard Earnshaw
0 siblings, 0 replies; 5+ messages in thread
From: Richard Earnshaw @ 2000-08-07 2:58 UTC (permalink / raw)
To: Nick Clifton; +Cc: rearnsha
> Hi Giuliano,
>
> : Some of the gcc/libgcc/interwork/*.o use BX, some don't (rm-elf-objdump -d
> : $i | grep -q bx && echo $i). The ones that do not use BX seem to all come
> : from:
> :
> : ../egcs-20000619/gcc/config/arm/lib1funcs.asm
>
> It sounds like you have a broken build of libgcc.a.
>
Nick,
I think Giuliano is right. Consider the following code snippets.
file1.c:
int foo(a, b)
{
return a / b;
}
file2.c:
int bar(a, b)
{
return a / b;
}
file3.c:
int main()
{
foo (55, 2);
bar (55, 2);
return 0;
}
gcc -O -c -minterwork file1.c
gcc -O -c -mthumb -minterwork file2.c
Now, lets link with the ARM interworking libraries:
gcc -minterwork file3.c file1.o file2.o -o arm-code
We then get the division routine from the ARM+interworking library (ARM
code): but this doesn't use a bx instruction to return, so the call from
within bar will fail to switch back to thumb mode on return.
So, lets link with the thumb interworking libraries:
gcc -minterwork -mthumb file3.c file1.o file2.o -o thumb-code
We then get the division routine from the Thumb+interworking library
(Thumb code): but this doesn't use a bx instruction either, so the call
from within foo will fail.
I'm having a think about the problem. It isn't entirely obvious what is
the best solution is (I'm not convinced we should be switching in and out
of thumb/ARM mode for such low-level routines).
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: ARM thumb-interwork libgcc asm functions have no bx
@ 2000-08-04 15:16 Nick Clifton
2000-08-07 2:58 ` Richard Earnshaw
0 siblings, 1 reply; 5+ messages in thread
From: Nick Clifton @ 2000-08-04 15:16 UTC (permalink / raw)
To: Giuliano.Procida; +Cc: gcc, Simon.Gooch
Hi Giuliano,
: Some of the gcc/libgcc/interwork/*.o use BX, some don't (rm-elf-objdump -d
: $i | grep -q bx && echo $i). The ones that do not use BX seem to all come
: from:
:
: ../egcs-20000619/gcc/config/arm/lib1funcs.asm
It sounds like you have a broken build of libgcc.a.
All the functions in lib1funcs.asm come in two varieties, an ARM
encoded version and a Thumb encoded version. The versions in your
gcc/libgcc/interwork/*.o should all be the Thumb encoded versions not
the ARM encoded ones. (And hence there should be no need for the
linker to generate interworking stubs to switch into ARM mode to call
the _udivsi3 function).
The building of the Thumb version of the lib1funcs.asm functions is
controlled by the presence of the __thumb__ define when the library is
built. I would guess that this value is not being defined for some
reason.
The definition of __thumb__ is normally controlled by the
CPP_ISA_SPEC macro in gcc/config/arm/arm.h which gets added into the
EXTRA_SPECS macro. I would check your spec strings to see if this is
being defined properly.
I hope that this help syou to track down your problem.
Cheers
Nick
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2000-08-08 4:09 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2000-08-04 2:17 ARM thumb-interwork libgcc asm functions have no bx Giuliano Procida
2000-08-04 15:16 Nick Clifton
2000-08-07 2:58 ` Richard Earnshaw
2000-08-08 2:25 Giuliano Procida
2000-08-08 4:09 ` Richard Earnshaw
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).