Author: Mark de Wever Date: 2020-08-16T18:32:38+02:00 New Revision: 827ba67e383313b05e9b10c8215e501530d6c9e3
URL: https://github.com/llvm/llvm-project/commit/827ba67e383313b05e9b10c8215e501530d6c9e3 DIFF: https://github.com/llvm/llvm-project/commit/827ba67e383313b05e9b10c8215e501530d6c9e3.diff LOG: [Sema] Validate calls to GetExprRange. When a conditional expression has a throw expression it called GetExprRange with a void expression, which caused an assertion failure. This approach was suggested by Richard Smith. Fixes PR46484: Clang crash in clang/lib/Sema/SemaChecking.cpp:10028 Differential Revision: https://reviews.llvm.org/D85601 Added: Modified: clang/lib/Sema/SemaChecking.cpp clang/test/SemaCXX/conditional-expr.cpp Removed: ################################################################################ diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index bbd856e9262e..4efd62f58d2e 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -10368,10 +10368,16 @@ static IntRange GetExprRange(ASTContext &C, const Expr *E, unsigned MaxWidth, MaxWidth, InConstantContext); // Otherwise, conservatively merge. - IntRange L = - GetExprRange(C, CO->getTrueExpr(), MaxWidth, InConstantContext); - IntRange R = - GetExprRange(C, CO->getFalseExpr(), MaxWidth, InConstantContext); + // GetExprRange requires an integer expression, but a throw expression + // results in a void type. + Expr *E = CO->getTrueExpr(); + IntRange L = E->getType()->isVoidType() + ? IntRange{0, true} + : GetExprRange(C, E, MaxWidth, InConstantContext); + E = CO->getFalseExpr(); + IntRange R = E->getType()->isVoidType() + ? IntRange{0, true} + : GetExprRange(C, E, MaxWidth, InConstantContext); return IntRange::join(L, R); } diff --git a/clang/test/SemaCXX/conditional-expr.cpp b/clang/test/SemaCXX/conditional-expr.cpp index 8d0555ea5068..68e23a1f5727 100644 --- a/clang/test/SemaCXX/conditional-expr.cpp +++ b/clang/test/SemaCXX/conditional-expr.cpp @@ -409,3 +409,20 @@ namespace lifetime_extension { D d = b ? D{B()} : D{C()}; } } + +namespace PR46484 { +// expected-error@+4{{expected ':'}} +// expected-note@+3{{to match this '?'}} +// expected-warning@+2{{variable 'b' is uninitialized}} +// expected-error@+1 2 {{expected ';' after top level declarator}} +int a long b = a = b ? throw 0 1 + +void g() { + extern int a; + extern long b; + long c = a = b ? throw 0 : 1; + long d = a = b ? 1 : throw 0; + // expected-error@+1 {{assigning to 'int' from incompatible type 'void'}} + long e = a = b ? throw 0 : throw 1; +} +} // namespace PR46484 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits