mirror of
https://github.com/carbon-language/carbon-lang.git
synced 2026-10-04 11:21:05 +01:00
Restructure return declaration handling (#7076)
- A function with a return declaration always has exactly one `ReturnSlotPattern`, representing the whole return declaration (whereas previously that was omitted for value and reference returns). - The `ReturnSlotPattern` always has a subpattern with the same form. `OutParamPattern` already plays that role for initializing forms, and `TuplePattern` will play that role for tuple forms. This change introduces `ValueReturnPattern` and `RefReturnPattern` to represent value and reference return forms. - As before, the `ReturnSlotPattern` has a corresponding `ReturnSlot` that represents the output that is initialized by a `return` statement. Its structure parallels the structure of the `ReturnSlotPattern`, so we need `ValueReturn` and `RefReturn` insts that correspond to `ValueReturnPattern` and `RefReturnPattern`. This is a step toward supporting generic return forms, where the `ReturnSlotPattern`'s subpattern may be an action: this change ensures that evaluating the action for a specific form produces the same SemIR as if the form were concrete to begin with. More speculatively, this should simplify the implementation of `return` statements with compound return forms. --------- Co-authored-by: Chandler Carruth <chandlerc@gmail.com>
This commit is contained in:
co-authored by
Chandler Carruth
parent
3abc334c42
commit
49c7288619
@@ -667,23 +667,22 @@ auto PerformCppThunkCall(Context& context, SemIR::LocId loc_id,
|
||||
auto& callee_function = context.functions().Get(callee_function_id);
|
||||
auto callee_function_params =
|
||||
context.inst_blocks().Get(callee_function.call_params_id);
|
||||
auto callee_return_patterns =
|
||||
context.inst_blocks().GetOrEmpty(callee_function.return_patterns_id);
|
||||
auto num_callee_return_params =
|
||||
callee_function.call_param_ranges.return_size();
|
||||
|
||||
auto thunk_callee = GetCalleeAsFunction(context.sem_ir(), thunk_callee_id);
|
||||
auto& thunk_function = context.functions().Get(thunk_callee.function_id);
|
||||
auto thunk_function_params =
|
||||
context.inst_blocks().Get(thunk_function.call_params_id);
|
||||
auto thunk_return_patterns =
|
||||
context.inst_blocks().GetOrEmpty(thunk_function.return_patterns_id);
|
||||
auto num_thunk_return_params = thunk_function.call_param_ranges.return_size();
|
||||
|
||||
CARBON_CHECK(
|
||||
callee_return_patterns.size() <= 1 && thunk_return_patterns.size() <= 1,
|
||||
num_callee_return_params <= 1 && num_thunk_return_params <= 1,
|
||||
"TODO: generalize this logic to support multiple return patterns.");
|
||||
|
||||
// Whether we need to pass a return address to the thunk as a final argument.
|
||||
bool thunk_takes_return_address =
|
||||
!callee_return_patterns.empty() && thunk_return_patterns.empty();
|
||||
num_callee_return_params > 0 && num_thunk_return_params == 0;
|
||||
|
||||
// The number of arguments we should be acquiring in order to call the thunk.
|
||||
// This includes the return address parameters, if any.
|
||||
@@ -704,9 +703,9 @@ auto PerformCppThunkCall(Context& context, SemIR::LocId loc_id,
|
||||
// TODO: The parameter should probably only be created if the return pattern
|
||||
// actually needs a return address to be passed in.
|
||||
thunk_function_params =
|
||||
thunk_function_params.drop_back(thunk_return_patterns.size());
|
||||
thunk_function_params.drop_back(num_thunk_return_params);
|
||||
callee_function_params =
|
||||
callee_function_params.drop_back(callee_return_patterns.size());
|
||||
callee_function_params.drop_back(num_callee_return_params);
|
||||
|
||||
// We assume that the call parameters exactly match the parameter patterns for
|
||||
// both the thunk and the callee. This is guaranteed even when we generate a
|
||||
|
||||
Reference in New Issue
Block a user