use GetTagId

This commit is contained in:
Folkert 2021-06-20 20:49:36 +02:00
parent bc8bd95b3d
commit 0de501554a
2 changed files with 28 additions and 42 deletions

View file

@ -1660,8 +1660,7 @@ pub fn build_exp_expr<'a, 'ctx, 'env>(
builder.build_load(tag_id_pointer.into_pointer_value(), "load_tag_id") builder.build_load(tag_id_pointer.into_pointer_value(), "load_tag_id")
} }
UnionLayout::Recursive(_) => { UnionLayout::Recursive(_) => {
let pointer = builder.build_alloca(argument.get_type(), "get_type"); let pointer = argument.into_pointer_value();
builder.build_store(pointer, argument);
let tag_id_pointer = builder.build_bitcast( let tag_id_pointer = builder.build_bitcast(
pointer, pointer,
env.context.i64_type().ptr_type(AddressSpace::Generic), env.context.i64_type().ptr_type(AddressSpace::Generic),

View file

@ -1161,58 +1161,45 @@ fn test_to_equality<'a>(
Layout<'a>, Layout<'a>,
Option<ConstructorKnown<'a>>, Option<ConstructorKnown<'a>>,
) { ) {
let (rhs_symbol, mut stores, _layout) = let (rhs_symbol, mut stores, test_layout) =
path_to_expr_help(env, cond_symbol, &path, *cond_layout); path_to_expr_help(env, cond_symbol, &path, *cond_layout);
match test { match test {
Test::IsCtor { Test::IsCtor { tag_id, union, .. } => {
tag_id,
union,
arguments,
..
} => {
let path_symbol = rhs_symbol; let path_symbol = rhs_symbol;
// the IsCtor check should never be generated for tag unions of size 1 // the IsCtor check should never be generated for tag unions of size 1
// (e.g. record pattern guard matches) // (e.g. record pattern guard matches)
debug_assert!(union.alternatives.len() > 1); debug_assert!(union.alternatives.len() > 1);
let lhs = Expr::Literal(Literal::Int(tag_id as i128)); match test_layout {
Layout::Union(union_layout) => {
let lhs = Expr::Literal(Literal::Int(tag_id as i128));
let mut field_layouts = let rhs = Expr::GetTagId {
bumpalo::collections::Vec::with_capacity_in(arguments.len(), env.arena); structure: path_symbol,
union_layout,
};
// add the tag discriminant let lhs_symbol = env.unique_symbol();
field_layouts.push(Layout::Builtin(Builtin::Int64)); let rhs_symbol = env.unique_symbol();
for (_, layout) in arguments { stores.push((lhs_symbol, Layout::Builtin(Builtin::Int64), lhs));
field_layouts.push(layout); stores.push((rhs_symbol, Layout::Builtin(Builtin::Int64), rhs));
(
stores,
lhs_symbol,
rhs_symbol,
Layout::Builtin(Builtin::Int64),
Some(ConstructorKnown::OnlyPass {
scrutinee: path_symbol,
layout: *cond_layout,
tag_id,
}),
)
}
_ => unreachable!("{:?}", (cond_layout, union)),
} }
let field_layouts = field_layouts.into_bump_slice();
let rhs = Expr::AccessAtIndex {
index: 0,
field_layouts,
structure: path_symbol,
wrapped: Wrapped::MultiTagUnion,
};
let lhs_symbol = env.unique_symbol();
let rhs_symbol = env.unique_symbol();
stores.push((lhs_symbol, Layout::Builtin(Builtin::Int64), lhs));
stores.push((rhs_symbol, Layout::Builtin(Builtin::Int64), rhs));
(
stores,
lhs_symbol,
rhs_symbol,
Layout::Builtin(Builtin::Int64),
Some(ConstructorKnown::OnlyPass {
scrutinee: path_symbol,
layout: *cond_layout,
tag_id,
}),
)
} }
Test::IsInt(test_int) => { Test::IsInt(test_int) => {
// TODO don't downcast i128 here // TODO don't downcast i128 here