[llvm-commits] [llvm-gcc-4.2] r80449 - /llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp

Dan Gohman gohman at apple.com
Sat Aug 29 16:31:57 PDT 2009


Author: djg
Date: Sat Aug 29 18:31:56 2009
New Revision: 80449

URL: http://llvm.org/viewvc/llvm-project?rev=80449&view=rev
Log:
Support inline asm matching constraints where the input operand
is wider than the output operand. This is done by truncating the
input down to the narrower type, which appears to be consistent
with what GCC does. This is only enabled on little-endian
targets, as I haven't looked at what should happen on big-endian
targets.

This allows llvm-gcc to compile FD_ZERO on GLIBC, which is used
by SPEC 186.crafty, for example.

Modified:
    llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp

Modified: llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp?rev=80449&r1=80448&r2=80449&view=diff

==============================================================================
--- llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp (original)
+++ llvm-gcc-4.2/trunk/gcc/llvm-convert.cpp Sat Aug 29 18:31:56 2009
@@ -4487,12 +4487,25 @@
           }
           unsigned OTyBits = TD.getTypeSizeInBits(OTy);
           unsigned OpTyBits = TD.getTypeSizeInBits(OpTy);
-          if (OTyBits == 0 || OpTyBits == 0 || OTyBits < OpTyBits) {
+          if (OTyBits == 0 || OpTyBits == 0) {
             error("%Hunsupported inline asm: input constraint with a matching "
                   "output constraint of incompatible type!",
                   &EXPR_LOCATION(exp));
             return 0;
+          } else if (OTyBits < OpTyBits) {
+            // Truncate the input to match the output.
+            Op = CastToAnyType(Op, !TYPE_UNSIGNED(type),
+                               OTy, CallResultIsSigned[Match]);
+            // Big endian may be doable; I just don't know what the
+            // behavior is supposed to be.
+            if (BYTES_BIG_ENDIAN) {
+              error("%Hunsupported inline asm: input constraint with a "
+                    "matching output constraint of incompatible type!",
+                    &EXPR_LOCATION(exp));
+            }
+            OpTy = Op->getType();
           } else if (OTyBits > OpTyBits) {
+            // Extend the input to match the output.
             Op = CastToAnyType(Op, !TYPE_UNSIGNED(type),
                                OTy, CallResultIsSigned[Match]);
             if (BYTES_BIG_ENDIAN) {





More information about the llvm-commits mailing list