On 3/24/20 2:08 PM, Iain Sandoe wrote:
tree suspend = TREE_VEC_ELT (awaiter_calls, 1); /* await_suspend(). */
+ tree susp_type;
+ if (tree fndecl = cp_get_callee_fndecl_nofold (suspend))
+ susp_type = TREE_TYPE (TREE_TYPE (fndecl));
+ else
+ susp_type = TREE_TYPE (suspend);
Why, when there's a call of a named function, is it that TREE_TYPE
(suspend) is insufficient? You mentioned TARGET_EXPR, but why is their
type differenty?
@@ -2012,6 +2018,12 @@ build_actor_fn (location_t loc, tree coro_frame_type,
tree actor, tree fnbody,
= create_named_label_with_ctx (loc, "actor.begin", actor);
tree actor_frame = build1_loc (loc, INDIRECT_REF, coro_frame_type,
actor_fp);
+ /* Declare the continuation handle. */
+ tree ci = build_stmt (loc, DECL_EXPR, continuation);
+ ci = build1_loc (loc, CONVERT_EXPR, void_type_node, ci);
+ ci = maybe_cleanup_point_expr_void (ci);
+ add_stmt (ci);
you don't need to wrap in a CONVERT_EXPR, can you use add_decl_expr ?
@@ -2368,6 +2383,35 @@ build_actor_fn (location_t loc, tree coro_frame_type,
tree actor, tree fnbody,
+
+ /* Now we have the actual call, and we can mark it as a tail. */
+ CALL_EXPR_TAILCALL (resume) = true;
+ /* ... and for optimisation levels 0..1, mark it as requiring a tail-call
+ for correctness. It seems that doing this for optimisation levels that
+ normally perform tail-calling, confuses the ME (or it would be logical
+ to put this on unilaterally). */
+ if (optimize < 2)
+ CALL_EXPR_MUST_TAIL_CALL (resume) = true;
+ resume = coro_build_cvt_void_expr_stmt (resume, loc);
I'd be happier with
gcc_checking_assert (maybe_cleanup_point_expr_void (resume) == resume);
here. I see we can wrap RETURN_EXPRs with cleanups, so perhaps adding
is ok anyway?
nathan
--
Nathan Sidwell