feature. See also
. The project being documented here (as the example) is the Zig library itself.
Serialize.addModule
fn addModule(s: *Serialize, m: *std.Build.Module) !Configuration.Module.Index
File
Code
fn addModule(s: *Serialize, m: *std.Build.Module) !Configuration.Module.Index {
if (s.module_map.get(m)) |index| return index;
const wc = s.wc;
const arena = s.arena;
const rpaths = try arena.alloc(Configuration.Module.RPath, m.rpaths.items.len);
for (rpaths, m.rpaths.items) |*dest, src| dest.* = switch (src) {
.lazy_path => |lp| .{ .lazy_path = try addLazyPath(s, lp) },
.special => |slice| .{ .special = try wc.addString(slice) },
};
const link_objects = try arena.alloc(Configuration.Module.LinkObject, m.link_objects.items.len);
for (link_objects, m.link_objects.items) |*dest, *src| dest.* = switch (src.*) {
.static_path => |lp| .{ .static_path = try addLazyPath(s, lp) },
.other_step => |cs| .{ .other_step = stepIndex(s, &cs.step) },
.system_lib => |*sl| .{ .system_lib = try addSystemLib(s, sl) },
.assembly_file => |lp| .{ .assembly_file = try addLazyPath(s, lp) },
.c_source_file => |csf| .{ .c_source_file = try addCSourceFile(s, csf) },
.c_source_files => |csf| .{ .c_source_files = try addCSourceFiles(s, csf) },
.win32_resource_file => |wrf| .{ .win32_resource_file = try addRcSourceFile(s, wrf) },
};
const frameworks = try arena.alloc(Configuration.Module.Framework, m.frameworks.entries.len);
for (frameworks, m.frameworks.keys(), m.frameworks.values()) |*dest, name, options| dest.* = .{
.flags = .{
.needed = options.needed,
.weak = options.weak,
},
.name = try wc.addString(name),
};
const lib_paths = try initLazyPathList(s, m.lib_paths.items);
const c_macros = try initStringList(s, m.c_macros.items);
const export_symbol_names = try initStringList(s, m.export_symbol_names);
const module_index: Configuration.Module.Index = try wc.addExtra(Configuration.Module, .{
.flags = .{
.optimize = .init(m.optimize),
.strip = .init(m.strip),
.unwind_tables = .init(m.unwind_tables),
.dwarf_format = .init(m.dwarf_format),
.single_threaded = .init(m.single_threaded),
.stack_protector = .init(m.stack_protector),
.stack_check = .init(m.stack_check),
.sanitize_c = .init(m.sanitize_c),
.sanitize_thread = .init(m.sanitize_thread),
.fuzz = .init(m.fuzz),
.code_model = m.code_model,
.c_macros = c_macros.len != 0,
.include_dirs = m.include_dirs.items.len != 0,
.lib_paths = lib_paths.len != 0,
.rpaths = rpaths.len != 0,
.frameworks = frameworks.len != 0,
.link_objects = link_objects.len != 0,
.export_symbol_names = export_symbol_names.len != 0,
},
.flags2 = .{
.valgrind = .init(m.valgrind),
.pic = .init(m.pic),
.red_zone = .init(m.red_zone),
.omit_frame_pointer = .init(m.omit_frame_pointer),
.error_tracing = .init(m.error_tracing),
.link_libc = .init(m.link_libc),
.link_libcpp = .init(m.link_libcpp),
.no_builtin = .init(m.no_builtin),
},
.owner = try s.builderToPackage(m.owner),
.root_source_file = try s.addOptionalLazyPathEnum(m.root_source_file),
.import_table = .invalid,
.resolved_target = try addOptionalResolvedTarget(wc, m.resolved_target),
.c_macros = .{ .slice = c_macros },
.lib_paths = .{ .slice = lib_paths },
.export_symbol_names = .{ .slice = export_symbol_names },
.include_dirs = .init(try s.initIncludeDirList(m.include_dirs.items)),
.rpaths = .init(rpaths),
.link_objects = .init(link_objects),
.frameworks = .{ .slice = frameworks },
});
// loops. Therefore, we populate the module indexes only after adding
// the module to module_map.
try s.module_map.putNoClobber(arena, m, module_index);
var imports = try std.MultiArrayList(Configuration.ImportTable.Import).initCapacity(arena, m.import_table.entries.len);
imports.len = m.import_table.entries.len;
for (
imports.items(.name),
imports.items(.module),
m.import_table.keys(),
m.import_table.values(),
) |*dest_name, *dest_module, src_name, src_module| {
dest_name.* = try wc.addString(src_name);
dest_module.* = try addModule(s, src_module);
}
comptime assert(std.mem.eql(u8, @typeInfo(Configuration.Module).@"struct".field_names[2], "import_table"));
comptime assert(@typeInfo(Configuration.Module).@"struct".field_types[2] == Configuration.ImportTable.Index);
assert(wc.extra.items[@backingInt(module_index) + 2] == @backingInt(Configuration.ImportTable.Index.invalid));
const import_table_index = try wc.addDeduped(Configuration.ImportTable, .{
.imports = .{ .mal = imports },
});
wc.extra.items[@backingInt(module_index) + 2] = @backingInt(import_table_index);
return module_index;
}