mirror of
https://github.com/Noratrieb/riverdelta.git
synced 2026-01-16 09:25:03 +01:00
lower blocks
This commit is contained in:
parent
7c2faaecb8
commit
162d71c8b8
2 changed files with 48 additions and 13 deletions
14
src/index.ts
14
src/index.ts
|
|
@ -10,13 +10,15 @@ import fs from "fs";
|
||||||
import { exec } from "child_process";
|
import { exec } from "child_process";
|
||||||
|
|
||||||
const input = `
|
const input = `
|
||||||
function printInt(a: Int) = ;
|
function printInt(a: Int) = (
|
||||||
|
0;
|
||||||
function main() = (
|
(
|
||||||
let a = 0;
|
0;
|
||||||
let b = 0;
|
1
|
||||||
printInt(a + b);
|
);
|
||||||
);
|
);
|
||||||
|
|
||||||
|
function main() = ;
|
||||||
`;
|
`;
|
||||||
|
|
||||||
function main() {
|
function main() {
|
||||||
|
|
|
||||||
47
src/lower.ts
47
src/lower.ts
|
|
@ -1,4 +1,4 @@
|
||||||
import { Ast, Expr, FunctionDef, Item, Ty, TyFn, varUnreachable } from "./ast";
|
import { Ast, Expr, ExprBlock, FunctionDef, Item, Ty, TyFn, varUnreachable } from "./ast";
|
||||||
import * as wasm from "./wasm/defs";
|
import * as wasm from "./wasm/defs";
|
||||||
|
|
||||||
type StringifiedForMap<T> = string;
|
type StringifiedForMap<T> = string;
|
||||||
|
|
@ -111,6 +111,7 @@ Expression lowering.
|
||||||
function lowerExpr(fcx: FuncContext, instrs: wasm.Instr[], expr: Expr) {
|
function lowerExpr(fcx: FuncContext, instrs: wasm.Instr[], expr: Expr) {
|
||||||
const ty = expr.ty!;
|
const ty = expr.ty!;
|
||||||
|
|
||||||
|
|
||||||
switch (expr.kind) {
|
switch (expr.kind) {
|
||||||
case "empty":
|
case "empty":
|
||||||
// A ZST, do nothing.
|
// A ZST, do nothing.
|
||||||
|
|
@ -119,10 +120,23 @@ function lowerExpr(fcx: FuncContext, instrs: wasm.Instr[], expr: Expr) {
|
||||||
// Let, that's complicated.
|
// Let, that's complicated.
|
||||||
todo("let");
|
todo("let");
|
||||||
case "block":
|
case "block":
|
||||||
if (expr.exprs.length === 1) {
|
if (expr.exprs.length === 0) {
|
||||||
|
// do nothing
|
||||||
|
} else if (expr.exprs.length === 1) {
|
||||||
lowerExpr(fcx, instrs, expr.exprs[0]);
|
lowerExpr(fcx, instrs, expr.exprs[0]);
|
||||||
} else {
|
} else {
|
||||||
todo("complex blocks");
|
const typeIdx = internFuncType(fcx.cx, {
|
||||||
|
params: [],
|
||||||
|
returns: wasmTypeForBody(expr.ty!),
|
||||||
|
});
|
||||||
|
|
||||||
|
const instr: wasm.Instr = {
|
||||||
|
kind: "block",
|
||||||
|
instrs: lowerExprBlockBody(fcx, expr),
|
||||||
|
type: { kind: "typeidx", idx: typeIdx },
|
||||||
|
};
|
||||||
|
|
||||||
|
instrs.push(instr);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case "literal":
|
case "literal":
|
||||||
|
|
@ -266,6 +280,23 @@ function lowerExpr(fcx: FuncContext, instrs: wasm.Instr[], expr: Expr) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function lowerExprBlockBody(fcx: FuncContext, expr: ExprBlock & Expr): wasm.Instr[] {
|
||||||
|
const innerInstrs: wasm.Instr[] = [];
|
||||||
|
|
||||||
|
const headExprs = expr.exprs.slice(0, -1);
|
||||||
|
const tailExpr = expr.exprs[expr.exprs.length - 1];
|
||||||
|
|
||||||
|
headExprs.forEach((inner) => {
|
||||||
|
lowerExpr(fcx, innerInstrs, inner);
|
||||||
|
const types = wasmTypeForBody(inner.ty!);
|
||||||
|
types.forEach(() => innerInstrs.push({ kind: "drop" }));
|
||||||
|
});
|
||||||
|
|
||||||
|
lowerExpr(fcx, innerInstrs, tailExpr);
|
||||||
|
|
||||||
|
return innerInstrs;
|
||||||
|
}
|
||||||
|
|
||||||
function loadVariable(instrs: wasm.Instr[], loc: VarLocation) {
|
function loadVariable(instrs: wasm.Instr[], loc: VarLocation) {
|
||||||
switch (loc.kind) {
|
switch (loc.kind) {
|
||||||
case "local": {
|
case "local": {
|
||||||
|
|
@ -376,25 +407,27 @@ function wasmTypeForAbi(abi: Abi): {
|
||||||
return { type: { params, returns }, paramLocations };
|
return { type: { params, returns }, paramLocations };
|
||||||
}
|
}
|
||||||
|
|
||||||
function wasmTypeForBody(ty: Ty): wasm.ValType | undefined {
|
function wasmTypeForBody(ty: Ty): wasm.ValType[] {
|
||||||
switch (ty.kind) {
|
switch (ty.kind) {
|
||||||
case "string":
|
case "string":
|
||||||
todo("string types");
|
todo("string types");
|
||||||
case "int":
|
case "int":
|
||||||
return "i64";
|
return ["i64"];
|
||||||
case "bool":
|
case "bool":
|
||||||
return "i32";
|
return ["i32"];
|
||||||
case "list":
|
case "list":
|
||||||
todo("list types");
|
todo("list types");
|
||||||
case "tuple":
|
case "tuple":
|
||||||
if (ty.elems.length === 0) {
|
if (ty.elems.length === 0) {
|
||||||
return undefined;
|
return [];
|
||||||
} else if (ty.elems.length === 1) {
|
} else if (ty.elems.length === 1) {
|
||||||
return wasmTypeForBody(ty.elems[0]);
|
return wasmTypeForBody(ty.elems[0]);
|
||||||
}
|
}
|
||||||
todo("complex tuples");
|
todo("complex tuples");
|
||||||
case "fn":
|
case "fn":
|
||||||
todo("fn types");
|
todo("fn types");
|
||||||
|
case "struct":
|
||||||
|
todo("struct types");
|
||||||
case "var":
|
case "var":
|
||||||
varUnreachable();
|
varUnreachable();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue