This is the mail archive of the
mailing list for the binutils project.
Re: Branch instruction(b/bl) for ARM
- To: Myunghui Ryu <mega74 at vitals dot co dot kr>
- Subject: Re: Branch instruction(b/bl) for ARM
- From: Nick Clifton <nickc at cambridge dot redhat dot com>
- Date: 30 Jul 2001 19:09:16 +0100
- Cc: Binutils <binutils at sourceware dot cygnus dot com>
- References: <3B64ADEE.64ED506C@vitals.co.kr>
> but, b/bl instructions branch the recursive like folllow:
> 00000000 <_mainCRTStartup>:
> 28: ebfffffe bl 28 <_mainCRTStartup+0x28>
> 28: R_ARM_PC24 memset
> 2c: ebfffffe bl 2c <_mainCRTStartup+0x2c>
> Why was happend above problem?
This is not actually a problem, although it may appear confusing.
What has happened is that the assembler has stored the value "-8" in
the offset field of the BL instruction, so that it appears that the
branch will go to itself.
But... the instruction also has a reloc associated with it. This is
the "28: R_ARM_PC24 memset" line in the disassembler output. This is
a directive to the linker to change this instruction so that instead
of branching back on itself it branches to the 'memset' function.
If you look at the disassembly of a fully linked program you will see
that this instruction has changed so that it really is a branch and
link to the memset function.
So why does the assembler store "-8" in the offset field ? The answer
is that this is the PC bias in the current generation of ARM CPUs. So
all the linker has to do is to add the offset from the BL instruction
to the 'memset' function to the -8 and the correct value is computed.
The reason that linker does not generate this -8 value for itself is:
a) the ARM ELF ABI specifies that it should not do so
b) with this scheme the linker is independent of any changes in the
ARM's pipeline. If a new generations of ARMs came along that had
a PC bias of, say, 12 bytes, then all the assembler would have to
do is to store -12 in the offset field and the linker would
continue to work.
I hope that this makes things clear.