implement rdar://7432000 - signed negate should codegen as NSW.

While I'm in there, adjust pointer to member adjustments as well.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@106955 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Chris Lattner 2010-06-26 20:27:24 +00:00
Родитель abfe094ce7
Коммит e70ffd6311
4 изменённых файлов: 28 добавлений и 10 удалений

Просмотреть файл

@ -997,13 +997,13 @@ Value *ScalarExprEmitter::EmitCastExpr(CastExpr *CE) {
std::swap(DerivedDecl, BaseDecl);
if (llvm::Constant *Adj =
CGF.CGM.GetNonVirtualBaseClassOffset(DerivedDecl,
CE->getBasePath())) {
CGF.CGM.GetNonVirtualBaseClassOffset(DerivedDecl, CE->getBasePath())){
if (CE->getCastKind() == CastExpr::CK_DerivedToBaseMemberPointer)
Src = Builder.CreateSub(Src, Adj, "adj");
Src = Builder.CreateNSWSub(Src, Adj, "adj");
else
Src = Builder.CreateAdd(Src, Adj, "adj");
Src = Builder.CreateNSWAdd(Src, Adj, "adj");
}
return Src;
}
@ -1117,6 +1117,11 @@ Value *ScalarExprEmitter::VisitUnaryMinus(const UnaryOperator *E) {
Value *Op = Visit(E->getSubExpr());
if (Op->getType()->isFPOrFPVectorTy())
return Builder.CreateFNeg(Op, "neg");
// Signed integer overflow is undefined behavior.
if (E->getType()->isSignedIntegerType())
return Builder.CreateNSWNeg(Op, "neg");
return Builder.CreateNeg(Op, "neg");
}

Просмотреть файл

@ -43,13 +43,13 @@ int main ()
int res_i;
/* vec_abs */
vsc = vec_abs(vsc); // CHECK: sub <16 x i8> zeroinitializer
vsc = vec_abs(vsc); // CHECK: sub nsw <16 x i8> zeroinitializer
// CHECK: @llvm.ppc.altivec.vmaxsb
vs = vec_abs(vs); // CHECK: sub <8 x i16> zeroinitializer
vs = vec_abs(vs); // CHECK: sub nsw <8 x i16> zeroinitializer
// CHECK: @llvm.ppc.altivec.vmaxsh
vi = vec_abs(vi); // CHECK: sub <4 x i32> zeroinitializer
vi = vec_abs(vi); // CHECK: sub nsw <4 x i32> zeroinitializer
// CHECK: @llvm.ppc.altivec.vmaxsw
vf = vec_abs(vf); // CHECK: and <4 x i32>

Просмотреть файл

@ -1,4 +1,4 @@
// RUN: %clang_cc1 %s -emit-llvm -o -
// RUN: %clang_cc1 %s -emit-llvm -o - | FileCheck %s
// PR1895
// sizeof function
@ -119,3 +119,16 @@ void f9(struct S *x) {
void f10() {
__builtin_sin(0);
}
// Tests for signed integer overflow stuff.
// rdar://7432000
void f11() {
// CHECK: define void @f11
extern volatile int f11G, a, b;
// CHECK: add nsw i32
f11G = a + b;
// CHECK: sub nsw i32
f11G = a - b;
// CHECK: sub nsw i32 0,
f11G = -a;
}

Просмотреть файл

@ -68,11 +68,11 @@ void f() {
// CHECK: store i64 -1, i64* @_ZN5Casts2paE
pa = 0;
// CHECK: [[ADJ:%[a-zA-Z0-9\.]+]] = add i64 {{.*}}, 4
// CHECK: [[ADJ:%[a-zA-Z0-9\.]+]] = add nsw i64 {{.*}}, 4
// CHECK: store i64 [[ADJ]], i64* @_ZN5Casts2pcE
pc = pa;
// CHECK: [[ADJ:%[a-zA-Z0-9\.]+]] = sub i64 {{.*}}, 4
// CHECK: [[ADJ:%[a-zA-Z0-9\.]+]] = sub nsw i64 {{.*}}, 4
// CHECK: store i64 [[ADJ]], i64* @_ZN5Casts2paE
pa = static_cast<int A::*>(pc);
}