add function calls
This commit is contained in:
parent
4f0c43865f
commit
5ba807d93f
3 changed files with 74 additions and 1 deletions
|
@ -30,4 +30,6 @@ fn main(a int) int {
|
||||||
loop a > 2 {
|
loop a > 2 {
|
||||||
println('skirts')
|
println('skirts')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cock_and_ball_torture('cbt', 1, 2, 3)
|
||||||
}
|
}
|
||||||
|
|
20
src/ast.zig
20
src/ast.zig
|
@ -76,6 +76,7 @@ pub const ExprType = enum {
|
||||||
Logical,
|
Logical,
|
||||||
Literal,
|
Literal,
|
||||||
Variable,
|
Variable,
|
||||||
|
Call,
|
||||||
Grouping,
|
Grouping,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -84,6 +85,12 @@ pub const VarDecl = struct {
|
||||||
mutable: bool = false,
|
mutable: bool = false,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
pub const CallExpr = struct {
|
||||||
|
callee: *Expr,
|
||||||
|
paren: Token,
|
||||||
|
arguments: ExprList,
|
||||||
|
};
|
||||||
|
|
||||||
pub const Expr = union(ExprType) {
|
pub const Expr = union(ExprType) {
|
||||||
Assign: AssignExpr,
|
Assign: AssignExpr,
|
||||||
VarDecl: VarDecl,
|
VarDecl: VarDecl,
|
||||||
|
@ -95,6 +102,7 @@ pub const Expr = union(ExprType) {
|
||||||
|
|
||||||
Variable: Token,
|
Variable: Token,
|
||||||
Grouping: *Expr,
|
Grouping: *Expr,
|
||||||
|
Call: CallExpr,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const Block = std.ArrayList(*Stmt);
|
pub const Block = std.ArrayList(*Stmt);
|
||||||
|
@ -305,6 +313,18 @@ pub fn printExpr(expr: *Expr) void {
|
||||||
std.debug.warn(")");
|
std.debug.warn(")");
|
||||||
},
|
},
|
||||||
|
|
||||||
|
.Call => |call| {
|
||||||
|
std.debug.warn("(");
|
||||||
|
printExpr(call.callee);
|
||||||
|
|
||||||
|
for (call.arguments.toSlice()) |arg| {
|
||||||
|
std.debug.warn(" ");
|
||||||
|
printExpr(arg);
|
||||||
|
}
|
||||||
|
|
||||||
|
std.debug.warn(")");
|
||||||
|
},
|
||||||
|
|
||||||
else => std.debug.warn("UnknownExpr-{}", @tagName(expr.*)),
|
else => std.debug.warn("UnknownExpr-{}", @tagName(expr.*)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -241,6 +241,19 @@ pub const Parser = struct {
|
||||||
return vardecl;
|
return vardecl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn mkCall(self: *@This(), callee: *Expr, paren: Token, args: ast.ExprList) !*Expr {
|
||||||
|
var expr = try self.allocator.create(Expr);
|
||||||
|
expr.* = Expr{
|
||||||
|
.Call = ast.CallExpr{
|
||||||
|
.callee = callee,
|
||||||
|
.paren = paren,
|
||||||
|
.arguments = args,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
return expr;
|
||||||
|
}
|
||||||
|
|
||||||
fn mkBool(self: *Parser, val: bool) !*ast.Expr {
|
fn mkBool(self: *Parser, val: bool) !*ast.Expr {
|
||||||
var expr = try self.allocator.create(Expr);
|
var expr = try self.allocator.create(Expr);
|
||||||
expr.* = Expr{
|
expr.* = Expr{
|
||||||
|
@ -676,10 +689,48 @@ pub const Parser = struct {
|
||||||
return try self.mkUnary(op, right);
|
return try self.mkUnary(op, right);
|
||||||
}
|
}
|
||||||
|
|
||||||
var expr = try self.parsePrimary();
|
var expr = try self.parseCall();
|
||||||
return expr;
|
return expr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn parseCall(self: *@This()) !*Expr {
|
||||||
|
var expr = try self.parsePrimary();
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
if (self.check(.LeftParen)) {
|
||||||
|
_ = try self.consumeSingle(.LeftParen);
|
||||||
|
expr = try self.finishCall(expr);
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return expr;
|
||||||
|
}
|
||||||
|
|
||||||
|
fn finishCall(self: *@This(), callee: *Expr) !*Expr {
|
||||||
|
var args = ast.ExprList.init(self.allocator);
|
||||||
|
errdefer args.deinit();
|
||||||
|
|
||||||
|
if (!self.check(.RightParen)) {
|
||||||
|
|
||||||
|
// emulating do-while really badly
|
||||||
|
var arg = (try self.parseExpr()).Expr;
|
||||||
|
try args.append(arg);
|
||||||
|
|
||||||
|
while (self.check(.Comma)) {
|
||||||
|
_ = try self.consumeSingle(.Comma);
|
||||||
|
|
||||||
|
arg = (try self.parseExpr()).Expr;
|
||||||
|
try args.append(arg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var paren = try self.consume(.RightParen, "Expected ')' after arguments");
|
||||||
|
|
||||||
|
return self.mkCall(callee, paren, args);
|
||||||
|
}
|
||||||
|
|
||||||
fn parsePrimary(self: *@This()) !*Expr {
|
fn parsePrimary(self: *@This()) !*Expr {
|
||||||
const curtype = self.peek().ttype;
|
const curtype = self.peek().ttype;
|
||||||
const lexeme = self.peek().lexeme;
|
const lexeme = self.peek().lexeme;
|
||||||
|
|
Loading…
Reference in a new issue