mirror of
https://github.com/ziglang/zig.git
synced 2026-02-21 16:54:52 +00:00
zig fmt: implement slices
This commit is contained in:
parent
33915cb1ed
commit
0929fcbc34
@ -688,6 +688,20 @@ pub const Tree = struct {
|
||||
return main_tokens[n] + end_offset;
|
||||
}
|
||||
},
|
||||
.SliceOpen => {
|
||||
end_offset += 2; // ellipsis2 and rbracket
|
||||
n = datas[n].rhs;
|
||||
},
|
||||
.Slice => {
|
||||
const extra = tree.extraData(datas[n].rhs, Node.Slice);
|
||||
if (extra.sentinel != 0) {
|
||||
n = extra.sentinel;
|
||||
} else {
|
||||
assert(extra.end != 0); // should have used SliceOpen if end and sentinel are 0
|
||||
n = extra.end;
|
||||
}
|
||||
end_offset += 1; // rbracket
|
||||
},
|
||||
|
||||
// These are not supported by lastToken() because implementation would
|
||||
// require recursion due to the optional comma followed by rbrace.
|
||||
@ -708,8 +722,6 @@ pub const Tree = struct {
|
||||
.ErrorSetDecl => unreachable, // TODO
|
||||
.AsmSimple => unreachable, // TODO
|
||||
.Asm => unreachable, // TODO
|
||||
.SliceOpen => unreachable, // TODO
|
||||
.Slice => unreachable, // TODO
|
||||
.SwitchCaseOne => unreachable, // TODO
|
||||
.SwitchRange => unreachable, // TODO
|
||||
.ArrayType => unreachable, // TODO
|
||||
@ -1094,6 +1106,35 @@ pub const Tree = struct {
|
||||
});
|
||||
}
|
||||
|
||||
pub fn sliceOpen(tree: Tree, node: Node.Index) Full.Slice {
|
||||
assert(tree.nodes.items(.tag)[node] == .SliceOpen);
|
||||
const data = tree.nodes.items(.data)[node];
|
||||
return .{
|
||||
.ast = .{
|
||||
.sliced = data.lhs,
|
||||
.lbracket = tree.nodes.items(.main_token)[node],
|
||||
.start = data.rhs,
|
||||
.end = 0,
|
||||
.sentinel = 0,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
pub fn slice(tree: Tree, node: Node.Index) Full.Slice {
|
||||
assert(tree.nodes.items(.tag)[node] == .Slice);
|
||||
const data = tree.nodes.items(.data)[node];
|
||||
const extra = tree.extraData(data.rhs, Node.Slice);
|
||||
return .{
|
||||
.ast = .{
|
||||
.sliced = data.lhs,
|
||||
.lbracket = tree.nodes.items(.main_token)[node],
|
||||
.start = extra.start,
|
||||
.end = extra.end,
|
||||
.sentinel = extra.sentinel,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
pub fn containerDeclTwo(tree: Tree, buffer: *[2]Node.Index, node: Node.Index) Full.ContainerDecl {
|
||||
assert(tree.nodes.items(.tag)[node] == .ContainerDeclTwo or
|
||||
tree.nodes.items(.tag)[node] == .ContainerDeclTwoComma);
|
||||
@ -1452,6 +1493,18 @@ pub const Full = struct {
|
||||
};
|
||||
};
|
||||
|
||||
pub const Slice = struct {
|
||||
ast: Ast,
|
||||
|
||||
pub const Ast = struct {
|
||||
sliced: Node.Index,
|
||||
lbracket: TokenIndex,
|
||||
start: Node.Index,
|
||||
end: Node.Index,
|
||||
sentinel: Node.Index,
|
||||
};
|
||||
};
|
||||
|
||||
pub const ContainerDecl = struct {
|
||||
layout_token: ?TokenIndex,
|
||||
ast: Ast,
|
||||
@ -1860,10 +1913,10 @@ pub const Node = struct {
|
||||
/// main_token is the asterisk if a pointer or the lbrace if a slice
|
||||
PtrTypeBitRange,
|
||||
/// `lhs[rhs..]`
|
||||
/// main_token is the `[`.
|
||||
/// main_token is the lbracket.
|
||||
SliceOpen,
|
||||
/// `lhs[b..c :d]`. `slice_list[rhs]`.
|
||||
/// main_token is the `[`.
|
||||
/// `lhs[b..c :d]`. rhs is index into Slice
|
||||
/// main_token is the lbracket.
|
||||
Slice,
|
||||
/// `lhs.*`. rhs is unused.
|
||||
Deref,
|
||||
|
||||
@ -637,6 +637,24 @@ test "zig fmt: sentinel array literal 1 element" {
|
||||
);
|
||||
}
|
||||
|
||||
test "zig fmt: slices" {
|
||||
try testCanonical(
|
||||
\\const a = b[0..];
|
||||
\\const c = d[0..1];
|
||||
\\const e = f[0..1 :0];
|
||||
\\
|
||||
);
|
||||
}
|
||||
|
||||
test "zig fmt: slices with spaces in bounds" {
|
||||
try testCanonical(
|
||||
\\const a = b[0 + 0 ..];
|
||||
\\const c = d[0 + 0 .. 1];
|
||||
\\const e = f[0 .. 1 + 1 :0];
|
||||
\\
|
||||
);
|
||||
}
|
||||
|
||||
//test "zig fmt: async function" {
|
||||
// try testCanonical(
|
||||
// \\pub const Server = struct {
|
||||
|
||||
@ -466,34 +466,8 @@ fn renderExpression(ais: *Ais, tree: ast.Tree, node: ast.Node.Index, space: Spac
|
||||
return renderToken(ais, tree, rbracket, space); // ]
|
||||
},
|
||||
|
||||
.Slice => unreachable, // TODO
|
||||
.SliceOpen => unreachable, // TODO
|
||||
//.Slice => {
|
||||
// const suffix_op = base.castTag(.Slice).?;
|
||||
// try renderExpression(ais, tree, suffix_op.lhs, Space.None);
|
||||
|
||||
// const lbracket = tree.prevToken(suffix_op.start.firstToken());
|
||||
// const dotdot = tree.nextToken(suffix_op.start.lastToken());
|
||||
|
||||
// const after_start_space_bool = nodeCausesSliceOpSpace(suffix_op.start) or
|
||||
// (if (suffix_op.end) |end| nodeCausesSliceOpSpace(end) else false);
|
||||
// const after_start_space = if (after_start_space_bool) Space.Space else Space.None;
|
||||
// const after_op_space = if (suffix_op.end != null) after_start_space else Space.None;
|
||||
|
||||
// try renderToken(ais, tree, lbracket, Space.None); // [
|
||||
// try renderExpression(ais, tree, suffix_op.start, after_start_space);
|
||||
// try renderToken(ais, tree, dotdot, after_op_space); // ..
|
||||
// if (suffix_op.end) |end| {
|
||||
// const after_end_space = if (suffix_op.sentinel != null) Space.Space else Space.None;
|
||||
// try renderExpression(ais, tree, end, after_end_space);
|
||||
// }
|
||||
// if (suffix_op.sentinel) |sentinel| {
|
||||
// const colon = tree.prevToken(sentinel.firstToken());
|
||||
// try renderToken(ais, tree, colon, Space.None); // :
|
||||
// try renderExpression(ais, tree, sentinel, Space.None);
|
||||
// }
|
||||
// return renderToken(ais, tree, suffix_op.rtoken, space); // ]
|
||||
//},
|
||||
.SliceOpen => try renderSlice(ais, tree, tree.sliceOpen(node), space),
|
||||
.Slice => try renderSlice(ais, tree, tree.slice(node), space),
|
||||
|
||||
.Deref => {
|
||||
try renderExpression(ais, tree, datas[node].lhs, .None);
|
||||
@ -1142,6 +1116,40 @@ fn renderPtrType(
|
||||
try renderExpression(ais, tree, ptr_type.ast.child_type, space);
|
||||
}
|
||||
|
||||
fn renderSlice(
|
||||
ais: *Ais,
|
||||
tree: ast.Tree,
|
||||
slice: ast.Full.Slice,
|
||||
space: Space,
|
||||
) Error!void {
|
||||
const node_tags = tree.nodes.items(.tag);
|
||||
const after_start_space_bool = nodeCausesSliceOpSpace(node_tags[slice.ast.start]) or
|
||||
if (slice.ast.end != 0) nodeCausesSliceOpSpace(node_tags[slice.ast.end]) else false;
|
||||
const after_start_space = if (after_start_space_bool) Space.Space else Space.None;
|
||||
const after_dots_space = if (slice.ast.end != 0) after_start_space else Space.None;
|
||||
|
||||
try renderExpression(ais, tree, slice.ast.sliced, .None);
|
||||
try renderToken(ais, tree, slice.ast.lbracket, .None); // lbracket
|
||||
|
||||
const start_last = tree.lastToken(slice.ast.start);
|
||||
try renderExpression(ais, tree, slice.ast.start, after_start_space);
|
||||
try renderToken(ais, tree, start_last + 1, after_dots_space); // ellipsis2 ("..")
|
||||
if (slice.ast.end == 0) {
|
||||
return renderToken(ais, tree, start_last + 2, space); // rbracket
|
||||
}
|
||||
|
||||
const end_last = tree.lastToken(slice.ast.end);
|
||||
const after_end_space = if (slice.ast.sentinel != 0) Space.Space else Space.None;
|
||||
try renderExpression(ais, tree, slice.ast.end, after_end_space);
|
||||
if (slice.ast.sentinel == 0) {
|
||||
return renderToken(ais, tree, end_last + 1, space); // rbracket
|
||||
}
|
||||
|
||||
try renderToken(ais, tree, end_last + 1, .None); // colon
|
||||
try renderExpression(ais, tree, slice.ast.sentinel, .None);
|
||||
try renderToken(ais, tree, tree.lastToken(slice.ast.sentinel) + 1, space); // rbracket
|
||||
}
|
||||
|
||||
fn renderAsmOutput(
|
||||
allocator: *mem.Allocator,
|
||||
ais: *Ais,
|
||||
@ -2099,8 +2107,8 @@ fn nodeIsBlock(tag: ast.Node.Tag) bool {
|
||||
};
|
||||
}
|
||||
|
||||
fn nodeCausesSliceOpSpace(base: ast.Node.Index) bool {
|
||||
return switch (base.tag) {
|
||||
fn nodeCausesSliceOpSpace(tag: ast.Node.Tag) bool {
|
||||
return switch (tag) {
|
||||
.Catch,
|
||||
.Add,
|
||||
.AddWrap,
|
||||
@ -2139,7 +2147,6 @@ fn nodeCausesSliceOpSpace(base: ast.Node.Index) bool {
|
||||
.Mod,
|
||||
.Mul,
|
||||
.MulWrap,
|
||||
.Range,
|
||||
.Sub,
|
||||
.SubWrap,
|
||||
.OrElse,
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user