[llvm-branch-commits] [cfe-branch] r311799 - Merging r311695:
Hans Wennborg via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Fri Aug 25 13:27:58 PDT 2017
Author: hans
Date: Fri Aug 25 13:27:58 2017
New Revision: 311799
URL: http://llvm.org/viewvc/llvm-project?rev=311799&view=rev
Log:
Merging r311695:
------------------------------------------------------------------------
r311695 | rsmith | 2017-08-24 13:10:33 -0700 (Thu, 24 Aug 2017) | 9 lines
[ubsan] PR34266: When sanitizing the 'this' value for a member function that happens to be a lambda call operator, use the lambda's 'this' pointer, not the captured enclosing 'this' pointer (if any).
Do not sanitize the 'this' pointer of a member call operator for a lambda with
no capture-default, since that call operator can legitimately be called with a
null this pointer from the static invoker function. Any actual call with a null
this pointer should still be caught in the caller (if it is being sanitized).
This reinstates r311589 (reverted in r311680) with the above fix.
------------------------------------------------------------------------
Modified:
cfe/branches/release_50/ (props changed)
cfe/branches/release_50/include/clang/AST/DeclCXX.h
cfe/branches/release_50/lib/CodeGen/CodeGenFunction.cpp
cfe/branches/release_50/test/CodeGenCXX/catch-undef-behavior.cpp
Propchange: cfe/branches/release_50/
------------------------------------------------------------------------------
--- svn:mergeinfo (original)
+++ svn:mergeinfo Fri Aug 25 13:27:58 2017
@@ -1,4 +1,4 @@
/cfe/branches/type-system-rewrite:134693-134817
-/cfe/trunk:308455,308722,308824,308897,308996,309054,309058,309112-309113,309263,309382-309383,309488,309503,309523,309569,309607,309633,309636,309640,309722,309752,309975,310006,310158,310191,310359,310516,310672,310691-310692,310694,310700,310704,310706,310776,310804,310829,310983,311115,311182,311330,311391,311397,311443,311532,311601
+/cfe/trunk:308455,308722,308824,308897,308996,309054,309058,309112-309113,309263,309382-309383,309488,309503,309523,309569,309607,309633,309636,309640,309722,309752,309975,310006,310158,310191,310359,310516,310672,310691-310692,310694,310700,310704,310706,310776,310804,310829,310983,311115,311182,311330,311391,311397,311443,311532,311601,311695
/cfe/trunk/test:170344
/cfe/trunk/test/SemaTemplate:126920
Modified: cfe/branches/release_50/include/clang/AST/DeclCXX.h
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_50/include/clang/AST/DeclCXX.h?rev=311799&r1=311798&r2=311799&view=diff
==============================================================================
--- cfe/branches/release_50/include/clang/AST/DeclCXX.h (original)
+++ cfe/branches/release_50/include/clang/AST/DeclCXX.h Fri Aug 25 13:27:58 2017
@@ -2028,7 +2028,10 @@ public:
/// \brief Returns the type of the \c this pointer.
///
- /// Should only be called for instance (i.e., non-static) methods.
+ /// Should only be called for instance (i.e., non-static) methods. Note
+ /// that for the call operator of a lambda closure type, this returns the
+ /// desugared 'this' type (a pointer to the closure type), not the captured
+ /// 'this' type.
QualType getThisType(ASTContext &C) const;
unsigned getTypeQualifiers() const {
Modified: cfe/branches/release_50/lib/CodeGen/CodeGenFunction.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_50/lib/CodeGen/CodeGenFunction.cpp?rev=311799&r1=311798&r2=311799&view=diff
==============================================================================
--- cfe/branches/release_50/lib/CodeGen/CodeGenFunction.cpp (original)
+++ cfe/branches/release_50/lib/CodeGen/CodeGenFunction.cpp Fri Aug 25 13:27:58 2017
@@ -22,6 +22,7 @@
#include "CodeGenPGO.h"
#include "TargetInfo.h"
#include "clang/AST/ASTContext.h"
+#include "clang/AST/ASTLambda.h"
#include "clang/AST/Decl.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/StmtCXX.h"
@@ -983,11 +984,22 @@ void CodeGenFunction::StartFunction(Glob
}
// Check the 'this' pointer once per function, if it's available.
- if (CXXThisValue) {
+ if (CXXABIThisValue) {
SanitizerSet SkippedChecks;
SkippedChecks.set(SanitizerKind::ObjectSize, true);
QualType ThisTy = MD->getThisType(getContext());
- EmitTypeCheck(TCK_Load, Loc, CXXThisValue, ThisTy,
+
+ // If this is the call operator of a lambda with no capture-default, it
+ // may have a static invoker function, which may call this operator with
+ // a null 'this' pointer.
+ if (isLambdaCallOperator(MD) &&
+ cast<CXXRecordDecl>(MD->getParent())->getLambdaCaptureDefault() ==
+ LCD_None)
+ SkippedChecks.set(SanitizerKind::Null, true);
+
+ EmitTypeCheck(isa<CXXConstructorDecl>(MD) ? TCK_ConstructorCall
+ : TCK_MemberCall,
+ Loc, CXXABIThisValue, ThisTy,
getContext().getTypeAlignInChars(ThisTy->getPointeeType()),
SkippedChecks);
}
Modified: cfe/branches/release_50/test/CodeGenCXX/catch-undef-behavior.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_50/test/CodeGenCXX/catch-undef-behavior.cpp?rev=311799&r1=311798&r2=311799&view=diff
==============================================================================
--- cfe/branches/release_50/test/CodeGenCXX/catch-undef-behavior.cpp (original)
+++ cfe/branches/release_50/test/CodeGenCXX/catch-undef-behavior.cpp Fri Aug 25 13:27:58 2017
@@ -449,6 +449,28 @@ void upcast_to_vbase() {
}
}
+struct ThisAlign {
+ void this_align_lambda();
+ void this_align_lambda_2();
+};
+void ThisAlign::this_align_lambda() {
+ // CHECK-LABEL: define {{.*}}@"_ZZN9ThisAlign17this_align_lambdaEvENK3$_0clEv"
+ // CHECK-SAME: (%{{.*}}* %[[this:[^)]*]])
+ // CHECK: %[[this_addr:.*]] = alloca
+ // CHECK: store %{{.*}}* %[[this]], %{{.*}}** %[[this_addr]],
+ // CHECK: %[[this_inner:.*]] = load %{{.*}}*, %{{.*}}** %[[this_addr]],
+ // CHECK: %[[this_outer_addr:.*]] = getelementptr inbounds %{{.*}}, %{{.*}}* %[[this_inner]], i32 0, i32 0
+ // CHECK: %[[this_outer:.*]] = load %{{.*}}*, %{{.*}}** %[[this_outer_addr]],
+ //
+ // CHECK: %[[this_inner_isnonnull:.*]] = icmp ne %{{.*}}* %[[this_inner]], null
+ // CHECK: %[[this_inner_asint:.*]] = ptrtoint %{{.*}}* %[[this_inner]] to i
+ // CHECK: %[[this_inner_misalignment:.*]] = and i{{32|64}} %[[this_inner_asint]], {{3|7}},
+ // CHECK: %[[this_inner_isaligned:.*]] = icmp eq i{{32|64}} %[[this_inner_misalignment]], 0
+ // CHECK: %[[this_inner_valid:.*]] = and i1 %[[this_inner_isnonnull]], %[[this_inner_isaligned]],
+ // CHECK: br i1 %[[this_inner_valid:.*]]
+ [&] { return this; } ();
+}
+
namespace CopyValueRepresentation {
// CHECK-LABEL: define {{.*}} @_ZN23CopyValueRepresentation2S3aSERKS0_
// CHECK-NOT: call {{.*}} @__ubsan_handle_load_invalid_value
@@ -532,4 +554,18 @@ namespace CopyValueRepresentation {
}
}
+void ThisAlign::this_align_lambda_2() {
+ // CHECK-LABEL: define {{.*}}@"_ZZN9ThisAlign19this_align_lambda_2EvENK3$_1clEv"
+ // CHECK-SAME: (%{{.*}}* %[[this:[^)]*]])
+ // CHECK: %[[this_addr:.*]] = alloca
+ // CHECK: store %{{.*}}* %[[this]], %{{.*}}** %[[this_addr]],
+ // CHECK: %[[this_inner:.*]] = load %{{.*}}*, %{{.*}}** %[[this_addr]],
+ //
+ // Do not perform a null check on the 'this' pointer if the function might be
+ // called from a static invoker.
+ // CHECK-NOT: icmp ne %{{.*}}* %[[this_inner]], null
+ auto *p = +[] {};
+ p();
+}
+
// CHECK: attributes [[NR_NUW]] = { noreturn nounwind }
More information about the llvm-branch-commits
mailing list