Merge branch 'trunk' into NumBytesTo

This commit is contained in:
Richard Feldman 2021-08-19 01:37:39 -04:00 committed by GitHub
commit 0bebb64bae
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
16 changed files with 555 additions and 325 deletions

View file

@ -271,33 +271,11 @@ fn build_transform_caller_help<'a, 'ctx, 'env>(
}
match closure_data_layout {
Layout::Closure(_, lambda_set, _) => {
if let Layout::Struct(&[]) = lambda_set.runtime_representation() {
// do nothing
} else {
let closure_type =
basic_type_from_layout(env, &lambda_set.runtime_representation())
.ptr_type(AddressSpace::Generic);
let closure_cast = env
.builder
.build_bitcast(closure_ptr, closure_type, "load_opaque")
.into_pointer_value();
let closure_data = env.builder.build_load(closure_cast, "load_opaque");
arguments_cast.push(closure_data);
}
Layout::Struct(&[]) => {
// nothing to add
}
Layout::Struct([Layout::Closure(_, lambda_set, _)]) => {
// a case required for Set.walk; may be able to remove when we can define builtins in
// terms of other builtins in the right way (using their function symbols instead of
// hacking with lowlevel ops).
let closure_type = basic_type_from_layout(
env,
&Layout::Struct(&[lambda_set.runtime_representation()]),
)
.ptr_type(AddressSpace::Generic);
other => {
let closure_type = basic_type_from_layout(env, &other).ptr_type(AddressSpace::Generic);
let closure_cast = env
.builder
@ -308,13 +286,6 @@ fn build_transform_caller_help<'a, 'ctx, 'env>(
arguments_cast.push(closure_data);
}
Layout::Struct([]) => {
// do nothing, should try to remove this case later
}
Layout::Struct(_) => {
// do nothing, should try to remove this case later
}
other => unreachable!("layout is not valid for a closure: {:?}", other),
}
let call = {
@ -625,26 +596,23 @@ pub fn build_compare_wrapper<'a, 'ctx, 'env>(
let default = [value1, value2];
let arguments_cast = match closure_data_layout {
Layout::Closure(_, lambda_set, _) => {
if let Layout::Struct(&[]) = lambda_set.runtime_representation() {
&default
} else {
let closure_type =
basic_type_from_layout(env, &lambda_set.runtime_representation())
.ptr_type(AddressSpace::Generic);
let closure_cast = env
.builder
.build_bitcast(closure_ptr, closure_type, "load_opaque")
.into_pointer_value();
let closure_data = env.builder.build_load(closure_cast, "load_opaque");
env.arena.alloc([value1, value2, closure_data]) as &[_]
}
Layout::Struct(&[]) => {
// nothing to add
&default
}
other => {
let closure_type =
basic_type_from_layout(env, &other).ptr_type(AddressSpace::Generic);
let closure_cast = env
.builder
.build_bitcast(closure_ptr, closure_type, "load_opaque")
.into_pointer_value();
let closure_data = env.builder.build_load(closure_cast, "load_opaque");
env.arena.alloc([value1, value2, closure_data]) as &[_]
}
Layout::Struct([]) => &default,
other => unreachable!("layout is not valid for a closure: {:?}", other),
};
let call = env.builder.build_call(

View file

@ -1082,14 +1082,6 @@ pub fn build_exp_expr<'a, 'ctx, 'env>(
)
.unwrap()
}
(StructValue(argument), Layout::Closure(_, _, _)) => env
.builder
.build_extract_value(
argument,
*index as u32,
env.arena.alloc(format!("closure_field_access_{}_", index)),
)
.unwrap(),
(
PointerValue(argument),
Layout::Union(UnionLayout::NonNullableUnwrapped(fields)),
@ -3626,18 +3618,6 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
lambda_set: LambdaSet<'a>,
result: &Layout<'a>,
) {
let context = &env.context;
let builder = env.builder;
// STEP 1: build function header
// e.g. `roc__main_1_Fx_caller`
let function_name = format!(
"roc__{}_{}_caller",
def_name,
alias_symbol.as_str(&env.interns)
);
let mut argument_types = Vec::with_capacity_in(arguments.len() + 3, env.arena);
for layout in arguments {
@ -3654,6 +3634,9 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
};
argument_types.push(closure_argument_type.into());
let context = &env.context;
let builder = env.builder;
let result_type = basic_type_from_layout(env, result);
let roc_call_result_type =
@ -3662,6 +3645,15 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
let output_type = { roc_call_result_type.ptr_type(AddressSpace::Generic) };
argument_types.push(output_type.into());
// STEP 1: build function header
// e.g. `roc__main_1_Fx_caller`
let function_name = format!(
"roc__{}_{}_caller",
def_name,
alias_symbol.as_str(&env.interns)
);
let function_type = context.void_type().fn_type(&argument_types, false);
let function_value = add_func(
@ -3680,9 +3672,15 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
let mut parameters = function_value.get_params();
let output = parameters.pop().unwrap().into_pointer_value();
let closure_data_ptr = parameters.pop().unwrap().into_pointer_value();
let closure_data = builder.build_load(closure_data_ptr, "load_closure_data");
let closure_data = if let Some(closure_data_ptr) = parameters.pop() {
let closure_data =
builder.build_load(closure_data_ptr.into_pointer_value(), "load_closure_data");
env.arena.alloc([closure_data]) as &[_]
} else {
&[]
};
let mut parameters = parameters;
@ -3696,7 +3694,7 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
function_value,
evaluator,
evaluator.get_call_conventions(),
&[closure_data],
closure_data,
result_type,
);
@ -3714,8 +3712,12 @@ pub fn build_closure_caller<'a, 'ctx, 'env>(
);
// STEP 4: build a {} -> u64 function that gives the size of the closure
let layout = lambda_set.runtime_representation();
build_host_exposed_alias_size(env, def_name, alias_symbol, layout);
build_host_exposed_alias_size(
env,
def_name,
alias_symbol,
lambda_set.runtime_representation(),
);
}
fn build_host_exposed_alias_size<'a, 'ctx, 'env>(

View file

@ -88,10 +88,6 @@ fn build_hash_layout<'a, 'ctx, 'env>(
)
}
},
Layout::Closure(_, _, _) => {
unreachable!("the type system will guarantee these are never hashed")
}
}
}

View file

@ -198,10 +198,6 @@ fn build_eq<'a, 'ctx, 'env>(
)
}
},
Layout::Closure(_, _, _) => {
unreachable!("the type system will guarantee these are never compared")
}
}
}
@ -340,10 +336,6 @@ fn build_neq<'a, 'ctx, 'env>(
Layout::RecursivePointer => {
unreachable!("recursion pointers should never be compared directly")
}
Layout::Closure(_, _, _) => {
unreachable!("the type system will guarantee these are never compared")
}
}
}

View file

@ -26,10 +26,6 @@ pub fn basic_type_from_layout<'a, 'ctx, 'env>(
use Layout::*;
match layout {
Closure(_args, closure_layout, _ret_layout) => {
let closure_data_layout = closure_layout.runtime_representation();
basic_type_from_layout(env, &closure_data_layout)
}
Struct(sorted_fields) => basic_type_from_record(env, sorted_fields),
Union(union_layout) => {
use UnionLayout::*;

View file

@ -659,23 +659,6 @@ fn modify_refcount_layout_build_function<'a, 'ctx, 'env>(
Some(function)
}
Closure(_, lambda_set, _) => {
if lambda_set.contains_refcounted() {
let function = modify_refcount_layout_build_function(
env,
parent,
layout_ids,
mode,
when_recursive,
&lambda_set.runtime_representation(),
)?;
Some(function)
} else {
None
}
}
Struct(layouts) => {
let function = modify_refcount_struct(env, layout_ids, layouts, mode, when_recursive);