diff --git a/CompileCheck.zig b/CompileCheck.zig index a230dca..eafcbbe 100644 --- a/CompileCheck.zig +++ b/CompileCheck.zig @@ -146,7 +146,7 @@ fn make(step: *std.Build.Step, options: std.Build.Step.MakeOptions) anyerror!voi const source_path = check.source_path.getPath2(b, step); const result = blk: { - var zig_args: std.ArrayList([]const u8) = .init(b.allocator); + var zig_args: std.array_list.Managed([]const u8) = .init(b.allocator); defer zig_args.deinit(); try zig_args.append(b.graph.zig_exe); try zig_args.append(switch (check.kind) { @@ -170,7 +170,7 @@ fn make(step: *std.Build.Step, options: std.Build.Step.MakeOptions) anyerror!voi .other_step => |other| { switch (other.kind) { .exe => return step.fail("cannot link with an executable build artifact", .{}), - .@"test" => return step.fail("cannot link with a test", .{}), + .@"test", .test_obj => return step.fail("cannot link with a test", .{}), .obj => { try zig_args.append(other.getEmittedBin().getPath2(b, step)); }, @@ -248,7 +248,7 @@ fn make(step: *std.Build.Step, options: std.Build.Step.MakeOptions) anyerror!voi .undeclared_identifier_count = undeclared_identifier_count, } }; }, - inline else => return step.fail("zig {}", .{fmtTerm(result.term)}), + inline else => return step.fail("zig {f}", .{fmtTerm(result.term)}), } } @@ -264,19 +264,15 @@ fn getGeneratedFilePath(compile: *std.Build.Step.Compile, comptime tag_name: []c const maybe_path: ?*std.Build.GeneratedFile = @field(compile, tag_name); const generated_file = maybe_path orelse { - std.debug.lockStdErr(); - const stderr = std.io.getStdErr(); - - std.Build.dumpBadGetPathHelp(&compile.step, stderr, compile.step.owner, asking_step) catch {}; + const w = std.debug.lockStderrWriter(&.{}); + std.Build.dumpBadGetPathHelp(&compile.step, w, .detect(.stderr()), compile.step.owner, asking_step) catch {}; @panic("missing emit option for " ++ tag_name); }; const path = generated_file.path orelse { - std.debug.lockStdErr(); - const stderr = std.io.getStdErr(); - - std.Build.dumpBadGetPathHelp(&compile.step, stderr, compile.step.owner, asking_step) catch {}; + const w = std.debug.lockStderrWriter(&.{}); + std.Build.dumpBadGetPathHelp(&compile.step, w, .detect(.stderr()), compile.step.owner, asking_step) catch {}; @panic(tag_name ++ " is null. Is there a missing step dependency?"); }; @@ -284,17 +280,14 @@ fn getGeneratedFilePath(compile: *std.Build.Step.Compile, comptime tag_name: []c return path; } -fn fmtTerm(term: ?std.process.Child.Term) std.fmt.Formatter(formatTerm) { +fn fmtTerm(term: ?std.process.Child.Term) std.fmt.Alt(@TypeOf(term), formatTerm) { return .{ .data = term }; } +// comptime formatFn: fn (data: Data, writer: *Writer) Writer.Error!void, fn formatTerm( term: ?std.process.Child.Term, - comptime fmt: []const u8, - options: std.fmt.FormatOptions, - writer: anytype, -) !void { - _ = fmt; - _ = options; + writer: *std.Io.Writer, +) std.Io.Writer.Error!void { if (term) |t| switch (t) { .Exited => |code| try writer.print("exited with code {}", .{code}), .Signal => |sig| try writer.print("terminated with signal {}", .{sig}), diff --git a/build.zig b/build.zig index 0363450..ab0dfc4 100644 --- a/build.zig +++ b/build.zig @@ -432,18 +432,12 @@ fn addPythonExe( ) *std.Build.Step.Compile { const exe = b.addExecutable(.{ .name = args.name, - .target = target, - .optimize = optimize, + .root_module = b.createModule(.{ + .target = target, + .optimize = optimize, + }), }); - switch (args.pyconfig.version) { - .@"3.11.13" => { - // workaround dictobject.c memcpy alignment issue - exe.root_module.sanitize_c = false; - }, - .@"3.12.11" => {}, - } - exe.root_module.addCMacro("Py_BUILD_CORE", ""); exe.root_module.addCMacro("_GNU_SOURCE", ""); switch (optimize) { @@ -488,13 +482,29 @@ fn addPythonExe( }, } - const flags_common = [_][]const u8{ + const common_flags = [_][]const u8{ "-fwrapv", "-std=c11", "-fvisibility=hidden", "-DVPATH=\"\"", }; + var flags: std.ArrayList([]const u8) = .empty; + defer flags.deinit(b.allocator); + flags.appendSlice(b.allocator, &common_flags) catch @panic("OOM"); + switch (args.pyconfig.version) { + .@"3.11.13" => { + // workaround dictobject.c memcpy alignment issue + flags.append(b.allocator, "-fno-sanitize=alignment") catch @panic("OOM"); + }, + .@"3.12.11" => { + // Fixes some null pointer related ubsan checks when building with zig 0.15.1 + flags.append(b.allocator, "-fno-delete-null-pointer-checks") catch @panic("OOM"); + // Fixes some null pointer overflow issues flagged in UBSan triggered by deepfreeze.py + flags.append(b.allocator, "-fno-sanitize=pointer-overflow") catch @panic("OOM"); + }, + } + { const AddModules = struct { step: std.Build.Step, @@ -513,7 +523,7 @@ fn addPythonExe( }; defer step.owner.allocator.free(module_compile_args); - var files: std.ArrayListUnmanaged([]const u8) = .{}; + var files: std.ArrayList([]const u8) = .{}; defer files.deinit(step.owner.allocator); var line_it = std.mem.splitScalar(u8, module_compile_args, '\n'); @@ -537,7 +547,7 @@ fn addPythonExe( self.exe.root_module.addCSourceFiles(.{ .root = self.upstream.path("."), .files = files.items, - .flags = &flags_common, + .flags = &common_flags, }); } }.make; @@ -593,44 +603,52 @@ fn addPythonExe( }, }), }, - .flags = &flags_common, + .flags = flags.items, }); exe.addCSourceFile(.{ .file = args.makesetup_out.path(b, "config.c"), - .flags = &flags_common, + .flags = flags.items, }); + var get_path_flags: std.ArrayList([]const u8) = .empty; + defer get_path_flags.deinit(b.allocator); + get_path_flags.appendSlice(b.allocator, flags.items) catch @panic("OOM"); + get_path_flags.appendSlice(b.allocator, &.{ + "-DPREFIX=\"\"", + "-DEXEC_PREFIX=\"\"", + b.fmt("-DVERSION=\"{s}\"", .{args.pyconfig.version.libName()}), + "-DPLATLIBDIR=\"lib\"", + }) catch @panic("OOM"); switch (args.stage) { .freeze_module => {}, .bootstrap, .final => exe.addCSourceFile(.{ .file = upstream.path("Modules/getpath.c"), - .flags = &(flags_common ++ [_][]const u8{ - "-DPREFIX=\"\"", - "-DEXEC_PREFIX=\"\"", - b.fmt("-DVERSION=\"{s}\"", .{args.pyconfig.version.libName()}), - "-DPLATLIBDIR=\"lib\"", - }), + .flags = get_path_flags.items, }), } switch (args.stage) { .freeze_module, .bootstrap => {}, .final => |final| { - exe.addCSourceFile(.{ .file = final.deepfreeze_c, .flags = &flags_common }); + exe.addCSourceFile(.{ .file = final.deepfreeze_c, .flags = flags.items }); }, } if (target.result.os.tag == .windows) { exe.addCSourceFile(.{ .file = upstream.path("Python/dynload_win.c"), - .flags = &flags_common, + .flags = flags.items, }); } else { + var dynload_flags: std.ArrayList([]const u8) = .empty; + defer dynload_flags.deinit(b.allocator); + dynload_flags.appendSlice(b.allocator, flags.items) catch @panic("OOM"); + dynload_flags.appendSlice(b.allocator, &.{ + "-DSOABI=\"cpython-311-x86_64-linux-gnu\"", + }) catch @panic("OOM"); exe.addCSourceFile(.{ .file = upstream.path("Python/dynload_shlib.c"), - .flags = &(flags_common ++ .{ - "-DSOABI=\"cpython-311-x86_64-linux-gnu\"", - }), + .flags = dynload_flags.items, }); } @@ -1235,7 +1253,7 @@ fn addPyconfig( }; const config_header = b.addConfigHeader(.{ - .style = .{ .autoconf = upstream.path("pyconfig.h.in") }, + .style = .{ .autoconf_undef = upstream.path("pyconfig.h.in") }, .include_path = "pyconfig.h", }, .{ .ALIGNOF_LONG = 8, diff --git a/build.zig.zon b/build.zig.zon index 2e8e99b..ba534a8 100644 --- a/build.zig.zon +++ b/build.zig.zon @@ -2,7 +2,7 @@ .name = .cpython, .fingerprint = 0x3224901d1babdd14, .version = "0.0.0", - .minimum_zig_version = "0.14.1", + .minimum_zig_version = "0.15.1", .dependencies = .{ .@"upstream_3.11.13" = .{ .url = "git+https://github.com/python/cpython#498b971ea3673012a1d4b21860b229d55fc6e575", @@ -15,12 +15,12 @@ .lazy = true, }, .zlib = .{ - .url = "https://github.com/allyourcodebase/zlib/archive/6c72830882690c1eb2567a537525c3f432c1da50.tar.gz", - .hash = "zlib-1.3.1-ZZQ7lVgMAACwO4nUUd8GLhsuQ5JQq_VAhlEiENJTUv6h", + .url = "https://github.com/allyourcodebase/zlib/archive/61e7df7e996ec5a5f13a653db3c419adb340d6ef.tar.gz", + .hash = "zlib-1.3.1-ZZQ7lbYMAAB1hTSOKSXAKAgHsfDcyWNH_37ojw5WSpgR", }, .openssl = .{ - .url = "https://github.com/allyourcodebase/openssl/archive/f348124c5382bcc377f1b3277357cbf2ed2fb8db.tar.gz", - .hash = "openssl-3.3.1-2-TC9C3Se3ZACF5WO_CjoD7Bt_X94oCsAAbbwhOp1rTZBe", + .url = "https://github.com/allyourcodebase/openssl/archive/cad7ccba47e42fa608ca655ec14ae33202df86e1.tar.gz", + .hash = "openssl-3.3.2-TC9C3Wa3ZACgB1hZbrLOQCK9XccIBaW_F3imFfIeYP06", .lazy = true, }, }, diff --git a/makesetup.zig b/makesetup.zig index 3cea0d5..96aed5a 100644 --- a/makesetup.zig +++ b/makesetup.zig @@ -7,7 +7,7 @@ pub fn main() !void { // no need to free if (all_args.len <= 1) { - try std.io.getStdErr().writer().writeAll("usage: makesetup UPSTREAM_SRC OUT_DIR SETUP_FILES...\n"); + try std.fs.File.stderr().writeAll("usage: makesetup UPSTREAM_SRC OUT_DIR SETUP_FILES...\n"); std.process.exit(0xff); } const args = all_args[1..]; @@ -36,8 +36,9 @@ pub fn main() !void { { var file = try out_dir.createFile("config.c", .{}); defer file.close(); - var bw = std.io.bufferedWriter(file.writer()); - const writer = bw.writer(); + var file_buffer: [4096]u8 = undefined; + var bw = file.writer(&file_buffer); + const writer = &bw.interface; try writer.print("/* Generated automatically from {s} by makesetup. */\n", .{config_in_path}); var lines = std.mem.splitScalar(u8, config_in, '\n'); while (lines.next()) |line| { @@ -57,14 +58,15 @@ pub fn main() !void { try writer.writeAll(line); try writer.writeByte('\n'); } - try bw.flush(); + try writer.flush(); } { var out_file = try out_dir.createFile("module-compile-args.txt", .{}); defer out_file.close(); - var bw = std.io.bufferedWriter(out_file.writer()); - const writer = bw.writer(); + var out_file_buffer: [4096]u8 = undefined; + var bw = out_file.writer(&out_file_buffer); + const writer = &bw.interface; var it = setup.modules.iterator(); while (it.next()) |entry| { @@ -79,7 +81,7 @@ pub fn main() !void { .include => |inc| try writer.print("{s}-I{s}\n", .{ prefix, inc }), }; } - try bw.flush(); + try writer.flush(); } } diff --git a/replace.zig b/replace.zig index ed1f8dd..19dd7f5 100644 --- a/replace.zig +++ b/replace.zig @@ -7,7 +7,7 @@ pub fn main() !void { // no need to free if (all_args.len <= 1) { - try std.io.getStdErr().writer().writeAll("usage: replace IN_FILE OUT_FILE NAME=VALUE...\n"); + try std.fs.File.stderr().writeAll("usage: replace IN_FILE OUT_FILE NAME=VALUE...\n"); std.process.exit(0xff); } const args = all_args[1..]; @@ -41,8 +41,9 @@ pub fn main() !void { var out_file = try std.fs.cwd().createFile(out_path, .{}); defer out_file.close(); - var bw = std.io.bufferedWriter(out_file.writer()); - const writer = bw.writer(); + var out_file_buffer: [4096]u8 = undefined; + var bw = out_file.writer(&out_file_buffer); + const writer = &bw.interface; var missing_count: usize = 0; var offset: usize = 0; @@ -65,7 +66,7 @@ pub fn main() !void { offset = end + 1; } try writer.writeAll(in[offset..]); - try bw.flush(); + try writer.flush(); if (missing_count > 0) errExit("{} missing variable(s) for template '{s}'", .{ missing_count, in_path }); var unused_count: usize = 0;