-
Notifications
You must be signed in to change notification settings - Fork 2
/
build.zig
180 lines (153 loc) · 6.54 KB
/
build.zig
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
const std = @import("std");
const Build = std.Build;
const Mode = std.builtin.Mode;
pub fn build(b: *Build) void {
const target = b.standardTargetOptions(.{});
const optimize = b.standardOptimizeOption(.{});
const xml = b.addModule("xml", .{
.root_source_file = b.path("src/xml.zig"),
});
addTests(b, target, optimize, xml);
addDocs(b, target);
addExamples(b, target, optimize, xml);
addFuzz(b, target, xml);
}
fn addTests(b: *Build, target: Build.ResolvedTarget, optimize: Mode, xml: *Build.Module) void {
const main_tests = b.addTest(.{
.root_source_file = b.path("src/xml.zig"),
.target = target,
.optimize = optimize,
});
const run_main_tests = b.addRunArtifact(main_tests);
const test_step = b.step("test", "Run library tests");
test_step.dependOn(&run_main_tests.step);
const xmlconf_exe = b.addExecutable(.{
.name = "xmlconf",
.root_source_file = b.path("test/xmlconf.zig"),
.target = target,
.optimize = optimize,
});
xmlconf_exe.root_module.addImport("xml", xml);
const install_xmlconf_step = b.step("install-xmlconf", "Install xmlconf test runner");
install_xmlconf_step.dependOn(&b.addInstallArtifact(xmlconf_exe, .{}).step);
const run_xmlconf_exe = b.addRunArtifact(xmlconf_exe);
if (b.args) |args| {
run_xmlconf_exe.addArgs(args);
}
// Since we can't yet handle doctypes, the test files need to be specified
// individually
run_xmlconf_exe.addArgs(&.{
"test/xmlconf/eduni/errata-2e/errata2e.xml",
"test/xmlconf/eduni/errata-3e/errata3e.xml",
"test/xmlconf/eduni/errata-4e/errata4e.xml",
"test/xmlconf/eduni/misc/ht-bh.xml",
"test/xmlconf/eduni/namespaces/1.0/rmt-ns10.xml",
"test/xmlconf/eduni/namespaces/1.1/rmt-ns11.xml",
"test/xmlconf/eduni/namespaces/errata-1e/errata1e.xml",
"test/xmlconf/eduni/xml-1.1/xml11.xml",
"test/xmlconf/ibm/ibm_oasis_invalid.xml",
"test/xmlconf/ibm/ibm_oasis_not-wf.xml",
"test/xmlconf/ibm/ibm_oasis_valid.xml",
"test/xmlconf/japanese/japanese.xml",
"test/xmlconf/oasis/oasis.xml",
// The test case files in the sun directory do not have an enclosing
// TESTCASES element, and only work when directly substituted as entity
// content, so they cannot be used at this time.
"test/xmlconf/xmltest/xmltest.xml",
});
const run_xmlconf_step = b.step("run-xmlconf", "Run xmlconf test cases");
run_xmlconf_step.dependOn(&run_xmlconf_exe.step);
}
fn addDocs(b: *Build, target: Build.ResolvedTarget) void {
const obj = b.addObject(.{
.name = "xml",
.root_source_file = b.path("src/xml.zig"),
.target = target,
.optimize = .Debug,
});
const docs_path = obj.getEmittedDocs();
const install_docs = b.addInstallDirectory(.{
.source_dir = docs_path,
.install_dir = .prefix,
.install_subdir = "docs",
});
const docs_step = b.step("docs", "Generate documentation");
docs_step.dependOn(&install_docs.step);
}
fn addExamples(b: *Build, target: Build.ResolvedTarget, optimize: Mode, xml: *Build.Module) void {
const install_examples_step = b.step("install-examples", "Install examples");
const scan_exe = b.addExecutable(.{
.name = "scan",
.root_source_file = b.path("examples/scan.zig"),
.target = target,
.optimize = optimize,
});
scan_exe.root_module.addImport("xml", xml);
install_examples_step.dependOn(&b.addInstallArtifact(scan_exe, .{}).step);
const run_scan_exe = b.addRunArtifact(scan_exe);
if (b.args) |args| {
run_scan_exe.addArgs(args);
}
const run_scan_step = b.step("run-example-scan", "Run scan example");
run_scan_step.dependOn(&run_scan_exe.step);
const read_exe = b.addExecutable(.{
.name = "read",
.root_source_file = b.path("examples/read.zig"),
.target = target,
.optimize = optimize,
});
read_exe.root_module.addImport("xml", xml);
install_examples_step.dependOn(&b.addInstallArtifact(read_exe, .{}).step);
const run_read_exe = b.addRunArtifact(read_exe);
if (b.args) |args| {
run_read_exe.addArgs(args);
}
const run_read_step = b.step("run-example-read", "Run read example");
run_read_step.dependOn(&run_read_exe.step);
}
fn addFuzz(b: *Build, target: Build.ResolvedTarget, xml: *Build.Module) void {
// Thanks to https://www.ryanliptak.com/blog/fuzzing-zig-code/ for the basis of this!
const fuzz_lib = b.addStaticLibrary(.{
.name = "fuzz",
.root_source_file = b.path("fuzz/main.zig"),
.target = target,
.optimize = .Debug,
});
fuzz_lib.want_lto = true;
fuzz_lib.bundle_compiler_rt = true;
fuzz_lib.root_module.addImport("xml", xml);
const fuzz_compile = b.addSystemCommand(&.{ "afl-clang-lto", "-o" });
const fuzz_exe = fuzz_compile.addOutputFileArg("fuzz");
fuzz_compile.addArtifactArg(fuzz_lib);
const fuzz_install = b.addInstallBinFile(fuzz_exe, "fuzz");
const run_fuzz_compile_step = b.step("install-fuzz", "Build executable for fuzz testing using afl-clang-lto");
run_fuzz_compile_step.dependOn(&fuzz_install.step);
const run_fuzz = b.addSystemCommand(&.{"afl-fuzz"});
run_fuzz.addArg("-i");
if (b.option(bool, "resume", "Resume fuzzing rather than starting a new run") orelse false) {
run_fuzz.addArg("-");
} else {
run_fuzz.addArg(b.pathJoin(&.{ "fuzz", "inputs" }));
}
run_fuzz.addArgs(&.{ "-o", b.pathJoin(&.{ "fuzz", "outputs" }) });
const dictionaries = &[_][]const u8{ "xml.dict", "xml_UTF_16.dict", "xml_UTF_16BE.dict", "xml_UTF_16LE.dict" };
for (dictionaries) |dictionary| {
run_fuzz.addArgs(&.{ "-x", b.pathJoin(&.{ "fuzz", "dictionaries", dictionary }) });
}
run_fuzz.addFileArg(fuzz_exe);
const run_fuzz_step = b.step("fuzz", "Execute afl-fuzz with the fuzz testing executable");
run_fuzz_step.dependOn(&run_fuzz.step);
const fuzz_reproduce_exe = b.addExecutable(.{
.name = "fuzz-reproduce",
.root_source_file = b.path("fuzz/main.zig"),
.target = target,
.optimize = .Debug,
});
fuzz_reproduce_exe.root_module.addImport("xml", xml);
const run_fuzz_reproduce_exe = b.addRunArtifact(fuzz_reproduce_exe);
if (b.args) |args| {
run_fuzz_reproduce_exe.addArgs(args);
}
const run_fuzz_reproduce_step = b.step("fuzz-reproduce", "Reproduce crash found by fuzzing");
run_fuzz_reproduce_step.dependOn(&run_fuzz_reproduce_exe.step);
}