aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/MC/MCExpr.cpp
diff options
context:
space:
mode:
authorSanjay Patel <spatel@rotateright.com>2016-05-20 14:09:41 +0000
committerSanjay Patel <spatel@rotateright.com>2016-05-20 14:09:41 +0000
commit42bbe77009b0875524f9f14b176c757393bf5da3 (patch)
treeaa07dc879197f1025e8154aa1efe0600c0059e7e /llvm/lib/MC/MCExpr.cpp
parenta053101c9516485afe9fb55daa0493ab8acc0eb8 (diff)
downloadllvm-42bbe77009b0875524f9f14b176c757393bf5da3.zip
llvm-42bbe77009b0875524f9f14b176c757393bf5da3.tar.gz
llvm-42bbe77009b0875524f9f14b176c757393bf5da3.tar.bz2
[MCExpr] avoid UB via negation of INT_MIN
I accidentally exposed a bug in MCExpr::evaluateAsRelocatableImpl() with the test file added in: http://reviews.llvm.org/rL269977 Differential Revision: http://reviews.llvm.org/D20434 llvm-svn: 270218
Diffstat (limited to 'llvm/lib/MC/MCExpr.cpp')
-rw-r--r--llvm/lib/MC/MCExpr.cpp7
1 files changed, 5 insertions, 2 deletions
diff --git a/llvm/lib/MC/MCExpr.cpp b/llvm/lib/MC/MCExpr.cpp
index 4dfb971..6f90ff8 100644
--- a/llvm/lib/MC/MCExpr.cpp
+++ b/llvm/lib/MC/MCExpr.cpp
@@ -663,8 +663,10 @@ bool MCExpr::evaluateAsRelocatableImpl(MCValue &Res, const MCAssembler *Asm,
/// -(a - b + const) ==> (b - a - const)
if (Value.getSymA() && !Value.getSymB())
return false;
+
+ // The cast avoids undefined behavior if the constant is INT64_MIN.
Res = MCValue::get(Value.getSymB(), Value.getSymA(),
- -Value.getConstant());
+ -(uint64_t)Value.getConstant());
break;
case MCUnaryExpr::Not:
if (!Value.isAbsolute())
@@ -697,9 +699,10 @@ bool MCExpr::evaluateAsRelocatableImpl(MCValue &Res, const MCAssembler *Asm,
return false;
case MCBinaryExpr::Sub:
// Negate RHS and add.
+ // The cast avoids undefined behavior if the constant is INT64_MIN.
return EvaluateSymbolicAdd(Asm, Layout, Addrs, InSet, LHSValue,
RHSValue.getSymB(), RHSValue.getSymA(),
- -RHSValue.getConstant(), Res);
+ -(uint64_t)RHSValue.getConstant(), Res);
case MCBinaryExpr::Add:
return EvaluateSymbolicAdd(Asm, Layout, Addrs, InSet, LHSValue,