fix if alternative unconditional jump len

This commit is contained in:
Scott Richmond 2025-06-20 17:09:41 -04:00
parent 92d0915a71
commit 23d9945c48
5 changed files with 34 additions and 29 deletions

View File

@ -589,10 +589,10 @@ fn zero? {
fn gt? { fn gt? {
"Returns true if numbers are in decreasing order." "Returns true if numbers are in decreasing order."
(x as :number) -> true (x as :number) -> true
(x as :number, y as :number) -> base :gt (x, y) (x as :number, y as :number) -> base :gt? (x, y)
(x, y, ...zs) -> loop (y, zs) with { (x, y, ...zs) -> loop (y, zs) with {
(a, [b]) -> base :gt (a, b) (a, [b]) -> base :gt? (a, b)
(a, [b, ...cs]) -> if base :gt (a, b) (a, [b, ...cs]) -> if base :gt? (a, b)
then recur (b, cs) then recur (b, cs)
else false else false
} }
@ -601,10 +601,10 @@ fn gt? {
fn gte? { fn gte? {
"Returns true if numbers are in decreasing or flat order." "Returns true if numbers are in decreasing or flat order."
(x as :number) -> true (x as :number) -> true
(x as :number, y as :number) -> base :gte (x, y) (x as :number, y as :number) -> base :gte? (x, y)
(x, y, ...zs) -> loop (y, zs) with { (x, y, ...zs) -> loop (y, zs) with {
(a, [b]) -> base :gte (a, b) (a, [b]) -> base :gte? (a, b)
(a, [b, ...cs]) -> if base :gte (a, b) (a, [b, ...cs]) -> if base :gte? (a, b)
then recur (b, cs) then recur (b, cs)
else false else false
} }
@ -613,10 +613,10 @@ fn gte? {
fn lt? { fn lt? {
"Returns true if numbers are in increasing order." "Returns true if numbers are in increasing order."
(x as :number) -> true (x as :number) -> true
(x as :number, y as :number) -> base :lt (x, y) (x as :number, y as :number) -> base :lt? (x, y)
(x, y, ...zs) -> loop (y, zs) with { (x, y, ...zs) -> loop (y, zs) with {
(a, [b]) -> base :lt (a, b) (a, [b]) -> base :lt? (a, b)
(a, [b, ...cs]) -> if base :lt (a, b) (a, [b, ...cs]) -> if base :lt? (a, b)
then recur (b, cs) then recur (b, cs)
else false else false
} }
@ -625,10 +625,10 @@ fn lt? {
fn lte? { fn lte? {
"Returns true if numbers are in increasing or flat order." "Returns true if numbers are in increasing or flat order."
(x as :number) -> true (x as :number) -> true
(x as :number, y as :number) -> base :lte (x, y) (x as :number, y as :number) -> base :lte? (x, y)
(x, y, ...zs) -> loop (y, zs) with { (x, y, ...zs) -> loop (y, zs) with {
(a, [b]) -> base :lte (a, b) (a, [b]) -> base :lte? (a, b)
(a, [b, ...cs]) -> if base :lte (a, b) (a, [b, ...cs]) -> if base :lte? (a, b)
then recur (b, cs) then recur (b, cs)
else false else false
} }
@ -669,7 +669,7 @@ fn odd? {
fn min { fn min {
"Returns the number in its arguments that is closest to negative infinity." "Returns the number in its arguments that is closest to negative infinity."
(x as :number) -> x (x as :number) -> x
(x as :number, y as :number) -> if lt? (x, y) then x else y (x as :number, y as :number) -> if base :lt? (x, y) then x else y
(x, y, ...zs) -> fold (min, zs, min (x, y)) (x, y, ...zs) -> fold (min, zs, min (x, y))
} }
@ -698,7 +698,7 @@ fn at {
fn first { fn first {
"Returns the first element of a list or tuple." "Returns the first element of a list or tuple."
(xs) if ordered? (xs) -> at (xs, 0) (xs) if ordered? -> at (xs, 0)
} }
fn second { fn second {

View File

@ -1,15 +1,10 @@
fn add (x as :number, y as :number) -> base :add (x, y) fn min {
"Returns the number in its arguments that is closest to negative infinity."
(x as :number) -> x
(x as :number, y as :number) -> if base :lt? (x, y) then x else y
(x, y, ...zs) -> (min, zs, min (x, y))
}
fn inc (n as :number) -> base :add (n, 1) fn lt? (x as :number, y as :number) -> base :lt? (x, y)
fn dec (n as :number) -> base :sub (n, 1) #{min, lt?}
fn sub (x as :number, y as :number) -> base :sub (x, y)
fn panics! () -> add ("foo", "bar")
fn print!(x) -> base :print! (x)
fn eq? (x, y) -> base :eq? (x, y)
#{add, inc, dec, sub, print!, panics!, eq?}

View File

@ -352,3 +352,13 @@ The second clause causes a panic in the compiler.
I'm not entirely sure what's going on. I'm not entirely sure what's going on.
That said, I'm pretty sure the root of it is that the fact that `two` was already bound in the first clause means that it's in the constants vector in that chunk under the name "two." That said, I'm pretty sure the root of it is that the fact that `two` was already bound in the first clause means that it's in the constants vector in that chunk under the name "two."
...
So that's fixed!
But:
Prelude functions are not properly closing over their upvalues.
Which is not right.
We get: `get_upvalue 000` and a panic: `index out of bounds: the len is 0 but the index is 0`.
The vec in question is the LFn::Defined.closed.

View File

@ -733,7 +733,7 @@ impl<'a> Compiler<'a> {
self.stack_depth -= 1; self.stack_depth -= 1;
let end_idx = self.len(); let end_idx = self.len();
let jif_offset = jump_idx - jif_idx; let jif_offset = jump_idx - jif_idx;
let jump_offset = end_idx - jump_idx - 1; let jump_offset = end_idx - jump_idx - 3;
self.patch_jump(jif_idx, jif_offset); self.patch_jump(jif_idx, jif_offset);
self.patch_jump(jump_idx, jump_offset); self.patch_jump(jump_idx, jump_offset);
} }

View File

@ -114,7 +114,7 @@ pub fn run(src: &'static str) {
pub fn main() { pub fn main() {
env::set_var("RUST_BACKTRACE", "1"); env::set_var("RUST_BACKTRACE", "1");
let src = " let src = "
let (1, 2, 3) = (1, 2, 3)
"; ";
run(src); run(src);
} }