This is the mail archive of the
gcc-help@gcc.gnu.org
mailing list for the GCC project.
Re: Inline Assembly: Assembling ARM/Thumb-16 ADDS or ADD with status update
On 23/06/11 00:41, Jeffrey Walton wrote:
> On Tue, Jun 21, 2011 at 4:50 AM, Andrew Haley <aph@redhat.com> wrote:
>> On 21/06/11 06:21, Jeffrey Walton wrote:
>>> Hi All,
>>>
>>> ARMv6, -mthumb, and Apple's AS (1.38, probably modified).
>>>
>>> I've got a routine to add two unsigned ints and then check the carry
>>> flag in the CPSR. To perform the add, I use the Thumb-16 ADD
>>> instruction (ADDS is not available).
>>>
>>> __asm__ volatile
>>> (
>>> "ldr r4, %[xa] ;" // R4 = a
>>> "ldr r5, %[xb] ;" // R5 = b
>>> "add r6, r4, r5 ;" // R6 = R4 + R5, set status
>>> "bcc 1f ;" // jump if carry is clear
>>> "mov r5, #0 ;" // set overflow
>>> "str r5, %[xc] ;" // write it to memory
>>> "1: ;" // jump label
>>> "str r6, %[xr] ;" // result = R6
>>> : [xr] "=m" (result), [xc] "=m" (no_carry)
>>> : [xa] "m" (a), [xb] "m" (b)
>>> : "r4", "r5", "r6"
>>> );
>>>
>>> According to 'ARM® Developer Suite, v1.2', Section 2.2.8, page 2-9,
>>> the status flags are set with ADD under Thumb-16:
>>>
>>> The conditional branch instruction is the only Thumb
>>> instruction that can be executed conditionally on the
>>> value of the ALU status flags in the CPSR. All data
>>> processing instructions update these flags, except
>>> when one or more high registers are specified as
>>> operands to the MOV or ADD instructions. In these
>>> cases the flags cannot be updated.
>>>
>>> Unfortunately, the status flags are not being updated.
>>
>> Yes they are, as you'll see when you step through.
>>
>> This is a logic failure: your asm declares that it writes no_carry, but
>> it only does so if carry is set. Your asm must also write to no_carry
>> when carry is clear. Then your asm will work.
> Thanks Andrew. My bad - what you did not see was the C language
> prologue which initialized no_carry.
That does not help at all. Your asm declares that it writes no_carry,
so it must do so in both cases. The compiler can drop the initialization
to no_carry in the C language prologue because it has no effect.
Incidentally, this is a useful lesson: when you post sample code,
you must post a complete example that other people can run.
Andrew.