summaryrefslogtreecommitdiff
path: root/lib/CodeGen/SelectionDAG
diff options
context:
space:
mode:
authorTim Northover <tnorthover@apple.com>2014-06-15 09:27:20 +0000
committerTim Northover <tnorthover@apple.com>2014-06-15 09:27:20 +0000
commit40ed1d89b19856777b2072ab8a0ae89d54b2e440 (patch)
treecbcee58ce76a9972c569a0e763a4aea1af98a4c9 /lib/CodeGen/SelectionDAG
parent8bfc50e4a976476425e8f2ba7e71d7d14b48b474 (diff)
downloadllvm-40ed1d89b19856777b2072ab8a0ae89d54b2e440.tar.gz
llvm-40ed1d89b19856777b2072ab8a0ae89d54b2e440.tar.bz2
llvm-40ed1d89b19856777b2072ab8a0ae89d54b2e440.tar.xz
LegalizeDAG: make sure cast is unsigned before using FP_TO_UINT.
It's valid to use FP_TO_SINT when asking for a smaller type (e.g. all "unsigned int16" values fit into a "signed int32"), but the reverse isn't true. Unfortunately, I'm not actually aware of any architecture with asymmetric FP_TO_SINT and FP_TO_UINT handling and the logic happens to work in the symmetric case, so I can't actually write a test for this. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@210986 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/SelectionDAG')
-rw-r--r--lib/CodeGen/SelectionDAG/LegalizeDAG.cpp5
1 files changed, 4 insertions, 1 deletions
diff --git a/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp b/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
index c76a52abe6..48eb86c49c 100644
--- a/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
+++ b/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
@@ -2650,12 +2650,15 @@ SDValue SelectionDAGLegalize::PromoteLegalFP_TO_INT(SDValue LegalOp,
NewOutTy = (MVT::SimpleValueType)(NewOutTy.getSimpleVT().SimpleTy+1);
assert(NewOutTy.isInteger() && "Ran out of possibilities!");
+ // A larger signed type can hold all unsigned values of the requested type,
+ // so using FP_TO_SINT is valid
if (TLI.isOperationLegalOrCustom(ISD::FP_TO_SINT, NewOutTy)) {
OpToUse = ISD::FP_TO_SINT;
break;
}
- if (TLI.isOperationLegalOrCustom(ISD::FP_TO_UINT, NewOutTy)) {
+ // However, if the value may be < 0.0, we *must* use some FP_TO_SINT.
+ if (!isSigned && TLI.isOperationLegalOrCustom(ISD::FP_TO_UINT, NewOutTy)) {
OpToUse = ISD::FP_TO_UINT;
break;
}