std.zig.parser now parses toplevel use
parent
db0812d4b7
commit
3b80e66507
|
@ -11,6 +11,7 @@ pub const Node = struct {
|
||||||
pub const Id = enum {
|
pub const Id = enum {
|
||||||
Root,
|
Root,
|
||||||
VarDecl,
|
VarDecl,
|
||||||
|
Use,
|
||||||
ErrorSetDecl,
|
ErrorSetDecl,
|
||||||
ContainerDecl,
|
ContainerDecl,
|
||||||
StructField,
|
StructField,
|
||||||
|
@ -63,6 +64,7 @@ pub const Node = struct {
|
||||||
return switch (base.id) {
|
return switch (base.id) {
|
||||||
Id.Root => @fieldParentPtr(NodeRoot, "base", base).iterate(index),
|
Id.Root => @fieldParentPtr(NodeRoot, "base", base).iterate(index),
|
||||||
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).iterate(index),
|
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).iterate(index),
|
||||||
|
Id.Use => @fieldParentPtr(NodeUse, "base", base).iterate(index),
|
||||||
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).iterate(index),
|
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).iterate(index),
|
||||||
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).iterate(index),
|
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).iterate(index),
|
||||||
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).iterate(index),
|
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).iterate(index),
|
||||||
|
@ -116,6 +118,7 @@ pub const Node = struct {
|
||||||
return switch (base.id) {
|
return switch (base.id) {
|
||||||
Id.Root => @fieldParentPtr(NodeRoot, "base", base).firstToken(),
|
Id.Root => @fieldParentPtr(NodeRoot, "base", base).firstToken(),
|
||||||
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).firstToken(),
|
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).firstToken(),
|
||||||
|
Id.Use => @fieldParentPtr(NodeUse, "base", base).firstToken(),
|
||||||
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).firstToken(),
|
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).firstToken(),
|
||||||
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).firstToken(),
|
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).firstToken(),
|
||||||
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).firstToken(),
|
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).firstToken(),
|
||||||
|
@ -169,6 +172,7 @@ pub const Node = struct {
|
||||||
return switch (base.id) {
|
return switch (base.id) {
|
||||||
Id.Root => @fieldParentPtr(NodeRoot, "base", base).lastToken(),
|
Id.Root => @fieldParentPtr(NodeRoot, "base", base).lastToken(),
|
||||||
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).lastToken(),
|
Id.VarDecl => @fieldParentPtr(NodeVarDecl, "base", base).lastToken(),
|
||||||
|
Id.Use => @fieldParentPtr(NodeUse, "base", base).lastToken(),
|
||||||
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).lastToken(),
|
Id.ErrorSetDecl => @fieldParentPtr(NodeErrorSetDecl, "base", base).lastToken(),
|
||||||
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).lastToken(),
|
Id.ContainerDecl => @fieldParentPtr(NodeContainerDecl, "base", base).lastToken(),
|
||||||
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).lastToken(),
|
Id.StructField => @fieldParentPtr(NodeStructField, "base", base).lastToken(),
|
||||||
|
@ -288,6 +292,31 @@ pub const NodeVarDecl = struct {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
pub const NodeUse = struct {
|
||||||
|
base: Node,
|
||||||
|
visib_token: ?Token,
|
||||||
|
expr: &Node,
|
||||||
|
semicolon_token: Token,
|
||||||
|
|
||||||
|
pub fn iterate(self: &NodeUse, index: usize) ?&Node {
|
||||||
|
var i = index;
|
||||||
|
|
||||||
|
if (i < 1) return self.expr;
|
||||||
|
i -= 1;
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn firstToken(self: &NodeUse) Token {
|
||||||
|
if (self.visib_token) |visib_token| return visib_token;
|
||||||
|
return self.expr.firstToken();
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn lastToken(self: &NodeUse) Token {
|
||||||
|
return self.semicolon_token;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
pub const NodeErrorSetDecl = struct {
|
pub const NodeErrorSetDecl = struct {
|
||||||
base: Node,
|
base: Node,
|
||||||
error_token: Token,
|
error_token: Token,
|
||||||
|
|
|
@ -348,31 +348,54 @@ pub const Parser = struct {
|
||||||
},
|
},
|
||||||
State.TopLevelExtern => |ctx| {
|
State.TopLevelExtern => |ctx| {
|
||||||
const token = self.getNextToken();
|
const token = self.getNextToken();
|
||||||
if (token.id == Token.Id.Keyword_extern) {
|
switch (token.id) {
|
||||||
const lib_name_token = self.getNextToken();
|
Token.Id.Keyword_use => {
|
||||||
const lib_name = blk: {
|
const node = try arena.create(ast.NodeUse);
|
||||||
if (lib_name_token.id == Token.Id.StringLiteral) {
|
*node = ast.NodeUse {
|
||||||
const res = try self.createStringLiteral(arena, lib_name_token);
|
.base = self.initNode(ast.Node.Id.Use),
|
||||||
break :blk &res.base;
|
|
||||||
} else {
|
|
||||||
self.putBackToken(lib_name_token);
|
|
||||||
break :blk null;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
stack.append(State {
|
|
||||||
.TopLevelDecl = TopLevelDeclCtx {
|
|
||||||
.decls = ctx.decls,
|
|
||||||
.visib_token = ctx.visib_token,
|
.visib_token = ctx.visib_token,
|
||||||
.extern_token = token,
|
.expr = undefined,
|
||||||
.lib_name = lib_name,
|
.semicolon_token = undefined,
|
||||||
},
|
};
|
||||||
}) catch unreachable;
|
try ctx.decls.append(&node.base);
|
||||||
continue;
|
|
||||||
|
stack.append(State {
|
||||||
|
.ExpectTokenSave = ExpectTokenSave {
|
||||||
|
.id = Token.Id.Semicolon,
|
||||||
|
.ptr = &node.semicolon_token,
|
||||||
|
}
|
||||||
|
}) catch unreachable;
|
||||||
|
try stack.append(State { .Expression = DestPtr { .Field = &node.expr } });
|
||||||
|
continue;
|
||||||
|
},
|
||||||
|
Token.Id.Keyword_extern => {
|
||||||
|
const lib_name_token = self.getNextToken();
|
||||||
|
const lib_name = blk: {
|
||||||
|
if (lib_name_token.id == Token.Id.StringLiteral) {
|
||||||
|
const res = try self.createStringLiteral(arena, lib_name_token);
|
||||||
|
break :blk &res.base;
|
||||||
|
} else {
|
||||||
|
self.putBackToken(lib_name_token);
|
||||||
|
break :blk null;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
stack.append(State {
|
||||||
|
.TopLevelDecl = TopLevelDeclCtx {
|
||||||
|
.decls = ctx.decls,
|
||||||
|
.visib_token = ctx.visib_token,
|
||||||
|
.extern_token = token,
|
||||||
|
.lib_name = lib_name,
|
||||||
|
},
|
||||||
|
}) catch unreachable;
|
||||||
|
continue;
|
||||||
|
},
|
||||||
|
else => {
|
||||||
|
self.putBackToken(token);
|
||||||
|
stack.append(State { .TopLevelDecl = ctx }) catch unreachable;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
self.putBackToken(token);
|
|
||||||
stack.append(State { .TopLevelDecl = ctx }) catch unreachable;
|
|
||||||
continue;
|
|
||||||
},
|
},
|
||||||
State.TopLevelDecl => |ctx| {
|
State.TopLevelDecl => |ctx| {
|
||||||
const token = self.getNextToken();
|
const token = self.getNextToken();
|
||||||
|
@ -3068,6 +3091,15 @@ pub const Parser = struct {
|
||||||
|
|
||||||
try stack.append(RenderState { .Expression = decl });
|
try stack.append(RenderState { .Expression = decl });
|
||||||
},
|
},
|
||||||
|
ast.Node.Id.Use => {
|
||||||
|
const use_decl = @fieldParentPtr(ast.NodeUse, "base", decl);
|
||||||
|
if (use_decl.visib_token) |visib_token| {
|
||||||
|
try stream.print("{} ", self.tokenizer.getTokenSlice(visib_token));
|
||||||
|
}
|
||||||
|
try stream.print("use ");
|
||||||
|
try stack.append(RenderState { .Text = ";" });
|
||||||
|
try stack.append(RenderState { .Expression = use_decl.expr });
|
||||||
|
},
|
||||||
ast.Node.Id.VarDecl => {
|
ast.Node.Id.VarDecl => {
|
||||||
const var_decl = @fieldParentPtr(ast.NodeVarDecl, "base", decl);
|
const var_decl = @fieldParentPtr(ast.NodeVarDecl, "base", decl);
|
||||||
try stack.append(RenderState { .VarDecl = var_decl});
|
try stack.append(RenderState { .VarDecl = var_decl});
|
||||||
|
@ -4086,6 +4118,7 @@ pub const Parser = struct {
|
||||||
ast.Node.Id.EnumTag,
|
ast.Node.Id.EnumTag,
|
||||||
ast.Node.Id.Root,
|
ast.Node.Id.Root,
|
||||||
ast.Node.Id.VarDecl,
|
ast.Node.Id.VarDecl,
|
||||||
|
ast.Node.Id.Use,
|
||||||
ast.Node.Id.TestDecl,
|
ast.Node.Id.TestDecl,
|
||||||
ast.Node.Id.ParamDecl => unreachable,
|
ast.Node.Id.ParamDecl => unreachable,
|
||||||
},
|
},
|
||||||
|
@ -5000,3 +5033,11 @@ test "zig fmt: Block after if" {
|
||||||
\\
|
\\
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test "zig fmt: use" {
|
||||||
|
try testCanonical(
|
||||||
|
\\use @import("std");
|
||||||
|
\\pub use @import("std");
|
||||||
|
\\
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue