]> granicus.if.org Git - clang/commitdiff
Don't crash when passing &@selector to a _Nonnull parameter. Fixes PR24774.
authorNico Weber <nicolasweber@gmx.de>
Tue, 15 Sep 2015 23:17:17 +0000 (23:17 +0000)
committerNico Weber <nicolasweber@gmx.de>
Tue, 15 Sep 2015 23:17:17 +0000 (23:17 +0000)
The root cause here is that ObjCSelectorExpr is an rvalue, yet it can have its
address taken.  That's kind of awkward, but fixing this is awkward in other
ways, see https://llvm.org/bugs/show_bug.cgi?id=24774#c16 .  For now, just
fix the crash.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@247740 91177308-0d34-0410-b5e6-96231b3b80d8

lib/AST/ExprConstant.cpp
test/SemaObjCXX/sel-address.mm

index 5eaf40eb2ad00aa72652d2806eaee12a70517aee..2fb8c9c137b21a15d64dbe70fec97ba86e79dd04 100644 (file)
@@ -4557,12 +4557,13 @@ public:
 } // end anonymous namespace
 
 /// Evaluate an expression as an lvalue. This can be legitimately called on
-/// expressions which are not glvalues, in two cases:
+/// expressions which are not glvalues, in three cases:
 ///  * function designators in C, and
 ///  * "extern void" objects
+///  * @selector() expressions in Objective-C
 static bool EvaluateLValue(const Expr *E, LValue &Result, EvalInfo &Info) {
   assert(E->isGLValue() || E->getType()->isFunctionType() ||
-         E->getType()->isVoidType());
+         E->getType()->isVoidType() || isa<ObjCSelectorExpr>(E));
   return LValueExprEvaluator(Info, Result).Visit(E);
 }
 
index 931d793fd508dafcd3a4fa4ac6cdb874e5d110d0..a1209abd4e687df303b8321df7374ee2de6109f3 100644 (file)
@@ -2,7 +2,8 @@
 // pr7390
 
 void f(const SEL& v2) {}
-void g() {
+void g(SEL* _Nonnull);
+void h() {
   f(@selector(dealloc));
 
   SEL s = @selector(dealloc);
@@ -11,4 +12,8 @@ void g() {
   @selector(dealloc) = s;  // expected-error {{expression is not assignable}}
 
   SEL* ps2 = &@selector(dealloc);
+
+  // Shouldn't crash.
+  g(&@selector(foo));
 }
+