diff --git a/flipjump/stl/hex/div.fj b/flipjump/stl/hex/div.fj index 067ec07..8561257 100644 --- a/flipjump/stl/hex/div.fj +++ b/flipjump/stl/hex/div.fj @@ -76,18 +76,18 @@ ns hex { // r = a%b (signed modulo - signed according to rem_opt:) // if rem_opt is 0: sign(r)==sign(b) // Most programming languages implement this option. // if rem_opt is 1: sign(r)==sign(a) - // if rem_opt is 0: sign(r) is always positive + // if rem_opt is 2: sign(r) is always positive + // (On any other rem_opt value, will jump to "div0". This check is guaranteed to be after the b==0 check). // Anyway, a == q*b + r. // @NOTE: a,b are SIGNED numbers. If you want a division with unsigned ints, use the div macro. // - // // q,a are hex[:n], while r,b are hex[:nb]. div0 is the bit-address this function will jump to in-case b is zero. // @requires hex.sub.init & hex.cmp.init (or hex.init) - def idiv n, nb, q, r, a, b, div0, rem_opt @ set_negative_a, test_b, set_negative_b,\ - negative_a, negative_b, one_negative, do_div, neg_b_2, neg_ans, end { - stl.comp_if1 rem_opt == 444, end // TODO remove when the 3 rem_opts are implemented - + def idiv n, nb, q, r, a, b, div0, rem_opt\ + @ set_negative_a, test_b, set_negative_b, update_rem_opt_0, update_rem_opt_2, add_b, sub_b,\ + negative_a, negative_b, one_negative, do_div, neg_b_2, neg_ans, end, fix_rem { .if0 nb, b, div0 + stl.comp_if1 ((rem_opt < 0) | (rem_opt > 2)), div0 bit.zero negative_a bit.zero negative_b @@ -110,13 +110,34 @@ ns hex { bit.if0 negative_a, neg_b_2 .neg n, a + .neg nb, r neg_b_2: bit.if0 negative_b, neg_ans .neg nb, b - .neg nb, r neg_ans: - bit.if0 one_negative, end + bit.if0 one_negative, fix_rem .neg n, q + + fix_rem: + stl.comp_if1 rem_opt == 0, update_rem_opt_0 + stl.comp_if1 rem_opt == 2, update_rem_opt_2 + ;end + + update_rem_opt_0: + bit.if one_negative, end, add_b + + update_rem_opt_2: + bit.if0 negative_a, end + bit.if negative_b, add_b, sub_b + + add_b: + hex.add nb, r, b + hex.dec n, q + ;end + + sub_b: + hex.sub nb, r, b + hex.inc n, q ;end negative_a: diff --git a/programs/hexlib_tests/div/test_idiv_cases.fj b/programs/hexlib_tests/div/test_idiv_cases.fj index b4f134d..352cdb3 100644 --- a/programs/hexlib_tests/div/test_idiv_cases.fj +++ b/programs/hexlib_tests/div/test_idiv_cases.fj @@ -1,8 +1,17 @@ test_idiv_opt 20, 12, 1, 8, idiv_opt0 +test_idiv_opt 20, (0-12), (0-2), (0-4), idiv_opt0 +test_idiv_opt (0-20), 12, (0-2), 4, idiv_opt0 +test_idiv_opt (0-20), (0-12), 1, (0-8), idiv_opt0 test_idiv_opt 20, 12, 1, 8, idiv_opt1 +test_idiv_opt 20, (0-12), (0-1), 8, idiv_opt1 +test_idiv_opt (0-20), 12, (0-1), (0-8), idiv_opt1 +test_idiv_opt (0-20), (0-12), 1, (0-8), idiv_opt1 test_idiv_opt 20, 12, 1, 8, idiv_opt2 +test_idiv_opt 20, (0-12), (0-1), 8, idiv_opt2 +test_idiv_opt (0-20), 12, (0-2), 4, idiv_opt2 +test_idiv_opt (0-20), (0-12), 2, 4, idiv_opt2 stl.loop diff --git a/tests/inout/hexlib_tests/div/test_idiv_cases.out b/tests/inout/hexlib_tests/div/test_idiv_cases.out index 10b596f..565d270 100644 --- a/tests/inout/hexlib_tests/div/test_idiv_cases.out +++ b/tests/inout/hexlib_tests/div/test_idiv_cases.out @@ -1,3 +1,12 @@ == == == +== +== +== +== +== +== +== +== +==