diff options
Diffstat (limited to 'clang/lib/Sema')
| -rw-r--r-- | clang/lib/Sema/SemaChecking.cpp | 20 | ||||
| -rw-r--r-- | clang/lib/Sema/SemaCoroutine.cpp | 18 |
2 files changed, 25 insertions, 13 deletions
diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index 9e53c478ef6..e2d044c00e4 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -7493,18 +7493,16 @@ void AnalyzeImplicitConversions(Sema &S, Expr *OrigE, SourceLocation CC) { CheckImplicitConversion(S, E, T, CC); // Now continue drilling into this expression. - - if (PseudoObjectExpr * POE = dyn_cast<PseudoObjectExpr>(E)) { - if (POE->getResultExpr()) - E = POE->getResultExpr(); - } - - if (const OpaqueValueExpr *OVE = dyn_cast<OpaqueValueExpr>(E)) { - if (OVE->getSourceExpr()) - AnalyzeImplicitConversions(S, OVE->getSourceExpr(), CC); - return; + + if (PseudoObjectExpr *POE = dyn_cast<PseudoObjectExpr>(E)) { + // The bound subexpressions in a PseudoObjectExpr are not reachable + // as transitive children. + // FIXME: Use a more uniform representation for this. + for (auto *SE : POE->semantics()) + if (auto *OVE = dyn_cast<OpaqueValueExpr>(SE)) + AnalyzeImplicitConversions(S, OVE->getSourceExpr(), CC); } - + // Skip past explicit casts. if (isa<ExplicitCastExpr>(E)) { E = cast<ExplicitCastExpr>(E)->getSubExpr()->IgnoreParenImpCasts(); diff --git a/clang/lib/Sema/SemaCoroutine.cpp b/clang/lib/Sema/SemaCoroutine.cpp index 8d91e43f41e..a0d24b8cecd 100644 --- a/clang/lib/Sema/SemaCoroutine.cpp +++ b/clang/lib/Sema/SemaCoroutine.cpp @@ -300,8 +300,22 @@ ExprResult Sema::BuildCoyieldExpr(SourceLocation Loc, Expr *E) { E = R.get(); } - // FIXME: Build await_* calls. - Expr *Res = new (Context) CoyieldExpr(Loc, Context.VoidTy, E); + if (E->getType()->isDependentType()) { + Expr *Res = new (Context) CoyieldExpr(Loc, Context.DependentTy, E); + Coroutine->CoroutineStmts.push_back(Res); + return Res; + } + + // FIXME: If E is a prvalue, create a temporary. + // FIXME: If E is an xvalue, convert to lvalue. + + // Build the await_ready, await_suspend, await_resume calls. + ReadySuspendResumeResult RSS = buildCoawaitCalls(*this, Loc, E); + if (RSS.IsInvalid) + return ExprError(); + + Expr *Res = new (Context) CoyieldExpr(Loc, E, RSS.Results[0], RSS.Results[1], + RSS.Results[2]); Coroutine->CoroutineStmts.push_back(Res); return Res; } |

