Commit dbd60e3d29
Changed files (3)
lib
src
lib/docs/index.html
@@ -711,7 +711,11 @@
<h2>Examples</h2>
<ul id="listFnExamples" class="examples"></ul>
</div>
- <div id="sectTests" class="hidden">
+ <div id="sectDocTests" class="hidden">
+ <h2>DocTests</h2>
+ <pre id="docTestsCode"></pre>
+ </div>
+ <div id="sectTests" class="hidden">
<h2>Tests</h2>
<div class="table-container">
<table>
lib/docs/main.js
@@ -13,6 +13,8 @@ var zigAnalysis;
const domListTypes = document.getElementById("listTypes");
const domSectTests = document.getElementById("sectTests");
const domListTests = document.getElementById("listTests");
+ const domSectDocTests = document.getElementById("sectDocTests");
+ const domDocTestsCode = document.getElementById("docTestsCode");
const domSectNamespaces = document.getElementById("sectNamespaces");
const domListNamespaces = document.getElementById("listNamespaces");
const domSectErrSets = document.getElementById("sectErrSets");
@@ -384,6 +386,7 @@ var zigAnalysis;
domSectPkgs.classList.add("hidden");
domSectTypes.classList.add("hidden");
domSectTests.classList.add("hidden");
+ domSectDocTests.classList.add("hidden");
domSectNamespaces.classList.add("hidden");
domSectErrSets.classList.add("hidden");
domSectFns.classList.add("hidden");
@@ -452,6 +455,10 @@ var zigAnalysis;
let lastIsDecl = isDecl(last);
let lastIsType = isType(last);
let lastIsContainerType = isContainerType(last);
+
+ if (lastIsDecl){
+ renderDocTest(last);
+ }
if (lastIsContainerType) {
return renderContainer(last);
@@ -477,6 +484,14 @@ var zigAnalysis;
return renderValue(last);
}
+
+ }
+
+ function renderDocTest(decl) {
+ if (!("decltest" in decl)) return;
+ const astNode = zigAnalysis.astNodes[decl.decltest];
+ domSectDocTests.classList.remove("hidden");
+ domDocTestsCode.innerHTML = astNode.code;
}
function renderUnknownDecl(decl) {
src/Autodoc.zig
@@ -58,7 +58,7 @@ const RefPathResumeInfo = struct {
const SrcLocInfo = struct {
bytes: u32 = 0,
line: usize = 0,
- src_node: i32 = 0,
+ src_node: u32 = 0,
};
var arena_allocator: std.heap.ArenaAllocator = undefined;
@@ -481,6 +481,7 @@ const DocData = struct {
line: usize = 0,
col: usize = 0,
name: ?[]const u8 = null,
+ code: ?[]const u8 = null,
docs: ?[]const u8 = null,
fields: ?[]usize = null, // index into astNodes
@"comptime": bool = false,
@@ -2441,7 +2442,10 @@ fn walkInstruction(
break :blk src_node;
} else null;
- const src_info = try self.srcLocInfo(file, src_node, parent_src);
+ const src_info = if (src_node) |sn|
+ try self.srcLocInfo(file, sn, parent_src)
+ else
+ parent_src;
_ = src_info;
const decls_len = if (small.has_decls_len) blk: {
@@ -2500,7 +2504,10 @@ fn walkInstruction(
break :blk src_node;
} else null;
- const src_info = try self.srcLocInfo(file, src_node, parent_src);
+ const src_info = if (src_node) |sn|
+ try self.srcLocInfo(file, sn, parent_src)
+ else
+ parent_src;
const tag_type: ?Ref = if (small.has_tag_type) blk: {
const tag_type = file.zir.extra[extra_index];
@@ -2623,7 +2630,10 @@ fn walkInstruction(
break :blk src_node;
} else null;
- const src_info = try self.srcLocInfo(file, src_node, parent_src);
+ const src_info = if (src_node) |sn|
+ try self.srcLocInfo(file, sn, parent_src)
+ else
+ parent_src;
const tag_type: ?Ref = if (small.has_tag_type) blk: {
const tag_type = file.zir.extra[extra_index];
@@ -2770,7 +2780,10 @@ fn walkInstruction(
break :blk src_node;
} else null;
- const src_info = try self.srcLocInfo(file, src_node, parent_src);
+ const src_info = if (src_node) |sn|
+ try self.srcLocInfo(file, sn, parent_src)
+ else
+ parent_src;
const fields_len = if (small.has_fields_len) blk: {
const fields_len = file.zir.extra[extra_index];
@@ -2911,6 +2924,7 @@ fn walkDecls(
priv_decl_indexes: *std.ArrayListUnmanaged(usize),
extra_start: usize,
) AutodocErrors!usize {
+ const data = file.zir.instructions.items(.data);
const bit_bags_count = std.math.divCeil(usize, decls_len, 8) catch unreachable;
var extra_index = extra_start + bit_bags_count;
var bit_bag_index: usize = extra_start;
@@ -2938,7 +2952,7 @@ fn walkDecls(
// const hash_u32s = file.zir.extra[extra_index..][0..4];
extra_index += 4;
- //const line = file.zir.extra[extra_index];
+ // const line = file.zir.extra[extra_index];
extra_index += 1;
const decl_name_index = file.zir.extra[extra_index];
extra_index += 1;
@@ -2968,10 +2982,11 @@ fn walkDecls(
};
_ = addrspace_inst;
- // const pub_str = if (is_pub) "pub " else "";
- // const hash_bytes = @bitCast([16]u8, hash_u32s.*);
+ // This is known to work because decl values are always block_inlines
+ const value_pl_node = data[value_index].pl_node;
+ const decl_src = try self.srcLocInfo(file, value_pl_node.src_node, parent_src);
- var is_test = false; // we discover if it's a test by lookin at its name
+ var is_test = false; // we discover if it's a test by looking at its name
const name: []const u8 = blk: {
if (decl_name_index == 0) {
break :blk if (is_exported) "usingnamespace" else "comptime";
@@ -2979,84 +2994,32 @@ fn walkDecls(
is_test = true;
break :blk "test";
} else if (decl_name_index == 2) {
- is_test = true;
- // TODO: remove temporary hack
- break :blk "test";
- // // it is a decltest
- // const decl_being_tested = scope.resolveDeclName(doc_comment_index);
- // const ast_node_index = idx: {
- // const idx = self.ast_nodes.items.len;
- // const file_source = file.getSource(self.module.gpa) catch unreachable; // TODO fix this
- // const source_of_decltest_function = srcloc: {
- // const func_index = getBlockInlineBreak(file.zir, value_index);
- // // a decltest is always a function
- // const tag = file.zir.instructions.items(.tag)[Zir.refToIndex(func_index).?];
- // std.debug.assert(tag == .func_extended);
-
- // const pl_node = file.zir.instructions.items(.data)[Zir.refToIndex(func_index).?].pl_node;
- // const extra = file.zir.extraData(Zir.Inst.ExtendedFunc, pl_node.payload_index);
- // const bits = @bitCast(Zir.Inst.ExtendedFunc.Bits, extra.data.bits);
-
- // var extra_index_for_this_func: usize = extra.end;
- // if (bits.has_lib_name) extra_index_for_this_func += 1;
- // if (bits.has_cc) extra_index_for_this_func += 1;
- // if (bits.has_align) extra_index_for_this_func += 1;
-
- // const ret_ty_body = file.zir.extra[extra_index_for_this_func..][0..extra.data.ret_body_len];
- // extra_index_for_this_func += ret_ty_body.len;
-
- // const body = file.zir.extra[extra_index_for_this_func..][0..extra.data.body_len];
- // extra_index_for_this_func += body.len;
-
- // var src_locs: Zir.Inst.Func.SrcLocs = undefined;
- // if (body.len != 0) {
- // src_locs = file.zir.extraData(Zir.Inst.Func.SrcLocs, extra_index_for_this_func).data;
- // } else {
- // src_locs = .{
- // .lbrace_line = line,
- // .rbrace_line = line,
- // .columns = 0, // TODO get columns when body.len == 0
- // };
- // }
- // break :srcloc src_locs;
- // };
- // const source_slice = slice: {
- // var start_byte_offset: u32 = 0;
- // var end_byte_offset: u32 = 0;
- // const rbrace_col = @truncate(u16, source_of_decltest_function.columns >> 16);
- // var lines: u32 = 0;
- // for (file_source.bytes) |b, i| {
- // if (b == '\n') {
- // lines += 1;
- // }
- // if (lines == source_of_decltest_function.lbrace_line) {
- // start_byte_offset = @intCast(u32, i);
- // }
- // if (lines == source_of_decltest_function.rbrace_line) {
- // end_byte_offset = @intCast(u32, i) + rbrace_col;
- // break;
- // }
- // }
- // break :slice file_source.bytes[start_byte_offset..end_byte_offset];
- // };
- // try self.ast_nodes.append(self.arena, .{
- // .file = 0,
- // .line = line,
- // .col = 0,
- // .name = try self.arena.dupe(u8, source_slice),
- // });
- // break :idx idx;
- // };
- // self.decls.items[decl_being_tested].decltest = ast_node_index;
- // self.decls.items[decls_slot_index] = .{
- // ._analyzed = true,
- // .name = "test",
- // .isTest = true,
- // .src = ast_node_index,
- // .value = .{ .expr = .{ .type = 0 } },
- // .kind = "const",
- // };
- // continue;
+ // it is a decltest
+ const decl_being_tested = scope.resolveDeclName(doc_comment_index);
+ const func_index = getBlockInlineBreak(file.zir, value_index);
+
+ const pl_node = data[Zir.refToIndex(func_index).?].pl_node;
+ const fn_src = try self.srcLocInfo(file, pl_node.src_node, decl_src);
+ const tree = try file.getTree(self.module.gpa);
+ const test_source_code = tree.getNodeSource(fn_src.src_node);
+
+ const ast_node_index = self.ast_nodes.items.len;
+ try self.ast_nodes.append(self.arena, .{
+ .file = 0,
+ .line = 0,
+ .col = 0,
+ .code = test_source_code,
+ });
+ self.decls.items[decl_being_tested].decltest = ast_node_index;
+ self.decls.items[decls_slot_index] = .{
+ ._analyzed = true,
+ .name = "test",
+ .isTest = true,
+ .src = ast_node_index,
+ .value = .{ .expr = .{ .type = 0 } },
+ .kind = "const",
+ };
+ continue;
} else {
const raw_decl_name = file.zir.nullTerminatedString(decl_name_index);
if (raw_decl_name.len == 0) {
@@ -3073,11 +3036,6 @@ fn walkDecls(
else
null;
- // This is known to work because decl values are always block_inlines
- const data = file.zir.instructions.items(.data);
- const value_pl_node = data[value_index].pl_node;
- const decl_src = try self.srcLocInfo(file, value_pl_node.src_node, parent_src);
-
// astnode
const ast_node_index = idx: {
const idx = self.ast_nodes.items.len;
@@ -4215,24 +4173,20 @@ fn writePackageTableToJson(
fn srcLocInfo(
self: Autodoc,
file: *File,
- src_node: ?i32,
+ src_node: i32,
parent_src: SrcLocInfo,
) !SrcLocInfo {
- if (src_node) |unwrapped_src_node| {
- const sn = parent_src.src_node + unwrapped_src_node;
- const tree = try file.getTree(self.module.gpa);
- const node_idx = @bitCast(Ast.Node.Index, sn);
- const tokens = tree.nodes.items(.main_token);
-
- const tok_idx = tokens[node_idx];
- const start = tree.tokens.items(.start)[tok_idx];
- const loc = tree.tokenLocation(parent_src.bytes, tok_idx);
- return SrcLocInfo{
- .line = parent_src.line + loc.line,
- .bytes = start,
- .src_node = sn,
- };
- } else {
- return parent_src;
- }
+ const sn = @intCast(u32, @intCast(i32, parent_src.src_node) + src_node);
+ const tree = try file.getTree(self.module.gpa);
+ const node_idx = @bitCast(Ast.Node.Index, sn);
+ const tokens = tree.nodes.items(.main_token);
+
+ const tok_idx = tokens[node_idx];
+ const start = tree.tokens.items(.start)[tok_idx];
+ const loc = tree.tokenLocation(parent_src.bytes, tok_idx);
+ return SrcLocInfo{
+ .line = parent_src.line + loc.line,
+ .bytes = start,
+ .src_node = sn,
+ };
}