Merge pull request #332 from rtfeldman/int-div

Int Div Code Gen
This commit is contained in:
Richard Feldman 2020-04-27 04:59:26 -04:00 committed by GitHub
commit 00d9c240e7
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 51 additions and 6 deletions

View file

@ -294,6 +294,12 @@ pub fn types() -> MutMap<Symbol, (SolvedType, Region)> {
),
);
// div : Int, Int -> Int
add_type(
Symbol::INT_DIV_UNSAFE,
SolvedType::Func(vec![int_type(), int_type()], Box::new(int_type())),
);
// mod : Int, Int -> Result Int [ DivByZero ]*
add_type(
Symbol::INT_MOD,

View file

@ -348,9 +348,23 @@ pub fn types() -> MutMap<Symbol, (SolvedType, Region)> {
// lowest : Int
add_type(Symbol::INT_LOWEST, int_type(UVAR1));
// div or (//) : Int, Int -> Int
// div or (//) : Int, Int -> Result Int [ DivByZero ]*
let div_by_zero = SolvedType::TagUnion(
vec![(TagName::Global("DivByZero".into()), vec![])],
Box::new(SolvedType::Wildcard),
);
add_type(
Symbol::INT_DIV,
unique_function(
vec![int_type(UVAR1), int_type(UVAR2)],
result_type(UVAR3, int_type(UVAR4), lift(UVAR5, div_by_zero)),
),
);
// div or (//) : Int, Int -> Int
add_type(
Symbol::INT_DIV_UNSAFE,
unique_function(vec![int_type(UVAR1), int_type(UVAR2)], int_type(UVAR3)),
);

View file

@ -1226,6 +1226,17 @@ fn call_with_args<'a, 'ctx, 'env>(
Symbol::FLOAT_ROUND => call_intrinsic(LLVM_LROUND_I64_F64, env, args),
Symbol::LIST_SET => list_set(parent, args, env, InPlace::Clone),
Symbol::LIST_SET_IN_PLACE => list_set(parent, args, env, InPlace::InPlace),
Symbol::INT_DIV_UNSAFE => {
debug_assert!(args.len() == 2);
let int_val = env.builder.build_int_signed_div(
args[0].0.into_int_value(),
args[1].0.into_int_value(),
"div_i64",
);
BasicValueEnum::IntValue(int_val)
}
_ => {
let fn_val = env
.module

View file

@ -159,6 +159,19 @@ mod gen_builtins {
);
}
#[test]
fn gen_div_i64() {
assert_evals_to!(
indoc!(
r#"
Int.divUnsafe 1000 100
"#
),
10,
i64
);
}
#[test]
fn gen_order_of_arithmetic_ops() {
assert_evals_to!(

View file

@ -599,6 +599,7 @@ define_builtins! {
9 INT_EQ_I64: "#eqi64" // Equality on 64-bit integers, the standard in Roc
10 INT_EQ_I1: "#eqi1" // Equality on boolean (theoretically i1) values
11 INT_EQ_I8: "#eqi8" // Equality on byte (theoretically i8) values
12 INT_DIV_UNSAFE: "divUnsafe" // TODO remove once we can code gen Result
}
3 FLOAT: "Float" => {
0 FLOAT_FLOAT: "Float" imported // the Float.Float type alias

View file

@ -1944,7 +1944,7 @@ mod test_uniq_solve {
Int.highest // Int.highest
"#
),
"Attr * Int",
"Attr * (Result (Attr * Int) (Attr * [ DivByZero ]*))",
);
}
@ -1956,7 +1956,7 @@ mod test_uniq_solve {
3 // 4
"#
),
"Attr * Int",
"Attr * (Result (Attr * Int) (Attr * [ DivByZero ]*))",
);
}
@ -1968,7 +1968,7 @@ mod test_uniq_solve {
3 // Int.highest
"#
),
"Attr * Int",
"Attr * (Result (Attr * Int) (Attr * [ DivByZero ]*))",
);
}
@ -2097,8 +2097,8 @@ mod test_uniq_solve {
reverse
"#
),
// "Attr * (Attr * (List (Attr (a | b) c)) -> Attr (* | a | b) (List (Attr b c)))",
"Attr * (Attr * (List (Attr (a | b) c)) -> Attr (* | a | b) (List (Attr a c)))",
"Attr * (Attr * (List (Attr (a | b) c)) -> Attr (* | a | b) (List (Attr b c)))",
// "Attr * (Attr * (List (Attr (a | b) c)) -> Attr (* | a | b) (List (Attr a c)))",
);
}