summaryrefslogtreecommitdiffstats
path: root/clang/lib
diff options
context:
space:
mode:
authorAaron Ballman <aaron@aaronballman.com>2016-09-02 13:45:40 +0000
committerAaron Ballman <aaron@aaronballman.com>2016-09-02 13:45:40 +0000
commitff7bd8bacd13019529b7709efa95ae834c4537a4 (patch)
treeff511e9235c978455b7449545dbefa7a2d123ae0 /clang/lib
parentfd503e5af306b6aad3dd3d7005ff86e008aad2dd (diff)
downloadbcm5719-llvm-ff7bd8bacd13019529b7709efa95ae834c4537a4.tar.gz
bcm5719-llvm-ff7bd8bacd13019529b7709efa95ae834c4537a4.zip
Allow a C11 generic selection expression to select a function with the overloadable attribute as the result expression without crashing. This fixes PR30201.
llvm-svn: 280483
Diffstat (limited to 'clang/lib')
-rw-r--r--clang/lib/Sema/SemaOverload.cpp25
1 files changed, 25 insertions, 0 deletions
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 72ad9a4d715..36643812b02 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -12984,6 +12984,31 @@ Expr *Sema::FixOverloadedFunctionReference(Expr *E, DeclAccessPair Found,
ICE->getValueKind());
}
+ if (auto *GSE = dyn_cast<GenericSelectionExpr>(E)) {
+ if (!GSE->isResultDependent()) {
+ Expr *SubExpr =
+ FixOverloadedFunctionReference(GSE->getResultExpr(), Found, Fn);
+ if (SubExpr == GSE->getResultExpr())
+ return GSE;
+
+ // Replace the resulting type information before rebuilding the generic
+ // selection expression.
+ SmallVector<Expr *, 4> AssocExprs(GSE->getAssocExprs().begin(),
+ GSE->getAssocExprs().end());
+ unsigned ResultIdx = GSE->getResultIndex();
+ AssocExprs[ResultIdx] = SubExpr;
+
+ return new (Context) GenericSelectionExpr(
+ Context, GSE->getGenericLoc(), GSE->getControllingExpr(),
+ GSE->getAssocTypeSourceInfos(), AssocExprs, GSE->getDefaultLoc(),
+ GSE->getRParenLoc(), GSE->containsUnexpandedParameterPack(),
+ ResultIdx);
+ }
+ // Rather than fall through to the unreachable, return the original generic
+ // selection expression.
+ return GSE;
+ }
+
if (UnaryOperator *UnOp = dyn_cast<UnaryOperator>(E)) {
assert(UnOp->getOpcode() == UO_AddrOf &&
"Can only take the address of an overloaded function");
OpenPOWER on IntegriCloud