Skip to content

Commit 60dcbb5

Browse files
philbertydkm
authored andcommitted
gccrs: Refactor TyTy::ConstType into separate types
This patch refactors the const generic type system to follow the same pattern as regular type parameters. The monolithic ConstType is split into four distinct types: ConstParamType (generic parameter placeholder) ConstValueType (resolved constant value) ConstInferType (inference variable) ConstErrorType (error sentinel) gcc/rust/ChangeLog: * backend/rust-compile-expr.cc (CompileExpr::array_copied_expr): refactor to new classes * backend/rust-compile-pattern.cc (CompilePatternCheckExpr::visit): likewise (CompilePatternBindings::visit): likewise * backend/rust-compile-type.cc (TyTyResolveCompile::visit): likewise * backend/rust-compile-type.h: likewise * typecheck/rust-hir-type-check-base.cc (TypeCheckBase::resolve_literal): likewise * typecheck/rust-hir-type-check-expr.cc (TypeCheckExpr::visit): likewise * typecheck/rust-hir-type-check-pattern.cc (TypeCheckPattern::visit): likewise * typecheck/rust-hir-type-check-type.cc (TypeCheckType::visit): likewise * typecheck/rust-substitution-mapper.cc (SubstMapperInternal::visit): likewise * typecheck/rust-substitution-mapper.h: likewise * typecheck/rust-type-util.cc (unify_site_and): remove bad delete (alpine32) * typecheck/rust-tyty-call.h: refactor to new classes * typecheck/rust-tyty-subst.cc (SubstitutionParamMapping::clone): likewise (SubstitutionRef::infer_substitions): likewise * typecheck/rust-tyty-util.cc (TyVar::get_implicit_const_infer_var): likewise * typecheck/rust-tyty-util.h: likewise * typecheck/rust-tyty-variance-analysis-private.h: likewise * typecheck/rust-tyty-visitor.h: likewise * typecheck/rust-tyty.cc (BaseType::destructure): likewise (BaseType::monomorphized_clone): likewise (BaseType::is_concrete): likewise (VariantDef::clone): likewise (VariantDef::monomorphized_clone): likewise (ArrayType::as_string): likewise (ArrayType::get_capacity): likewise (ArrayType::handle_substitions): likewise (generate_tree_str): likewise (ConstType::ConstType): likewise (ConstParamType::ConstParamType): likewise (ConstType::accept_vis): likewise (ConstParamType::const_kind): likewise (ConstParamType::get_symbol): likewise (ConstParamType::can_resolve): likewise (ConstParamType::resolve): likewise (ConstParamType::accept_vis): likewise (ConstType::set_value): likewise (ConstType::as_string): likewise (ConstParamType::as_string): likewise (ConstType::clone): likewise (ConstParamType::clone): likewise (ConstType::get_symbol): likewise (ConstParamType::get_name): likewise (ConstType::can_resolve): likewise (ConstParamType::is_equal): likewise (ConstType::resolve): likewise (ConstValueType::ConstValueType): likewise (ConstValueType::const_kind): likewise (ConstValueType::accept_vis): likewise (ConstValueType::as_string): likewise (ConstValueType::clone): likewise (ConstValueType::get_name): likewise (ConstValueType::is_equal): likewise (ConstValueType::get_value): likewise (ConstInferType::ConstInferType): likewise (ConstInferType::const_kind): likewise (ConstInferType::accept_vis): likewise (ConstType::get_name): likewise (ConstInferType::as_string): likewise (ConstInferType::clone): likewise (ConstInferType::get_name): likewise (ConstType::is_equal): likewise (ConstInferType::is_equal): likewise (ConstErrorType::ConstErrorType): likewise (ConstErrorType::const_kind): likewise (ConstType::handle_substitions): likewise (ConstErrorType::accept_vis): likewise (ConstErrorType::as_string): likewise (ConstErrorType::clone): likewise (ConstErrorType::get_name): likewise (ConstErrorType::is_equal): likewise * typecheck/rust-tyty.h (class BaseConstType): likewise (class ConstType): likewise (class ConstParamType): likewise (class ConstValueType): likewise (class ConstInferType): likewise (class ConstErrorType): likewise * typecheck/rust-unify.cc (UnifyRules::commit): likewise (UnifyRules::go): likewise (UnifyRules::expect_array): likewise (UnifyRules::expect_const): likewise * typecheck/rust-unify.h: likewise Signed-off-by: Philip Herron <[email protected]>
1 parent 135dd47 commit 60dcbb5

21 files changed

+920
-324
lines changed

gcc/rust/backend/rust-compile-expr.cc

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2010,11 +2010,25 @@ CompileExpr::array_copied_expr (location_t expr_locus,
20102010
return error_mark_node;
20112011
}
20122012

2013-
auto capacity_tyty = array_tyty.get_capacity ();
2014-
tree capacity_expr = capacity_tyty->get_value ();
2015-
if (!TREE_CONSTANT (capacity_expr))
2013+
auto capacity_ty = array_tyty.get_capacity ();
2014+
2015+
// Check if capacity is a const type
2016+
if (capacity_ty->get_kind () != TyTy::TypeKind::CONST)
2017+
{
2018+
rust_error_at (array_tyty.get_locus (),
2019+
"array capacity is not a const type");
2020+
return error_mark_node;
2021+
}
2022+
2023+
auto *capacity_const = capacity_ty->as_const_type ();
2024+
2025+
rust_assert (capacity_const->const_kind ()
2026+
== TyTy::BaseConstType::ConstKind::Value);
2027+
auto &capacity_value = *static_cast<TyTy::ConstValueType *> (capacity_const);
2028+
auto cap_tree = capacity_value.get_value ();
2029+
if (error_operand_p (cap_tree) || !TREE_CONSTANT (cap_tree))
20162030
{
2017-
rust_error_at (expr_locus, "non const num copies %qT", capacity_expr);
2031+
rust_error_at (expr_locus, "non const num copies %qT", cap_tree);
20182032
return error_mark_node;
20192033
}
20202034

@@ -2067,9 +2081,9 @@ CompileExpr::array_copied_expr (location_t expr_locus,
20672081
ctx->push_block (init_block);
20682082

20692083
tree tmp;
2070-
tree stmts = Backend::array_initializer (fndecl, init_block, array_type,
2071-
capacity_expr, translated_expr,
2072-
&tmp, expr_locus);
2084+
tree stmts
2085+
= Backend::array_initializer (fndecl, init_block, array_type, cap_tree,
2086+
translated_expr, &tmp, expr_locus);
20732087
ctx->add_statement (stmts);
20742088

20752089
tree block = ctx->pop_block ();

gcc/rust/backend/rust-compile-pattern.cc

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
#include "rust-hir-pattern.h"
2828
#include "rust-system.h"
2929
#include "rust-tyty.h"
30+
#include "tree.h"
3031

3132
namespace Rust {
3233
namespace Compile {
@@ -676,7 +677,18 @@ CompilePatternCheckExpr::visit (HIR::SlicePattern &pattern)
676677
// for array type scrutinee, we can simply get the capacity as a
677678
// const and calculate how many elements to skip
678679
auto array_ty = static_cast<TyTy::ArrayType *> (lookup);
679-
auto cap_tree = array_ty->get_capacity ()->get_value ();
680+
auto capacity_ty = array_ty->get_capacity ();
681+
682+
rust_assert (capacity_ty->get_kind () == TyTy::TypeKind::CONST);
683+
auto *capacity_const = capacity_ty->as_const_type ();
684+
rust_assert (capacity_const->const_kind ()
685+
== TyTy::BaseConstType::ConstKind::Value);
686+
auto &capacity_value
687+
= *static_cast<TyTy::ConstValueType *> (capacity_const);
688+
auto cap_tree = capacity_value.get_value ();
689+
690+
rust_assert (!error_operand_p (cap_tree));
691+
680692
size_t cap_wi = (size_t) wi::to_wide (cap_tree).to_uhwi ();
681693
element_index = cap_wi - items.get_upper_patterns ().size ();
682694
for (auto &pattern_member : items.get_upper_patterns ())
@@ -1164,7 +1176,18 @@ CompilePatternBindings::visit (HIR::SlicePattern &pattern)
11641176
case TyTy::TypeKind::ARRAY:
11651177
{
11661178
auto array_ty = static_cast<TyTy::ArrayType *> (lookup);
1167-
auto cap_tree = array_ty->get_capacity ()->get_value ();
1179+
auto capacity_ty = array_ty->get_capacity ();
1180+
1181+
rust_assert (capacity_ty->get_kind () == TyTy::TypeKind::CONST);
1182+
auto *capacity_const = capacity_ty->as_const_type ();
1183+
rust_assert (capacity_const->const_kind ()
1184+
== TyTy::BaseConstType::ConstKind::Value);
1185+
auto &capacity_value
1186+
= *static_cast<TyTy::ConstValueType *> (capacity_const);
1187+
auto cap_tree = capacity_value.get_value ();
1188+
1189+
rust_assert (!error_operand_p (cap_tree));
1190+
11681191
size_t cap_wi = (size_t) wi::to_wide (cap_tree).to_uhwi ();
11691192
element_index = cap_wi - items.get_upper_patterns ().size ();
11701193
for (auto &pattern_member : items.get_upper_patterns ())

gcc/rust/backend/rust-compile-type.cc

Lines changed: 36 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -136,13 +136,31 @@ TyTyResolveCompile::visit (const TyTy::InferType &type)
136136
}
137137

138138
void
139-
TyTyResolveCompile::visit (const TyTy::ParamType &)
139+
TyTyResolveCompile::visit (const TyTy::ParamType &type)
140140
{
141141
translated = error_mark_node;
142142
}
143143

144144
void
145-
TyTyResolveCompile::visit (const TyTy::ConstType &)
145+
TyTyResolveCompile::visit (const TyTy::ConstParamType &type)
146+
{
147+
translated = error_mark_node;
148+
}
149+
150+
void
151+
TyTyResolveCompile::visit (const TyTy::ConstValueType &type)
152+
{
153+
translated = error_mark_node;
154+
}
155+
156+
void
157+
TyTyResolveCompile::visit (const TyTy::ConstInferType &type)
158+
{
159+
translated = error_mark_node;
160+
}
161+
162+
void
163+
TyTyResolveCompile::visit (const TyTy::ConstErrorType &type)
146164
{
147165
translated = error_mark_node;
148166
}
@@ -470,8 +488,22 @@ TyTyResolveCompile::visit (const TyTy::ArrayType &type)
470488
{
471489
tree element_type
472490
= TyTyResolveCompile::compile (ctx, type.get_element_type ());
473-
TyTy::ConstType *const_capacity = type.get_capacity ();
474-
tree folded_capacity_expr = const_capacity->get_value ();
491+
auto const_capacity = type.get_capacity ();
492+
493+
// Check if capacity is a const type
494+
if (const_capacity->get_kind () != TyTy::TypeKind::CONST)
495+
{
496+
rust_error_at (type.get_locus (), "array capacity is not a const type");
497+
translated = error_mark_node;
498+
return;
499+
}
500+
501+
auto *capacity_const = const_capacity->as_const_type ();
502+
503+
rust_assert (capacity_const->const_kind ()
504+
== TyTy::BaseConstType::ConstKind::Value);
505+
auto &capacity_value = *static_cast<TyTy::ConstValueType *> (capacity_const);
506+
auto folded_capacity_expr = capacity_value.get_value ();
475507

476508
// build_index_type takes the maximum index, which is one less than
477509
// the length.

gcc/rust/backend/rust-compile-type.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,10 @@ class TyTyResolveCompile : protected TyTy::TyConstVisitor
5050
void visit (const TyTy::ReferenceType &) override;
5151
void visit (const TyTy::PointerType &) override;
5252
void visit (const TyTy::ParamType &) override;
53-
void visit (const TyTy::ConstType &) override;
53+
void visit (const TyTy::ConstParamType &) override;
54+
void visit (const TyTy::ConstValueType &) override;
55+
void visit (const TyTy::ConstInferType &) override;
56+
void visit (const TyTy::ConstErrorType &) override;
5457
void visit (const TyTy::StrType &) override;
5558
void visit (const TyTy::NeverType &) override;
5659
void visit (const TyTy::PlaceholderType &) override;

gcc/rust/typecheck/rust-hir-type-check-base.cc

Lines changed: 22 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -367,17 +367,17 @@ TypeCheckBase::resolve_literal (const Analysis::NodeMapping &expr_mappings,
367367
tree capacity = Compile::HIRCompileBase::query_compile_const_expr (
368368
ctx, expected_ty, *literal_capacity);
369369

370-
TyTy::ConstType *capacity_expr
371-
= new TyTy::ConstType (TyTy::ConstType::ConstKind::Value, "",
372-
expected_ty, capacity, {},
373-
literal_capacity->get_locus (),
374-
literal_capacity->get_mappings ().get_hirid (),
375-
literal_capacity->get_mappings ().get_hirid (),
376-
{});
377-
378-
TyTy::ArrayType *array
379-
= new TyTy::ArrayType (array_mapping.get_hirid (), locus,
380-
capacity_expr, TyTy::TyVar (u8->get_ref ()));
370+
HirId capacity_expr_id = literal_capacity->get_mappings ().get_hirid ();
371+
auto capacity_expr
372+
= new TyTy::ConstValueType (capacity, expected_ty, capacity_expr_id,
373+
capacity_expr_id);
374+
context->insert_type (literal_capacity->get_mappings (),
375+
capacity_expr->as_base_type ());
376+
377+
TyTy::ArrayType *array = new TyTy::ArrayType (
378+
array_mapping.get_hirid (), locus,
379+
TyTy::TyVar (capacity_expr->as_base_type ()->get_ty_ref ()),
380+
TyTy::TyVar (u8->get_ref ()));
381381
context->insert_type (array_mapping, array);
382382

383383
infered = new TyTy::ReferenceType (expr_mappings.get_hirid (),
@@ -597,22 +597,21 @@ TypeCheckBase::resolve_generic_params (
597597
= Compile::HIRCompileBase::query_compile_const_expr (
598598
ctx, specified_type, expr);
599599

600-
TyTy::ConstType *default_const_decl
601-
= new TyTy::ConstType (TyTy::ConstType::ConstKind::Value,
602-
param.get_name (), specified_type,
603-
default_value, {}, param.get_locus (),
604-
expr.get_mappings ().get_hirid (),
605-
expr.get_mappings ().get_hirid (), {});
600+
auto default_const_decl
601+
= new TyTy::ConstValueType (default_value, specified_type,
602+
expr.get_mappings ().get_hirid (),
603+
expr.get_mappings ().get_hirid (),
604+
{});
606605

607606
context->insert_type (expr.get_mappings (), default_const_decl);
608607
}
609608

610-
TyTy::ConstType *const_decl
611-
= new TyTy::ConstType (TyTy::ConstType::ConstKind::Decl,
612-
param.get_name (), specified_type,
613-
error_mark_node, {}, param.get_locus (),
614-
param.get_mappings ().get_hirid (),
615-
param.get_mappings ().get_hirid (), {});
609+
TyTy::BaseGeneric *const_decl
610+
= new TyTy::ConstParamType (param.get_name (), param.get_locus (),
611+
specified_type,
612+
param.get_mappings ().get_hirid (),
613+
param.get_mappings ().get_hirid (),
614+
{});
616615

617616
context->insert_type (generic_param->get_mappings (), const_decl);
618617
TyTy::SubstitutionParamMapping p (*generic_param, const_decl);

gcc/rust/typecheck/rust-hir-type-check-expr.cc

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
#include "rust-immutable-name-resolution-context.h"
3535
#include "rust-compile-base.h"
3636
#include "rust-tyty-util.h"
37+
#include "rust-tyty.h"
3738
#include "tree.h"
3839

3940
namespace Rust {
@@ -668,16 +669,9 @@ TypeCheckExpr::visit (HIR::AnonConst &expr)
668669
return;
669670
}
670671

671-
auto locus = expr.get_locus ();
672-
auto infer_ty_var = TyTy::TyVar::get_implicit_infer_var (locus);
673-
674-
HirId next = mappings.get_next_hir_id ();
675-
infered = new TyTy::ConstType (TyTy::ConstType::ConstKind::Infer, "",
676-
infer_ty_var.get_tyty (), error_mark_node, {},
677-
locus, next, next, {});
678-
679-
context->insert_implicit_type (infered->get_ref (), infered);
680-
mappings.insert_location (infered->get_ref (), locus);
672+
TyTy::TyVar var
673+
= TyTy::TyVar::get_implicit_const_infer_var (expr.get_locus ());
674+
infered = var.get_tyty ();
681675
}
682676

683677
void
@@ -1155,14 +1149,23 @@ TypeCheckExpr::visit (HIR::ArrayExpr &expr)
11551149
tree capacity_value
11561150
= Compile::HIRCompileBase::query_compile_const_expr (ctx, capacity_type,
11571151
*capacity_expr);
1158-
HirId size_id = capacity_expr->get_mappings ().get_hirid ();
1159-
TyTy::ConstType *const_type
1160-
= new TyTy::ConstType (TyTy::ConstType::ConstKind::Value, "", expected_ty,
1161-
capacity_value, {}, capacity_expr->get_locus (),
1162-
size_id, size_id);
1152+
1153+
// Create ConstValueType with ref == ty_ref (both pointing to capacity_expr)
1154+
// ty_ref gets updated during substitution via set_ty_ref()
1155+
HirId capacity_expr_id = capacity_expr->get_mappings ().get_hirid ();
1156+
auto const_type
1157+
= new TyTy::ConstValueType (capacity_value, expected_ty, capacity_expr_id,
1158+
capacity_expr_id);
1159+
1160+
// Insert the ConstValueType at its ref
1161+
context->insert_type (capacity_expr->get_mappings (),
1162+
const_type->as_base_type ());
1163+
11631164
infered
11641165
= new TyTy::ArrayType (expr.get_mappings ().get_hirid (), expr.get_locus (),
1165-
const_type, TyTy::TyVar (element_type->get_ref ()));
1166+
TyTy::TyVar (
1167+
const_type->as_base_type ()->get_ty_ref ()),
1168+
TyTy::TyVar (element_type->get_ref ()));
11661169
}
11671170

11681171
// empty struct

gcc/rust/typecheck/rust-hir-type-check-pattern.cc

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@
2121
#include "rust-hir-type-check-expr.h"
2222
#include "rust-type-util.h"
2323
#include "rust-immutable-name-resolution-context.h"
24+
#include "rust-tyty.h"
25+
#include "tree.h"
2426

2527
namespace Rust {
2628
namespace Resolver {
@@ -778,7 +780,32 @@ TypeCheckPattern::visit (HIR::SlicePattern &pattern)
778780
auto &array_ty_ty = static_cast<TyTy::ArrayType &> (*parent);
779781
parent_element_ty = array_ty_ty.get_element_type ();
780782
auto capacity = array_ty_ty.get_capacity ();
781-
tree cap = capacity->get_value ();
783+
784+
tree cap = error_mark_node;
785+
if (capacity->get_kind () != TyTy::TypeKind::CONST)
786+
{
787+
// Error case - capacity is not a const type
788+
break;
789+
}
790+
791+
auto *capacity_const = capacity->as_const_type ();
792+
switch (capacity_const->const_kind ())
793+
{
794+
case TyTy::BaseConstType::ConstKind::Value:
795+
{
796+
const auto &const_value
797+
= *static_cast<TyTy::ConstValueType *> (capacity);
798+
cap = const_value.get_value ();
799+
}
800+
break;
801+
802+
case TyTy::BaseConstType::ConstKind::Decl:
803+
case TyTy::BaseConstType::ConstKind::Infer:
804+
case TyTy::BaseConstType::ConstKind::Error:
805+
cap = error_mark_node;
806+
break;
807+
}
808+
782809
if (error_operand_p (cap))
783810
{
784811
rust_error_at (parent->get_locus (),

gcc/rust/typecheck/rust-hir-type-check-type.cc

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -706,14 +706,14 @@ TypeCheckType::visit (HIR::ArrayType &type)
706706
rust_assert (ok);
707707
context->insert_type (type.get_size_expr ().get_mappings (), expected_ty);
708708

709-
TyTy::ConstType *const_type = nullptr;
709+
TyTy::BaseConstType *const_type = nullptr;
710710
if (capacity_type->get_kind () == TyTy::TypeKind::CONST)
711711
{
712-
const_type = static_cast<TyTy::ConstType *> (capacity_type);
712+
const_type = capacity_type->as_const_type ();
713713

714714
unify_site (type.get_size_expr ().get_mappings ().get_hirid (),
715715
TyTy::TyWithLocation (expected_ty),
716-
TyTy::TyWithLocation (const_type->get_ty (),
716+
TyTy::TyWithLocation (const_type->get_specified_type (),
717717
type.get_size_expr ().get_locus ()),
718718
type.get_size_expr ().get_locus ());
719719
}
@@ -727,30 +727,26 @@ TypeCheckType::visit (HIR::ArrayType &type)
727727
type.get_size_expr ().get_locus ());
728728

729729
if (result->is<TyTy::ErrorType> ())
730-
{
731-
const_type
732-
= new TyTy::ConstType (TyTy::ConstType::ConstKind::Error, "",
733-
expected_ty, error_mark_node, {},
734-
type.get_size_expr ().get_locus (), size_id,
735-
size_id);
736-
}
730+
const_type = new TyTy::ConstErrorType (expected_ty, size_id, size_id);
737731
else
738732
{
739733
auto ctx = Compile::Context::get ();
740734
tree capacity_expr
741735
= Compile::HIRCompileBase::query_compile_const_expr (
742736
ctx, capacity_type, type.get_size_expr ());
743737

744-
const_type = new TyTy::ConstType (TyTy::ConstType::ConstKind::Value,
745-
"", expected_ty, capacity_expr, {},
746-
type.get_size_expr ().get_locus (),
747-
size_id, size_id);
738+
const_type = new TyTy::ConstValueType (capacity_expr, expected_ty,
739+
size_id, size_id);
740+
context->insert_type (type.get_size_expr ().get_mappings (),
741+
const_type->as_base_type ());
748742
}
749743
}
750744

751745
translated
752746
= new TyTy::ArrayType (type.get_mappings ().get_hirid (), type.get_locus (),
753-
const_type, TyTy::TyVar (element_type->get_ref ()));
747+
TyTy::TyVar (
748+
const_type->as_base_type ()->get_ty_ref ()),
749+
TyTy::TyVar (element_type->get_ref ()));
754750
}
755751

756752
void

0 commit comments

Comments
 (0)