From bbf896e16558f78b160d8da207db4208d801b6da Mon Sep 17 00:00:00 2001 From: Jon Ross-Perkins Date: Wed, 26 Jul 2023 14:30:28 -0700 Subject: [PATCH] Convert returned associated constants. (#3029) Associated constants were getting returned directly, crashing because the value InterpProgram received was an AssociatedConstant instead of an IntValue. We have a similar Convert call in ReturnVar, so I _think_ this is the right approach. --- explorer/interpreter/interpreter.cpp | 10 ++++--- .../return/convert_return_assoc.carbon | 27 +++++++++++++++++++ 2 files changed, 34 insertions(+), 3 deletions(-) create mode 100644 explorer/testdata/return/convert_return_assoc.carbon diff --git a/explorer/interpreter/interpreter.cpp b/explorer/interpreter/interpreter.cpp index 52eec8114663..f9c7d6587fb5 100644 --- a/explorer/interpreter/interpreter.cpp +++ b/explorer/interpreter/interpreter.cpp @@ -2526,12 +2526,16 @@ auto Interpreter::StepStmt() -> ErrorOr { // { {v :: return [] :: C, E, F} :: {C', E', F'} :: S, H} // -> { {v :: C', E', F'} :: S, H} const CallableDeclaration& function = cast(stmt).function(); + CARBON_ASSIGN_OR_RETURN( + Nonnull return_value, + Convert(act.results()[0], &function.return_term().static_type(), + stmt.source_loc())); // Write to initialized storage location, if any. if (const auto location = act.location_received()) { - CARBON_RETURN_IF_ERROR(heap_.Write( - Address(*location), act.results()[0], stmt.source_loc())); + CARBON_RETURN_IF_ERROR( + heap_.Write(Address(*location), return_value, stmt.source_loc())); } - return todo_.UnwindPast(*function.body(), act.results()[0]); + return todo_.UnwindPast(*function.body(), return_value); } } } diff --git a/explorer/testdata/return/convert_return_assoc.carbon b/explorer/testdata/return/convert_return_assoc.carbon new file mode 100644 index 000000000000..c62c2c1fa48e --- /dev/null +++ b/explorer/testdata/return/convert_return_assoc.carbon @@ -0,0 +1,27 @@ +// Part of the Carbon Language project, under the Apache License v2.0 with LLVM +// Exceptions. See /LICENSE for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +// AUTOUPDATE +// CHECK:STDOUT: result: 1 + +package ExplorerTest api; + +interface I { + let Assoc:! i32; +} + +class C { + impl Self as I where .Assoc = 1 {} +} + +alias A = I where .Assoc == 1; + +fn F[T:! A](x: T) -> i32 { + return x.(A.Assoc); +} + +fn Main() -> i32 { + var a: C = {}; + return F(a); +}