[LLVMbugs] [Bug 23297] New: Extended asm %Qx/%Rx are backwards on big-endian ARMv7

bugzilla-daemon at llvm.org bugzilla-daemon at llvm.org
Mon Apr 20 11:49:26 PDT 2015


https://llvm.org/bugs/show_bug.cgi?id=23297

            Bug ID: 23297
           Summary: Extended asm %Qx/%Rx are backwards on big-endian ARMv7
           Product: clang
           Version: 3.5
          Hardware: Other
                OS: other
            Status: NEW
          Severity: normal
          Priority: P
         Component: Driver
          Assignee: unassignedclangbugs at nondot.org
          Reporter: solra at bizna.name
                CC: llvmbugs at cs.uiuc.edu
    Classification: Unclassified

This bug revolves around an obscure case in a compatible reimplementation of an
essentially undocumented aspect of a GCC extension. Here goes.

Example code: (compile with "-O3 -target armv7a-eabi" and either
"-mlittle-endian" or "-mbig-endian")

#include <stdio.h>
void test() {
  long long var;
  asm("MRRC p3, 0, %Q0, %R0, cr0":"=r"(var):);
  var = var + 1;
  printf("%016llX\n", var);
}

In GCC's extended asm for ARM targets, Q and R indicate, respectively, the
least significant and most significant register of a register pair. The given
example is a transfer from a 64-bit coprocessor register (cr0 of coprocessor
#3) to two core registers (the low-order half and the high-order half of
"var").

Regardless of whether I compile with -mlittle-endian or -mbig-endian, r0 is
given as the low register and r1 as the high register:

   8:   ec510300        mrrc    3, 0, r0, r1, cr0

But the following two instructions demonstrate that this order is incorrect on
big-endian:

Little-endian: (r0 is low, r1 is high)
   c:   e2902001        adds    r2, r0, #1
  10:   e2a13000        adc     r3, r1, #0
Big-endian: (r0 is high, r1 is low)
   c:   e2913001        adds    r3, r1, #1
  10:   e2a02000        adc     r2, r0, #0

GCC 4.6, on the other hand, handles this correctly:

Little-endian:
   8:   ec532300        mrrc    3, 0, r2, r3, cr0
Big-endian:
   8:   ec523300        mrrc    3, 0, r3, r2, cr0

Unrelatedly, it is interesting to compare GCC's optimization of this function
to Clang's... GCC saves, uses, and restores some wholly unnecessary scratch
registers, but also performs a tail call optimization, which Clang doesn't (and
can't, since it saves the frame pointer while GCC doesn't).

-- 
You are receiving this mail because:
You are on the CC list for the bug.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-bugs/attachments/20150420/80c5827a/attachment.html>


More information about the llvm-bugs mailing list