[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
This commit is contained in:
parent
f25d47b7ed
commit
827ba67e38
|
@ -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);
|
||||
}
|
||||
|
||||
|
|
|
@ -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
|
||||
|
|
Loading…
Reference in New Issue