Skip to content

Commit 43c3c76

Browse files
Merge pull request #1509 from andrew-johnson-4/poly-return-macro-helpers
Poly return macro helpers
2 parents 9f6386c + 510c653 commit 43c3c76

12 files changed

+30627
-30252
lines changed

BOOTSTRAP/cli.c

+30,528-30,216
Large diffs are not rendered by default.

PLATFORM/C/LIB/common-macros.lsts

+19-16
Original file line numberDiff line numberDiff line change
@@ -7,30 +7,33 @@ typed macro macro::set(lhs: lazy, rhs: lazy): lazy = (
77
mov(rhs, lhs)
88
);
99

10+
typed macro macro::set(base index: macro::lhs-index, rhs: lazy): lazy = (
11+
$"set[]"( base, index, rhs )
12+
);
13+
1014
#typed macro macro::set(base field: macro::lhs-field, rhs: lazy): lazy = (
1115
# macro::concat(l"set.", field) (base, rhs)
1216
#);
1317

14-
#typed macro macro::set(base index: macro::lhs-index, rhs: lazy): lazy = (
15-
# $"set[]"( macro::lhs-as-rhs(base), index, rhs )
16-
# macro::concat(l"set.", field) (base, rhs)
17-
#);
18+
typed macro macro::lhs-as-rhs(v: macro::variable): lazy = (
19+
v
20+
);
1821

19-
#typed macro macro::lhs-as-rhs(v: macro::variable): lazy = (
20-
# v
21-
#);
22+
typed macro macro::lhs-as-rhs(base: macro::lhs-address-of): lazy = (
23+
&v
24+
);
2225

23-
#typed macro macro::lhs-as-rhs(_: macro::literal<"&">, v: lazy): lazy = (
24-
# &v
25-
#);
26+
typed macro macro::lhs-address-of(base: lazy): lazy = (
27+
base
28+
);
2629

27-
#typed macro macro::lhs-as-rhs(base field: macro::lhs-index): lazy = (
28-
# macro::concat(l".", field)(base)
29-
#);
30+
typed macro macro::lhs-as-rhs(base field: macro::lhs-index): lazy = (
31+
macro::concat(l".", field)(base)
32+
);
3033

31-
#typed macro macro::lhs-index(base: lazy, field: lazy): lazy = (
32-
# base; field
33-
#);
34+
typed macro macro::lhs-index(base: lazy, field: lazy): lazy = (
35+
base; field
36+
);
3437

3538
typed macro macro::for(item: lazy, iter: List<?>, loop: lazy): lazy = (
3639
let uuid(iter-term) = iter;

PLUGINS/FRONTEND/LSTS/lsts-parse.lsts

+14-9
Original file line numberDiff line numberDiff line change
@@ -274,7 +274,12 @@ let lsts-parse-typed-macro(tokens: List<Token>): (AST, List<Token>) = (
274274
lsts-parse-expect(c"(", tokens); tokens = tail(tokens);
275275
while lsts-parse-head(tokens)!=c")" {
276276
if not(is(margs,ASTNil)) then { lsts-parse-expect(c",", tokens); tokens = tail(tokens); };
277-
(let mbind, tokens) = lsts-parse-atom-without-tail(tokens);
277+
(let binding, tokens) = lsts-parse-identifier(tokens);
278+
let mbind = mk-var(binding);
279+
while lsts-parse-head(tokens) != c":" {
280+
(binding, tokens) = lsts-parse-identifier(tokens);
281+
mbind = mk-cons(mbind, mk-var(binding));
282+
};
278283
lsts-parse-expect(c":", tokens); tokens = tail(tokens);
279284
(let mbindt, tokens) = lsts-parse-type(tokens);
280285
let marg = mk-app(mk-lit(c":"), mk-cons(mbind, mk-atype(mbindt)));
@@ -324,7 +329,7 @@ let lsts-parse-type-conjugate(tokens: List<Token>): Tuple<Type,List<Token>> = (
324329
lsts-parse-expect(c"?", tokens); tokens = tail(tokens);
325330
TAny {}
326331
} else if lsts-is-ident-head(lsts-parse-head(tokens)) && not(lsts-is-type-tag(lsts-parse-head(tokens))) {
327-
let varname = lsts-parse-head(tokens); tokens = tail(tokens);
332+
(let varname, tokens) = lsts-parse-identifier(tokens);
328333
TVar { varname }
329334
} else {
330335
if not(lsts-is-type-tag(lsts-parse-head(tokens))) {
@@ -1075,13 +1080,13 @@ let lsts-parse-small-expression(tokens: List<Token>): Tuple<AST,List<Token>> = (
10751080
tokens = rhs-rest.second;
10761081
lsts-parse-expect(c"}", tokens); tokens = tail(tokens);
10771082
base = mk-app(
1078-
Var{ c"macro::while", with-location(mk-token("macro::while"),loc) },
1079-
mk-cons(
1080-
c-rest.first,
1081-
mk-app(
1082-
Var{ c"scope", with-location(mk-token("scope"),loc) },
1083-
rhs-rest.first
1084-
)
1083+
mk-app(
1084+
Var{ c"while", with-location(mk-token("while"),loc) },
1085+
c-rest.first
1086+
),
1087+
mk-app(
1088+
Var{ c"scope", with-location(mk-token("scope"),loc) },
1089+
rhs-rest.first
10851090
)
10861091
);
10871092
);

SRC/std-apply-macro-candidates.lsts

+13-5
Original file line numberDiff line numberDiff line change
@@ -11,11 +11,9 @@ let std-apply-macro-candidates(tctx: TContext?, mname: CString, margs: AST, cand
1111
if not(non-zero(t)) {
1212
(let new-tctx, let mctx) = std-try-destructure-macro(tctx, margs, ctype, mlhs);
1313
if mctx.is-some then mctx = union(mctx, Some{extract-uuids(mrhs)});
14-
if mctx.is-some then t = with-location(substitute(mctx.get-or-panic, mrhs), margs.location);
14+
if mctx.is-some then t = with-location-preserve(substitute(mctx.get-or-panic, mrhs), margs.location);
1515
}
1616
};
17-
if not(non-zero(t)) then fail("Macro Application failed match during destructuring: \{mname}\n");
18-
(tctx, t) = std-infer-expr(tctx, t, false, Used, TAny);
1917
(tctx, t)
2018
);
2119

@@ -44,8 +42,18 @@ let std-try-destructure-macro(tctx: TContext?, margs: AST, mtype: Type, mcandida
4442
App{left:Lit{key:c":"}, right:App{mstruct=left, right:AType{tt=tt}}} => (
4543
if non-zero(std-macro-helper-name(tt))
4644
then {
47-
(tctx, let helped) = std-apply-macro(tctx, std-macro-helper-name(tt), margs);
48-
(tctx, std-direct-destructure-macro(helped, mstruct))
45+
let macro-helper = std-macro-helper-name(tt);
46+
match margs {
47+
App{left:Var{maybe-helper=key}, helper-args=right} => (
48+
if macro-helper==maybe-helper {
49+
(tctx, let helped) = std-apply-macro-weak(tctx, macro-helper, helper-args);
50+
if non-zero(helped)
51+
then (tctx, std-direct-destructure-macro(helped, mstruct))
52+
else (tctx, no)
53+
} else (tctx, no)
54+
);
55+
_ => (tctx, no);
56+
}
4957
} else (tctx, std-direct-destructure-macro(margs, mstruct))
5058
);
5159
_ => (tctx, no);

SRC/std-apply-macro.lsts

+9-2
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,10 @@ let std-apply-macro(tctx: Maybe<TContext>, t: AST): (TContext?, AST) = (
77
}
88
);
99

10-
let std-apply-macro(tctx: Maybe<TContext>, mname: CString, margs: AST): (TContext?, AST) = (
10+
let std-apply-macro(tctx: Maybe<TContext>, mname: CString, margs: AST): (TContext?, AST) = std-apply-macro(tctx, mname, margs, true);
11+
let std-apply-macro-weak(tctx: Maybe<TContext>, mname: CString, margs: AST): (TContext?, AST) = std-apply-macro(tctx, mname, margs, false);
12+
13+
let std-apply-macro(tctx: Maybe<TContext>, mname: CString, margs: AST, strong: Bool): (TContext?, AST) = (
1114
let row = index-macro-table.lookup(mname, [] :: List<(Type,Type,AST)>);
1215
let peep-holes = TAny;
1316
let peeped = TAny;
@@ -42,7 +45,10 @@ let std-apply-macro(tctx: Maybe<TContext>, mname: CString, margs: AST): (TContex
4245
candidates = [(mtype,mterm)];
4346
}
4447
};
45-
std-apply-macro-candidates(tctx, mname, margs, candidates);
48+
(tctx, let result) = std-apply-macro-candidates(tctx, mname, margs, candidates);
49+
if strong && not(non-zero(result)) then exit-error("Failed to Apply Macro: \{mname}", margs);
50+
if strong then (tctx, result) = std-infer-expr(tctx, result, false, Used, TAny);
51+
(tctx, result)
4652
);
4753

4854
let std-infer-peeped-arguments(tctx: Maybe<TContext>, t: AST, peep: Type): (Type, AST) = (
@@ -60,6 +66,7 @@ let std-infer-peeped-arguments(tctx: Maybe<TContext>, t: AST, peep: Type): (Type
6066
}
6167
);
6268
TAny{} => (ta, t);
69+
TVar{} => (ta, t);
6370
_ => (
6471
(_, t) = std-infer-expr(tctx, t, false, Used, TAny);
6572
(typeof(t), t);

SRC/std-destructure-macro.lsts

+9
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
2+
let std-destructure-macro(lhs: AST, rhs: AST): AContext? = (
3+
let no = None :: AContext?;
4+
match (lhs, rhs) {
5+
_ => fail("Unexpected std-destructure-macro\nLeft: \{lhs}\nRight: \{rhs}\n");
6+
};
7+
no
8+
);
9+

SRC/std-direct-destructure-macro.lsts

+8-1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,13 @@ let std-direct-destructure-macro(margs: AST, mstruct: AST): AContext? = (
33
let no = None :: AContext?;
44
match (margs, mstruct) {
55
Tuple{ val=first, second:Var{key=key} } => Some{[(key,val)]};
6-
_ => (fail("Unexpected Pattern std-direct-destructure-macro:\nargs: \{margs}\nlhs: \{mstruct}\n"); no);
6+
Tuple{
7+
first:App{is-cons:1_u8, lrest=left, val=right },
8+
second:App{is-cons:1_u8, rrest=left, right:Var{key=key} }
9+
} => (
10+
let ctx = std-direct-destructure-macro(lrest, rrest);
11+
if ctx.is-some then Some{cons((key,val), ctx.get-or-panic)} else no;
12+
);
13+
_ => fail("Unexpected std-direct-destructure-macro\nLeft: \{mstruct}\nRight: \{margs}\n");
714
}
815
);

SRC/substitute.lsts

+1-3
Original file line numberDiff line numberDiff line change
@@ -52,9 +52,7 @@ let substitute(ctx: AContext, term: AST): AST = (
5252
for vector s in seq { ret = ret.push(substitute(ctx,s)) };
5353
Seq{ret}
5454
);
55-
App{is-cons=is-cons,left=left,right=right} => if is-cons
56-
then mk-cons(substitute(ctx,left), substitute(ctx,right))
57-
else mk-app(substitute(ctx,left), substitute(ctx,right));
55+
App{is-cons=is-cons,left=left,right=right} => mk-cons-or-app(is-cons,substitute(ctx,left),substitute(ctx,right));
5856
Typedef{lhs=lhs,rhs=rhs} => mk-typedef(substitute(ctx,lhs), substitute(ctx,rhs));
5957
Abs{lhs=lhs,rhs=rhs,tt=tt} => mk-abs(substitute(ctx,lhs), substitute(ctx,rhs), tt);
6058
Glb{key=key,val=val} => mk-glb(key, substitute(ctx,val));

SRC/unit-orphans.lsts

+1
Original file line numberDiff line numberDiff line change
@@ -24,3 +24,4 @@ let .unroll-seq(t: AST): Vector<AST> = (
2424
_ => mk-vector(type(AST));
2525
}
2626
);
27+

SRC/with-location.lsts

+17
Original file line numberDiff line numberDiff line change
@@ -19,3 +19,20 @@ let with-location(term: AST, loc: SourceLocation): AST = (
1919
let with-location(t: Token, loc: SourceLocation): Token = (
2020
if non-zero(t.location) then t else Token{ t.skey, t.key, iuid(), loc }
2121
);
22+
23+
let with-location-preserve(term: AST, loc: SourceLocation): AST = (
24+
match term {
25+
Var{key=key,token=token} => Var{key,with-location(token,loc)};
26+
Lit{key=key,token=token} => Lit{key,with-location(token,loc)};
27+
App{is-cons=is-cons,left=left,right=right} => mk-cons-or-app(is-cons,with-location-preserve(left,loc),with-location-preserve(right,loc));
28+
Seq{seq=seq} => (
29+
let ret = mk-vector(type(AST), seq.length);
30+
for vector s in seq { ret = ret.push(with-location-preserve(s,loc)) };
31+
Seq{ret}
32+
);
33+
Abs{lhs=lhs,rhs=rhs,tt=tt} => Abs{close(with-location-preserve(lhs,loc)),close(with-location-preserve(rhs,loc)),tt};
34+
Typedef{lhs=lhs,rhs=rhs} => Typedef{close(with-location-preserve(lhs,loc)),close(with-location-preserve(rhs,loc))};
35+
Glb{key=key,val=val} => Glb{with-location(key,loc),close(with-location-preserve(val,loc))};
36+
_ => term;
37+
}
38+
);

tests/unit/ast-macros.lsts

+7
Original file line numberDiff line numberDiff line change
@@ -11,5 +11,12 @@ typed macro ast-macros-test-add(x: I64, y: lazy): lazy = (
1111
assert( ast-macros-test-add(1_u64, 2_u64) == 3_u64 );
1212
assert( ast-macros-test-add(2_i64, 3_i64) == 5_i64 );
1313

14+
(
15+
let x = mk-vector(type(U64)).push(1).push(2);
16+
$"macro::set"($"macro::lhs-index"(x,0), 3);
17+
$"macro::set"($"macro::lhs-index"(x,1), 4);
18+
print(x);
19+
);
20+
1421
#$"macro::for"(x, [1, 2], print(x));
1522
#$"macro::for"(x, mk-vector(type(U64)).push(3).push(4), print(x));

tests/unit/ast-macros.lsts.out

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
[3,4]

0 commit comments

Comments
 (0)