| ... | ... | @@ -4,22 +4,35 @@ const std = @import("std"); |
| 4 | 4 | const Io = std.Io; |
| 5 | 5 | const Configuration = std.Build.Configuration; |
| 6 | 6 | const Writer = std.Io.Writer; |
| 7 | const Path = std.Build.Cache.Path; |
| 8 | const Allocator = std.mem.Allocator; |
| 7 | 9 | |
| 8 | 10 | const Step = @import("../Step.zig"); |
| 9 | 11 | const Maker = @import("../../Maker.zig"); |
| 10 | 12 | |
| 13 | const header_text = "This file was generated by ConfigHeader using the Zig Build System."; |
| 14 | const c_generated_line = "/* " ++ header_text ++ " */\n"; |
| 15 | const asm_generated_line = "; " ++ header_text ++ "\n"; |
| 16 | |
| 11 | 17 | pub fn make( |
| 12 | 18 | config_header: *ConfigHeader, |
| 13 | 19 | step_index: Configuration.Step.Index, |
| 14 | 20 | maker: *Maker, |
| 15 | 21 | progress_node: std.Progress.Node, |
| 16 | 22 | ) Step.ExtendedMakeError!void { |
| 23 | _ = config_header; |
| 24 | _ = progress_node; |
| 17 | 25 | const graph = maker.graph; |
| 18 | | const arena = maker.graph.arena; // TODO don't leak into process arena |
| 26 | const gpa = maker.gpa; |
| 19 | 27 | const step = maker.stepByIndex(step_index); |
| 20 | 28 | const io = graph.io; |
| 29 | const arena = graph.arena; // TODO don't leak into the process arena |
| 30 | const conf = &maker.scanned_config.configuration; |
| 31 | const conf_step = step_index.ptr(conf); |
| 32 | const conf_ch = conf_step.extended.get(conf.extra).config_header; |
| 33 | const cache_root = graph.local_cache_root; |
| 21 | 34 | |
| 22 | | if (config_header.style.getPath()) |lp| |
| 35 | if (conf_ch.style.getPath()) |lp| |
| 23 | 36 | try step.singleUnchangingWatchInput(maker, arena, lp); |
| 24 | 37 | |
| 25 | 38 | var man = graph.cache.obtain(); |
| ... | ... | @@ -29,45 +42,51 @@ pub fn make( |
| 29 | 42 | // random bytes when ConfigHeader implementation is modified in a |
| 30 | 43 | // non-backwards-compatible way. |
| 31 | 44 | man.hash.add(@as(u32, 0xdef08d23)); |
| 32 | | man.hash.addBytes(config_header.include_path); |
| 33 | | man.hash.addOptionalBytes(config_header.include_guard_override); |
| 45 | man.hash.addBytes(conf_ch.include_path); |
| 46 | man.hash.addOptionalBytes(conf_ch.include_guard_override); |
| 34 | 47 | |
| 35 | 48 | var aw: Writer.Allocating = .init(arena); |
| 36 | 49 | defer aw.deinit(); |
| 37 | | const bw = &aw.writer; |
| 38 | 50 | |
| 39 | | const header_text = "This file was generated by ConfigHeader using the Zig Build System."; |
| 40 | | const c_generated_line = "/* " ++ header_text ++ " */\n"; |
| 41 | | const asm_generated_line = "; " ++ header_text ++ "\n"; |
| 42 | | |
| 43 | | switch (config_header.style) { |
| 44 | | .autoconf_undef, .autoconf_at => |file_source| { |
| 45 | | try bw.writeAll(c_generated_line); |
| 46 | | const src_path = file_source.getPath2(b, step); |
| 47 | | const contents = Io.Dir.cwd().readFileAlloc(io, src_path, arena, .limited(config_header.max_bytes)) catch |err| { |
| 51 | switch (conf_ch.flags.style) { |
| 52 | .autoconf_undef => { |
| 53 | const src_path = try maker.resolveLazyPathIndex(arena, conf_ch.template_file.value.?, step_index); |
| 54 | const contents = Io.Dir.cwd().readFileAlloc(io, src_path, arena, .limited(conf_ch.max_bytes)) catch |err| |
| 48 | 55 | return step.fail("unable to read autoconf input file {s}: {t}", .{ src_path, err }); |
| 56 | renderAutoConfUndef(step, contents, &aw.writer, &conf_ch.values, src_path) catch |err| switch (err) { |
| 57 | error.WriteFailed => return error.OutOfMemory, |
| 58 | else => |e| return e, |
| 59 | }; |
| 60 | }, |
| 61 | .autoconf_at => { |
| 62 | const src_path = try maker.resolveLazyPathIndex(arena, conf_ch.template_file.value.?, step_index); |
| 63 | const contents = Io.Dir.cwd().readFileAlloc(io, src_path, arena, .limited(conf_ch.max_bytes)) catch |err| |
| 64 | return step.fail("unable to read autoconf input file {s}: {t}", .{ src_path, err }); |
| 65 | renderAutoconfAt(step, contents, &aw, &conf_ch.values, src_path) catch |err| switch (err) { |
| 66 | error.WriteFailed => return error.OutOfMemory, |
| 67 | else => |e| return e, |
| 49 | 68 | }; |
| 50 | | switch (config_header.style) { |
| 51 | | .autoconf_undef => try render_autoconf_undef(step, contents, bw, &config_header.values, src_path), |
| 52 | | .autoconf_at => try render_autoconf_at(step, contents, &aw, &config_header.values, src_path), |
| 53 | | else => unreachable, |
| 54 | | } |
| 55 | 69 | }, |
| 56 | | .cmake => |file_source| { |
| 57 | | try bw.writeAll(c_generated_line); |
| 58 | | const src_path = file_source.getPath2(b, step); |
| 59 | | const contents = Io.Dir.cwd().readFileAlloc(io, src_path, arena, .limited(config_header.max_bytes)) catch |err| { |
| 70 | .cmake => { |
| 71 | const src_path = try maker.resolveLazyPathIndex(arena, conf_ch.template_file.value.?, step_index); |
| 72 | const contents = Io.Dir.cwd().readFileAlloc(io, src_path, arena, .limited(conf_ch.max_bytes)) catch |err| |
| 60 | 73 | return step.fail("unable to read cmake input file {s}: {t}", .{ src_path, err }); |
| 74 | renderCmake(step, contents, &aw.writer, conf_ch.values, src_path) catch |err| switch (err) { |
| 75 | error.WriteFailed => return error.OutOfMemory, |
| 76 | else => |e| return e, |
| 61 | 77 | }; |
| 62 | | try render_cmake(step, contents, bw, config_header.values, src_path); |
| 63 | 78 | }, |
| 64 | 79 | .blank => { |
| 65 | | try bw.writeAll(c_generated_line); |
| 66 | | try render_blank(gpa, bw, config_header.values, config_header.include_path, config_header.include_guard_override); |
| 80 | renderBlank(gpa, &aw.writer, conf_ch.values, conf_ch.include_path, conf_ch.include_guard_override) catch |err| switch (err) { |
| 81 | error.WriteFailed => return error.OutOfMemory, |
| 82 | else => |e| return e, |
| 83 | }; |
| 67 | 84 | }, |
| 68 | 85 | .nasm => { |
| 69 | | try bw.writeAll(asm_generated_line); |
| 70 | | try render_nasm(bw, config_header.values); |
| 86 | renderNasm(&aw.writer, conf_ch.values) catch |err| switch (err) { |
| 87 | error.WriteFailed => return error.OutOfMemory, |
| 88 | else => |e| return e, |
| 89 | }; |
| 71 | 90 | }, |
| 72 | 91 | } |
| 73 | 92 | |
| ... | ... | @@ -76,7 +95,10 @@ pub fn make( |
| 76 | 95 | |
| 77 | 96 | if (try step.cacheHit(&man)) { |
| 78 | 97 | const digest = man.final(); |
| 79 | | config_header.generated_dir.path = try b.cache_root.join(arena, &.{ "o", &digest }); |
| 98 | maker.generatedPath().* = .{ |
| 99 | .root_dir = cache_root, |
| 100 | .sub_path = try Io.Dir.path.join(arena, &.{ "o", &digest }), |
| 101 | }; |
| 80 | 102 | return; |
| 81 | 103 | } |
| 82 | 104 | |
| ... | ... | @@ -87,35 +109,38 @@ pub fn make( |
| 87 | 109 | // output_path is libavutil/avconfig.h |
| 88 | 110 | // We want to open directory zig-cache/o/HASH/libavutil/ |
| 89 | 111 | // but keep output_dir as zig-cache/o/HASH for -I include |
| 90 | | const sub_path = b.pathJoin(&.{ "o", &digest, config_header.include_path }); |
| 91 | | const sub_path_dirname = std.fs.path.dirname(sub_path).?; |
| 92 | | |
| 93 | | b.cache_root.handle.createDirPath(io, sub_path_dirname) catch |err| { |
| 94 | | return step.fail("unable to make path '{f}{s}': {s}", .{ |
| 95 | | b.cache_root, sub_path_dirname, @errorName(err), |
| 96 | | }); |
| 112 | const out_path: Path = .{ |
| 113 | .root_dir = cache_root, |
| 114 | .sub_path = try Io.Dir.path.join(arena, &.{ "o", &digest, conf_ch.include_path.slice(conf) }), |
| 97 | 115 | }; |
| 116 | const out_path_dirname = out_path.dirname().?; |
| 117 | |
| 118 | out_path_dirname.root_dir.handle.createDirPath(io, out_path_dirname.sub_path) catch |err| |
| 119 | return step.fail("unable to make path {f}: {t}", .{ out_path_dirname, err }); |
| 98 | 120 | |
| 99 | | b.cache_root.handle.writeFile(io, .{ .sub_path = sub_path, .data = output }) catch |err| { |
| 100 | | return step.fail("unable to write file '{f}{s}': {s}", .{ |
| 101 | | b.cache_root, sub_path, @errorName(err), |
| 102 | | }); |
| 121 | out_path.root_dir.handle.writeFile(io, .{ .sub_path = out_path.sub_path, .data = output }) catch |err| |
| 122 | return step.fail("unable to write file {f}: {t}", .{ out_path, err }); |
| 123 | |
| 124 | maker.generatedPath().* = .{ |
| 125 | .root_dir = cache_root, |
| 126 | .sub_path = try Io.Dir.path.join(arena, &.{ "o", &digest }), |
| 103 | 127 | }; |
| 104 | 128 | |
| 105 | | config_header.generated_dir.path = try b.cache_root.join(arena, &.{ "o", &digest }); |
| 106 | | try man.writeManifest(); |
| 129 | try step.writeManifest(maker, &man); |
| 107 | 130 | } |
| 108 | 131 | |
| 109 | | fn render_autoconf_undef( |
| 132 | fn renderAutoConfUndef( |
| 110 | 133 | step: *Step, |
| 111 | 134 | contents: []const u8, |
| 112 | | bw: *Writer, |
| 135 | w: *Writer, |
| 113 | 136 | values: *const std.array_hash_map.String(Value), |
| 114 | 137 | src_path: []const u8, |
| 115 | 138 | ) !void { |
| 116 | 139 | const build = step.owner; |
| 117 | 140 | const allocator = build.allocator; |
| 118 | 141 | |
| 142 | try w.writeAll(c_generated_line); |
| 143 | |
| 119 | 144 | var is_used: std.bit_set.Dynamic = try .initEmpty(allocator, values.count()); |
| 120 | 145 | defer is_used.deinit(allocator); |
| 121 | 146 | |
| ... | ... | @@ -124,15 +149,15 @@ fn render_autoconf_undef( |
| 124 | 149 | var line_it = std.mem.splitScalar(u8, contents, '\n'); |
| 125 | 150 | while (line_it.next()) |line| : (line_index += 1) { |
| 126 | 151 | if (!std.mem.startsWith(u8, line, "#")) { |
| 127 | | try bw.writeAll(line); |
| 128 | | try bw.writeByte('\n'); |
| 152 | try w.writeAll(line); |
| 153 | try w.writeByte('\n'); |
| 129 | 154 | continue; |
| 130 | 155 | } |
| 131 | 156 | var it = std.mem.tokenizeAny(u8, line[1..], " \t\r"); |
| 132 | 157 | const undef = it.next().?; |
| 133 | 158 | if (!std.mem.eql(u8, undef, "undef")) { |
| 134 | | try bw.writeAll(line); |
| 135 | | try bw.writeByte('\n'); |
| 159 | try w.writeAll(line); |
| 160 | try w.writeByte('\n'); |
| 136 | 161 | continue; |
| 137 | 162 | } |
| 138 | 163 | const name = it.next().?; |
| ... | ... | @@ -144,7 +169,7 @@ fn render_autoconf_undef( |
| 144 | 169 | continue; |
| 145 | 170 | }; |
| 146 | 171 | is_used.set(index); |
| 147 | | try renderValueC(bw, name, values.values()[index]); |
| 172 | try renderValueC(w, name, values.values()[index]); |
| 148 | 173 | } |
| 149 | 174 | |
| 150 | 175 | var unused_value_it = is_used.iterator(.{ .kind = .unset }); |
| ... | ... | @@ -158,7 +183,7 @@ fn render_autoconf_undef( |
| 158 | 183 | } |
| 159 | 184 | } |
| 160 | 185 | |
| 161 | | fn render_autoconf_at( |
| 186 | fn renderAutoconfAt( |
| 162 | 187 | step: *Step, |
| 163 | 188 | contents: []const u8, |
| 164 | 189 | aw: *Writer.Allocating, |
| ... | ... | @@ -167,7 +192,9 @@ fn render_autoconf_at( |
| 167 | 192 | ) !void { |
| 168 | 193 | const build = step.owner; |
| 169 | 194 | const allocator = build.allocator; |
| 170 | | const bw = &aw.writer; |
| 195 | const w = &aw.writer; |
| 196 | |
| 197 | try w.writeAll(c_generated_line); |
| 171 | 198 | |
| 172 | 199 | const used = allocator.alloc(bool, values.count()) catch @panic("OOM"); |
| 173 | 200 | for (used) |*u| u.* = false; |
| ... | ... | @@ -180,7 +207,7 @@ fn render_autoconf_at( |
| 180 | 207 | const last_line = line_it.index == line_it.buffer.len; |
| 181 | 208 | |
| 182 | 209 | const old_len = aw.written().len; |
| 183 | | expand_variables_autoconf_at(bw, line, values, used) catch |err| switch (err) { |
| 210 | expandVariablesAutoconfAt(w, line, values, used) catch |err| switch (err) { |
| 184 | 211 | error.MissingValue => { |
| 185 | 212 | const name = aw.written()[old_len..]; |
| 186 | 213 | defer aw.shrinkRetainingCapacity(old_len); |
| ... | ... | @@ -198,7 +225,7 @@ fn render_autoconf_at( |
| 198 | 225 | continue; |
| 199 | 226 | }, |
| 200 | 227 | }; |
| 201 | | if (!last_line) try bw.writeByte('\n'); |
| 228 | if (!last_line) try w.writeByte('\n'); |
| 202 | 229 | } |
| 203 | 230 | |
| 204 | 231 | for (values.entries.slice().items(.key), used) |name, u| { |
| ... | ... | @@ -211,16 +238,18 @@ fn render_autoconf_at( |
| 211 | 238 | if (any_errors) return error.MakeFailed; |
| 212 | 239 | } |
| 213 | 240 | |
| 214 | | fn render_cmake( |
| 241 | fn renderCmake( |
| 215 | 242 | step: *Step, |
| 216 | 243 | contents: []const u8, |
| 217 | | bw: *Writer, |
| 244 | w: *Writer, |
| 218 | 245 | values: std.array_hash_map.String(Value), |
| 219 | 246 | src_path: []const u8, |
| 220 | 247 | ) !void { |
| 221 | 248 | const build = step.owner; |
| 222 | 249 | const allocator = build.allocator; |
| 223 | 250 | |
| 251 | try w.writeAll(c_generated_line); |
| 252 | |
| 224 | 253 | var values_copy = try values.clone(allocator); |
| 225 | 254 | defer values_copy.deinit(allocator); |
| 226 | 255 | |
| ... | ... | @@ -230,7 +259,7 @@ fn render_cmake( |
| 230 | 259 | while (line_it.next()) |raw_line| : (line_index += 1) { |
| 231 | 260 | const last_line = line_it.index == line_it.buffer.len; |
| 232 | 261 | |
| 233 | | const line = expand_variables_cmake(allocator, raw_line, values) catch |err| switch (err) { |
| 262 | const line = expandVariablesCmake(allocator, raw_line, values) catch |err| switch (err) { |
| 234 | 263 | error.InvalidCharacter => { |
| 235 | 264 | try step.addError("{s}:{d}: error: invalid character in a variable name", .{ |
| 236 | 265 | src_path, line_index + 1, |
| ... | ... | @@ -249,16 +278,16 @@ fn render_cmake( |
| 249 | 278 | defer allocator.free(line); |
| 250 | 279 | |
| 251 | 280 | const line_start = std.mem.findNone(u8, line, " \t\r") orelse { |
| 252 | | try bw.writeAll(line); |
| 253 | | if (!last_line) try bw.writeByte('\n'); |
| 281 | try w.writeAll(line); |
| 282 | if (!last_line) try w.writeByte('\n'); |
| 254 | 283 | continue; |
| 255 | 284 | }; |
| 256 | 285 | const whitespace_prefix = line[0..line_start]; |
| 257 | 286 | const trimmed_line = line[line_start..]; |
| 258 | 287 | |
| 259 | 288 | if (!std.mem.startsWith(u8, trimmed_line, "#")) { |
| 260 | | try bw.writeAll(line); |
| 261 | | if (!last_line) try bw.writeByte('\n'); |
| 289 | try w.writeAll(line); |
| 290 | if (!last_line) try w.writeByte('\n'); |
| 262 | 291 | continue; |
| 263 | 292 | } |
| 264 | 293 | |
| ... | ... | @@ -267,8 +296,8 @@ fn render_cmake( |
| 267 | 296 | if (!std.mem.eql(u8, cmakedefine, "cmakedefine") and |
| 268 | 297 | !std.mem.eql(u8, cmakedefine, "cmakedefine01")) |
| 269 | 298 | { |
| 270 | | try bw.writeAll(line); |
| 271 | | if (!last_line) try bw.writeByte('\n'); |
| 299 | try w.writeAll(line); |
| 300 | if (!last_line) try w.writeByte('\n'); |
| 272 | 301 | continue; |
| 273 | 302 | } |
| 274 | 303 | |
| ... | ... | @@ -339,8 +368,8 @@ fn render_cmake( |
| 339 | 368 | value = Value{ .ident = it.rest() }; |
| 340 | 369 | } |
| 341 | 370 | |
| 342 | | try bw.writeAll(whitespace_prefix); |
| 343 | | try renderValueC(bw, name, value); |
| 371 | try w.writeAll(whitespace_prefix); |
| 372 | try renderValueC(w, name, value); |
| 344 | 373 | } |
| 345 | 374 | |
| 346 | 375 | if (any_errors) { |
| ... | ... | @@ -348,13 +377,15 @@ fn render_cmake( |
| 348 | 377 | } |
| 349 | 378 | } |
| 350 | 379 | |
| 351 | | fn render_blank( |
| 380 | fn renderBlank( |
| 352 | 381 | gpa: std.mem.Allocator, |
| 353 | | bw: *Writer, |
| 382 | w: *Writer, |
| 354 | 383 | defines: std.array_hash_map.String(Value), |
| 355 | 384 | include_path: []const u8, |
| 356 | 385 | include_guard_override: ?[]const u8, |
| 357 | 386 | ) !void { |
| 387 | try w.writeAll(c_generated_line); |
| 388 | |
| 358 | 389 | const include_guard_name = include_guard_override orelse blk: { |
| 359 | 390 | const name = try gpa.dupe(u8, include_path); |
| 360 | 391 | for (name) |*byte| { |
| ... | ... | @@ -368,51 +399,52 @@ fn render_blank( |
| 368 | 399 | }; |
| 369 | 400 | defer if (include_guard_override == null) gpa.free(include_guard_name); |
| 370 | 401 | |
| 371 | | try bw.print( |
| 402 | try w.print( |
| 372 | 403 | \\#ifndef {[0]s} |
| 373 | 404 | \\#define {[0]s} |
| 374 | 405 | \\ |
| 375 | 406 | , .{include_guard_name}); |
| 376 | 407 | |
| 377 | 408 | const values = defines.values(); |
| 378 | | for (defines.keys(), 0..) |name, i| try renderValueC(bw, name, values[i]); |
| 409 | for (defines.keys(), 0..) |name, i| try renderValueC(w, name, values[i]); |
| 379 | 410 | |
| 380 | | try bw.print( |
| 411 | try w.print( |
| 381 | 412 | \\#endif /* {s} */ |
| 382 | 413 | \\ |
| 383 | 414 | , .{include_guard_name}); |
| 384 | 415 | } |
| 385 | 416 | |
| 386 | | fn render_nasm(bw: *Writer, defines: std.array_hash_map.String(Value)) !void { |
| 387 | | for (defines.keys(), defines.values()) |name, value| try renderValueNasm(bw, name, value); |
| 417 | fn renderNasm(w: *Writer, defines: std.array_hash_map.String(Value)) !void { |
| 418 | try w.writeAll(asm_generated_line); |
| 419 | for (defines.keys(), defines.values()) |name, value| try renderValueNasm(w, name, value); |
| 388 | 420 | } |
| 389 | 421 | |
| 390 | | fn renderValueC(bw: *Writer, name: []const u8, value: Value) !void { |
| 422 | fn renderValueC(w: *Writer, name: []const u8, value: Value) !void { |
| 391 | 423 | switch (value) { |
| 392 | | .undef => try bw.print("/* #undef {s} */\n", .{name}), |
| 393 | | .defined => try bw.print("#define {s}\n", .{name}), |
| 394 | | .boolean => |b| try bw.print("#define {s} {c}\n", .{ name, @as(u8, '0') + @intFromBool(b) }), |
| 395 | | .int => |i| try bw.print("#define {s} {d}\n", .{ name, i }), |
| 396 | | .ident => |ident| try bw.print("#define {s} {s}\n", .{ name, ident }), |
| 424 | .undef => try w.print("/* #undef {s} */\n", .{name}), |
| 425 | .defined => try w.print("#define {s}\n", .{name}), |
| 426 | .boolean => |b| try w.print("#define {s} {c}\n", .{ name, @as(u8, '0') + @intFromBool(b) }), |
| 427 | .int => |i| try w.print("#define {s} {d}\n", .{ name, i }), |
| 428 | .ident => |ident| try w.print("#define {s} {s}\n", .{ name, ident }), |
| 397 | 429 | // TODO: use C-specific escaping instead of zig string literals |
| 398 | | .string => |string| try bw.print("#define {s} \"{f}\"\n", .{ name, std.zig.fmtString(string) }), |
| 430 | .string => |string| try w.print("#define {s} \"{f}\"\n", .{ name, std.zig.fmtString(string) }), |
| 399 | 431 | } |
| 400 | 432 | } |
| 401 | 433 | |
| 402 | | fn renderValueNasm(bw: *Writer, name: []const u8, value: Value) !void { |
| 434 | fn renderValueNasm(w: *Writer, name: []const u8, value: Value) !void { |
| 403 | 435 | switch (value) { |
| 404 | | .undef => try bw.print("; %undef {s}\n", .{name}), |
| 405 | | .defined => try bw.print("%define {s}\n", .{name}), |
| 406 | | .boolean => |b| try bw.print("%define {s} {c}\n", .{ name, @as(u8, '0') + @intFromBool(b) }), |
| 407 | | .int => |i| try bw.print("%define {s} {d}\n", .{ name, i }), |
| 408 | | .ident => |ident| try bw.print("%define {s} {s}\n", .{ name, ident }), |
| 436 | .undef => try w.print("; %undef {s}\n", .{name}), |
| 437 | .defined => try w.print("%define {s}\n", .{name}), |
| 438 | .boolean => |b| try w.print("%define {s} {c}\n", .{ name, @as(u8, '0') + @intFromBool(b) }), |
| 439 | .int => |i| try w.print("%define {s} {d}\n", .{ name, i }), |
| 440 | .ident => |ident| try w.print("%define {s} {s}\n", .{ name, ident }), |
| 409 | 441 | // TODO: use nasm-specific escaping instead of zig string literals |
| 410 | | .string => |string| try bw.print("%define {s} \"{f}\"\n", .{ name, std.zig.fmtString(string) }), |
| 442 | .string => |string| try w.print("%define {s} \"{f}\"\n", .{ name, std.zig.fmtString(string) }), |
| 411 | 443 | } |
| 412 | 444 | } |
| 413 | 445 | |
| 414 | | fn expand_variables_autoconf_at( |
| 415 | | bw: *Writer, |
| 446 | fn expandVariablesAutoconfAt( |
| 447 | w: *Writer, |
| 416 | 448 | contents: []const u8, |
| 417 | 449 | values: *const std.array_hash_map.String(Value), |
| 418 | 450 | used: []bool, |
| ... | ... | @@ -437,17 +469,17 @@ fn expand_variables_autoconf_at( |
| 437 | 469 | const key = contents[curr + 1 .. close_pos]; |
| 438 | 470 | const index = values.getIndex(key) orelse { |
| 439 | 471 | // Report the missing key to the caller. |
| 440 | | try bw.writeAll(key); |
| 472 | try w.writeAll(key); |
| 441 | 473 | return error.MissingValue; |
| 442 | 474 | }; |
| 443 | 475 | const value = values.entries.slice().items(.value)[index]; |
| 444 | 476 | used[index] = true; |
| 445 | | try bw.writeAll(contents[source_offset..curr]); |
| 477 | try w.writeAll(contents[source_offset..curr]); |
| 446 | 478 | switch (value) { |
| 447 | 479 | .undef, .defined => {}, |
| 448 | | .boolean => |b| try bw.writeByte(@as(u8, '0') + @intFromBool(b)), |
| 449 | | .int => |i| try bw.print("{d}", .{i}), |
| 450 | | .ident, .string => |s| try bw.writeAll(s), |
| 480 | .boolean => |b| try w.writeByte(@as(u8, '0') + @intFromBool(b)), |
| 481 | .int => |i| try w.print("{d}", .{i}), |
| 482 | .ident, .string => |s| try w.writeAll(s), |
| 451 | 483 | } |
| 452 | 484 | |
| 453 | 485 | curr = close_pos; |
| ... | ... | @@ -455,10 +487,10 @@ fn expand_variables_autoconf_at( |
| 455 | 487 | } |
| 456 | 488 | } |
| 457 | 489 | |
| 458 | | try bw.writeAll(contents[source_offset..]); |
| 490 | try w.writeAll(contents[source_offset..]); |
| 459 | 491 | } |
| 460 | 492 | |
| 461 | | fn expand_variables_cmake( |
| 493 | fn expandVariablesCmake( |
| 462 | 494 | allocator: Allocator, |
| 463 | 495 | contents: []const u8, |
| 464 | 496 | values: std.array_hash_map.String(Value), |
| ... | ... | @@ -602,7 +634,7 @@ fn testReplaceVariablesAutoconfAt( |
| 602 | 634 | for (used) |*u| u.* = false; |
| 603 | 635 | defer allocator.free(used); |
| 604 | 636 | |
| 605 | | try expand_variables_autoconf_at(&aw.writer, contents, values, used); |
| 637 | try expandVariablesAutoconfAt(&aw.writer, contents, values, used); |
| 606 | 638 | |
| 607 | 639 | for (used) |u| if (!u) return error.UnusedValue; |
| 608 | 640 | try std.testing.expectEqualStrings(expected, aw.written()); |
| ... | ... | @@ -614,13 +646,13 @@ fn testReplaceVariablesCMake( |
| 614 | 646 | expected: []const u8, |
| 615 | 647 | values: std.array_hash_map.String(Value), |
| 616 | 648 | ) !void { |
| 617 | | const actual = try expand_variables_cmake(allocator, contents, values); |
| 649 | const actual = try expandVariablesCmake(allocator, contents, values); |
| 618 | 650 | defer allocator.free(actual); |
| 619 | 651 | |
| 620 | 652 | try std.testing.expectEqualStrings(expected, actual); |
| 621 | 653 | } |
| 622 | 654 | |
| 623 | | test "expand_variables_autoconf_at simple cases" { |
| 655 | test "expandVariablesAutoconfAt simple cases" { |
| 624 | 656 | const allocator = std.testing.allocator; |
| 625 | 657 | var values: std.array_hash_map.String(Value) = .init(allocator); |
| 626 | 658 | defer values.deinit(); |
| ... | ... | @@ -716,7 +748,7 @@ test "expand_variables_autoconf_at simple cases" { |
| 716 | 748 | values.clearRetainingCapacity(); |
| 717 | 749 | } |
| 718 | 750 | |
| 719 | | test "expand_variables_autoconf_at edge cases" { |
| 751 | test "expandVariablesAutoconfAt edge cases" { |
| 720 | 752 | const allocator = std.testing.allocator; |
| 721 | 753 | var values: std.array_hash_map.String(Value) = .init(allocator); |
| 722 | 754 | defer values.deinit(); |
| ... | ... | @@ -732,7 +764,7 @@ test "expand_variables_autoconf_at edge cases" { |
| 732 | 764 | values.clearRetainingCapacity(); |
| 733 | 765 | } |
| 734 | 766 | |
| 735 | | test "expand_variables_cmake simple cases" { |
| 767 | test "expandVariablesCmake simple cases" { |
| 736 | 768 | const allocator = std.testing.allocator; |
| 737 | 769 | var values: std.array_hash_map.String(Value) = .init(allocator); |
| 738 | 770 | defer values.deinit(); |
| ... | ... | @@ -820,7 +852,7 @@ test "expand_variables_cmake simple cases" { |
| 820 | 852 | try std.testing.expectError(error.MissingValue, testReplaceVariablesCMake(allocator, "${bad}", "", values)); |
| 821 | 853 | } |
| 822 | 854 | |
| 823 | | test "expand_variables_cmake edge cases" { |
| 855 | test "expandVariablesCmake edge cases" { |
| 824 | 856 | const allocator = std.testing.allocator; |
| 825 | 857 | var values: std.array_hash_map.String(Value) = .init(allocator); |
| 826 | 858 | defer values.deinit(); |
| ... | ... | @@ -881,7 +913,7 @@ test "expand_variables_cmake edge cases" { |
| 881 | 913 | try std.testing.expectError(error.InvalidCharacter, testReplaceVariablesCMake(allocator, "${str@ing}", "", values)); |
| 882 | 914 | } |
| 883 | 915 | |
| 884 | | test "expand_variables_cmake escaped characters" { |
| 916 | test "expandVariablesCmake escaped characters" { |
| 885 | 917 | const allocator = std.testing.allocator; |
| 886 | 918 | var values: std.array_hash_map.String(Value) = .init(allocator); |
| 887 | 919 | defer values.deinit(); |