| author | |
| committer | |
| log | 4616af0ca459358ffa09ba27f9daa8527a38fd35 |
| tree | 2705847ded931e30dc924bd44acf24847743855c |
| parent | fba39ff331a84f1a32d076ccbb8b87cd02ea7121 |
| signature |
* re-introduce `std.build.Target` which is distinct from `std.Target`.
`std.build.Target` wraps `std.Target` so that it can be annotated as
"the native target" or an explicitly specified target.
* `std.Target.Os` is moved to `std.Target.Os.Tag`. The former is now a
struct which has the tag as well as version range information.
* `std.elf` gains some more ELF header constants.
* `std.Target.parse` gains the ability to parse operating system
version ranges as well as glibc version.
* Added `std.Target.isGnuLibC()`.
* self-hosted dynamic linker detection and glibc version detection.
This also adds the improved logic using `/usr/bin/env` rather than
invoking the system C compiler to find the dynamic linker when zig
is statically linked. Related: #2084
Note: this `/usr/bin/env` code is work-in-progress.
* `-target-glibc` CLI option is removed in favor of the new `-target`
syntax. Example: `-target x86_64-linux-gnu.2.27`
closes #190759 files changed, 1275 insertions(+), 933 deletions(-)
lib/std/build.zig+33-7| ... | @@ -971,9 +971,9 @@ pub const Builder = struct { | ... | @@ -971,9 +971,9 @@ pub const Builder = struct { |
| 971 | }; | 971 | }; |
| 972 | 972 | ||
| 973 | test "builder.findProgram compiles" { | 973 | test "builder.findProgram compiles" { |
| 974 | // TODO: uncomment and fix the leak | 974 | var buf: [1000]u8 = undefined; |
| 975 | // const builder = try Builder.create(std.testing.allocator, "zig", "zig-cache", "zig-cache"); | 975 | var fba = std.heap.FixedBufferAllocator.init(&buf); |
| 976 | const builder = try Builder.create(std.heap.page_allocator, "zig", "zig-cache", "zig-cache"); | 976 | const builder = try Builder.create(&fba.allocator, "zig", "zig-cache", "zig-cache"); |
| 977 | defer builder.destroy(); | 977 | defer builder.destroy(); |
| 978 | _ = builder.findProgram(&[_][]const u8{}, &[_][]const u8{}) catch null; | 978 | _ = builder.findProgram(&[_][]const u8{}, &[_][]const u8{}) catch null; |
| 979 | } | 979 | } |
| ... | @@ -981,11 +981,37 @@ test "builder.findProgram compiles" { | ... | @@ -981,11 +981,37 @@ test "builder.findProgram compiles" { |
| 981 | /// Deprecated. Use `builtin.Version`. | 981 | /// Deprecated. Use `builtin.Version`. |
| 982 | pub const Version = builtin.Version; | 982 | pub const Version = builtin.Version; |
| 983 | 983 | ||
| 984 | /// Deprecated. Use `std.Target.Cross`. | ||
| 985 | pub const CrossTarget = std.Target.Cross; | ||
| 986 | |||
| 987 | /// Deprecated. Use `std.Target`. | 984 | /// Deprecated. Use `std.Target`. |
| 988 | pub const Target = std.Target; | 985 | pub const CrossTarget = std.Target; |
| 986 | |||
| 987 | /// Wraps `std.Target` so that it can be annotated as "the native target" or an explicitly specified target. | ||
| 988 | pub const Target = union(enum) { | ||
| 989 | Native, | ||
| 990 | Cross: std.Target, | ||
| 991 | |||
| 992 | pub fn getTarget(self: Target) std.Target { | ||
| 993 | return switch (self) { | ||
| 994 | .Native => std.Target.current, | ||
| 995 | .Cross => |t| t, | ||
| 996 | }; | ||
| 997 | } | ||
| 998 | |||
| 999 | pub fn getOs(self: Target) std.Target.Os.Tag { | ||
| 1000 | return self.getTarget().os.tag; | ||
| 1001 | } | ||
| 1002 | |||
| 1003 | pub fn getCpu(self: Target) std.Target.Cpu { | ||
| 1004 | return self.getTarget().cpu; | ||
| 1005 | } | ||
| 1006 | |||
| 1007 | pub fn getAbi(self: Target) std.Target.Abi { | ||
| 1008 | return self.getTarget().abi; | ||
| 1009 | } | ||
| 1010 | |||
| 1011 | pub fn getArch(self: Target) std.Target.Cpu.Arch { | ||
| 1012 | return self.getCpu().arch; | ||
| 1013 | } | ||
| 1014 | }; | ||
| 989 | 1015 | ||
| 990 | pub const Pkg = struct { | 1016 | pub const Pkg = struct { |
| 991 | name: []const u8, | 1017 | name: []const u8, |
lib/std/build/run.zig+1-1| ... | @@ -82,7 +82,7 @@ pub const RunStep = struct { | ... | @@ -82,7 +82,7 @@ pub const RunStep = struct { |
| 82 | 82 | ||
| 83 | var key: []const u8 = undefined; | 83 | var key: []const u8 = undefined; |
| 84 | var prev_path: ?[]const u8 = undefined; | 84 | var prev_path: ?[]const u8 = undefined; |
| 85 | if (builtin.os == .windows) { | 85 | if (builtin.os.tag == .windows) { |
| 86 | key = "Path"; | 86 | key = "Path"; |
| 87 | prev_path = env_map.get(key); | 87 | prev_path = env_map.get(key); |
| 88 | if (prev_path == null) { | 88 | if (prev_path == null) { |
lib/std/builtin.zig+2-2| ... | @@ -411,7 +411,7 @@ pub const Version = struct { | ... | @@ -411,7 +411,7 @@ pub const Version = struct { |
| 411 | } | 411 | } |
| 412 | }; | 412 | }; |
| 413 | 413 | ||
| 414 | pub fn order(lhs: Version, rhs: version) std.math.Order { | 414 | pub fn order(lhs: Version, rhs: Version) std.math.Order { |
| 415 | if (lhs.major < rhs.major) return .lt; | 415 | if (lhs.major < rhs.major) return .lt; |
| 416 | if (lhs.major > rhs.major) return .gt; | 416 | if (lhs.major > rhs.major) return .gt; |
| 417 | if (lhs.minor < rhs.minor) return .lt; | 417 | if (lhs.minor < rhs.minor) return .lt; |
| ... | @@ -504,7 +504,7 @@ pub fn default_panic(msg: []const u8, error_return_trace: ?*StackTrace) noreturn | ... | @@ -504,7 +504,7 @@ pub fn default_panic(msg: []const u8, error_return_trace: ?*StackTrace) noreturn |
| 504 | root.os.panic(msg, error_return_trace); | 504 | root.os.panic(msg, error_return_trace); |
| 505 | unreachable; | 505 | unreachable; |
| 506 | } | 506 | } |
| 507 | switch (os) { | 507 | switch (os.tag) { |
| 508 | .freestanding => { | 508 | .freestanding => { |
| 509 | while (true) { | 509 | while (true) { |
| 510 | @breakpoint(); | 510 | @breakpoint(); |
lib/std/c.zig+12-13| ... | @@ -1,5 +1,5 @@ | ... | @@ -1,5 +1,5 @@ |
| 1 | const builtin = @import("builtin"); | ||
| 2 | const std = @import("std"); | 1 | const std = @import("std"); |
| 2 | const builtin = std.builtin; | ||
| 3 | const page_size = std.mem.page_size; | 3 | const page_size = std.mem.page_size; |
| 4 | 4 | ||
| 5 | pub const tokenizer = @import("c/tokenizer.zig"); | 5 | pub const tokenizer = @import("c/tokenizer.zig"); |
| ... | @@ -10,7 +10,7 @@ pub const ast = @import("c/ast.zig"); | ... | @@ -10,7 +10,7 @@ pub const ast = @import("c/ast.zig"); |
| 10 | 10 | ||
| 11 | pub usingnamespace @import("os/bits.zig"); | 11 | pub usingnamespace @import("os/bits.zig"); |
| 12 | 12 | ||
| 13 | pub usingnamespace switch (builtin.os) { | 13 | pub usingnamespace switch (std.Target.current.os.tag) { |
| 14 | .linux => @import("c/linux.zig"), | 14 | .linux => @import("c/linux.zig"), |
| 15 | .windows => @import("c/windows.zig"), | 15 | .windows => @import("c/windows.zig"), |
| 16 | .macosx, .ios, .tvos, .watchos => @import("c/darwin.zig"), | 16 | .macosx, .ios, .tvos, .watchos => @import("c/darwin.zig"), |
| ... | @@ -46,17 +46,16 @@ pub fn versionCheck(glibc_version: builtin.Version) type { | ... | @@ -46,17 +46,16 @@ pub fn versionCheck(glibc_version: builtin.Version) type { |
| 46 | return struct { | 46 | return struct { |
| 47 | pub const ok = blk: { | 47 | pub const ok = blk: { |
| 48 | if (!builtin.link_libc) break :blk false; | 48 | if (!builtin.link_libc) break :blk false; |
| 49 | switch (builtin.abi) { | 49 | if (std.Target.current.abi.isMusl()) break :blk true; |
| 50 | .musl, .musleabi, .musleabihf => break :blk true, | 50 | if (std.Target.current.isGnuLibC()) { |
| 51 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => { | 51 | const ver = std.Target.current.os.version_range.linux.glibc; |
| 52 | const ver = builtin.glibc_version orelse break :blk false; | 52 | const order = ver.order(glibc_version); |
| 53 | if (ver.major < glibc_version.major) break :blk false; | 53 | break :blk switch (order) { |
| 54 | if (ver.major > glibc_version.major) break :blk true; | 54 | .gt, .eq => true, |
| 55 | if (ver.minor < glibc_version.minor) break :blk false; | 55 | .lt => false, |
| 56 | if (ver.minor > glibc_version.minor) break :blk true; | 56 | }; |
| 57 | break :blk ver.patch >= glibc_version.patch; | 57 | } else { |
| 58 | }, | 58 | break :blk false; |
| 59 | else => break :blk false, | ||
| 60 | } | 59 | } |
| 61 | }; | 60 | }; |
| 62 | }; | 61 | }; |
lib/std/c/linux.zig+1-1| ... | @@ -94,7 +94,7 @@ pub const pthread_cond_t = extern struct { | ... | @@ -94,7 +94,7 @@ pub const pthread_cond_t = extern struct { |
| 94 | size: [__SIZEOF_PTHREAD_COND_T]u8 align(@alignOf(usize)) = [_]u8{0} ** __SIZEOF_PTHREAD_COND_T, | 94 | size: [__SIZEOF_PTHREAD_COND_T]u8 align(@alignOf(usize)) = [_]u8{0} ** __SIZEOF_PTHREAD_COND_T, |
| 95 | }; | 95 | }; |
| 96 | const __SIZEOF_PTHREAD_COND_T = 48; | 96 | const __SIZEOF_PTHREAD_COND_T = 48; |
| 97 | const __SIZEOF_PTHREAD_MUTEX_T = if (builtin.os == .fuchsia) 40 else switch (builtin.abi) { | 97 | const __SIZEOF_PTHREAD_MUTEX_T = if (builtin.os.tag == .fuchsia) 40 else switch (builtin.abi) { |
| 98 | .musl, .musleabi, .musleabihf => if (@sizeOf(usize) == 8) 40 else 24, | 98 | .musl, .musleabi, .musleabihf => if (@sizeOf(usize) == 8) 40 else 24, |
| 99 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => switch (builtin.arch) { | 99 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => switch (builtin.arch) { |
| 100 | .aarch64 => 48, | 100 | .aarch64 => 48, |
lib/std/child_process.zig+13-13| ... | @@ -17,9 +17,9 @@ const TailQueue = std.TailQueue; | ... | @@ -17,9 +17,9 @@ const TailQueue = std.TailQueue; |
| 17 | const maxInt = std.math.maxInt; | 17 | const maxInt = std.math.maxInt; |
| 18 | 18 | ||
| 19 | pub const ChildProcess = struct { | 19 | pub const ChildProcess = struct { |
| 20 | pid: if (builtin.os == .windows) void else i32, | 20 | pid: if (builtin.os.tag == .windows) void else i32, |
| 21 | handle: if (builtin.os == .windows) windows.HANDLE else void, | 21 | handle: if (builtin.os.tag == .windows) windows.HANDLE else void, |
| 22 | thread_handle: if (builtin.os == .windows) windows.HANDLE else void, | 22 | thread_handle: if (builtin.os.tag == .windows) windows.HANDLE else void, |
| 23 | 23 | ||
| 24 | allocator: *mem.Allocator, | 24 | allocator: *mem.Allocator, |
| 25 | 25 | ||
| ... | @@ -39,15 +39,15 @@ pub const ChildProcess = struct { | ... | @@ -39,15 +39,15 @@ pub const ChildProcess = struct { |
| 39 | stderr_behavior: StdIo, | 39 | stderr_behavior: StdIo, |
| 40 | 40 | ||
| 41 | /// Set to change the user id when spawning the child process. | 41 | /// Set to change the user id when spawning the child process. |
| 42 | uid: if (builtin.os == .windows) void else ?u32, | 42 | uid: if (builtin.os.tag == .windows) void else ?u32, |
| 43 | 43 | ||
| 44 | /// Set to change the group id when spawning the child process. | 44 | /// Set to change the group id when spawning the child process. |
| 45 | gid: if (builtin.os == .windows) void else ?u32, | 45 | gid: if (builtin.os.tag == .windows) void else ?u32, |
| 46 | 46 | ||
| 47 | /// Set to change the current working directory when spawning the child process. | 47 | /// Set to change the current working directory when spawning the child process. |
| 48 | cwd: ?[]const u8, | 48 | cwd: ?[]const u8, |
| 49 | 49 | ||
| 50 | err_pipe: if (builtin.os == .windows) void else [2]os.fd_t, | 50 | err_pipe: if (builtin.os.tag == .windows) void else [2]os.fd_t, |
| 51 | 51 | ||
| 52 | expand_arg0: Arg0Expand, | 52 | expand_arg0: Arg0Expand, |
| 53 | 53 | ||
| ... | @@ -96,8 +96,8 @@ pub const ChildProcess = struct { | ... | @@ -96,8 +96,8 @@ pub const ChildProcess = struct { |
| 96 | .term = null, | 96 | .term = null, |
| 97 | .env_map = null, | 97 | .env_map = null, |
| 98 | .cwd = null, | 98 | .cwd = null, |
| 99 | .uid = if (builtin.os == .windows) {} else null, | 99 | .uid = if (builtin.os.tag == .windows) {} else null, |
| 100 | .gid = if (builtin.os == .windows) {} else null, | 100 | .gid = if (builtin.os.tag == .windows) {} else null, |
| 101 | .stdin = null, | 101 | .stdin = null, |
| 102 | .stdout = null, | 102 | .stdout = null, |
| 103 | .stderr = null, | 103 | .stderr = null, |
| ... | @@ -118,7 +118,7 @@ pub const ChildProcess = struct { | ... | @@ -118,7 +118,7 @@ pub const ChildProcess = struct { |
| 118 | 118 | ||
| 119 | /// On success must call `kill` or `wait`. | 119 | /// On success must call `kill` or `wait`. |
| 120 | pub fn spawn(self: *ChildProcess) SpawnError!void { | 120 | pub fn spawn(self: *ChildProcess) SpawnError!void { |
| 121 | if (builtin.os == .windows) { | 121 | if (builtin.os.tag == .windows) { |
| 122 | return self.spawnWindows(); | 122 | return self.spawnWindows(); |
| 123 | } else { | 123 | } else { |
| 124 | return self.spawnPosix(); | 124 | return self.spawnPosix(); |
| ... | @@ -132,7 +132,7 @@ pub const ChildProcess = struct { | ... | @@ -132,7 +132,7 @@ pub const ChildProcess = struct { |
| 132 | 132 | ||
| 133 | /// Forcibly terminates child process and then cleans up all resources. | 133 | /// Forcibly terminates child process and then cleans up all resources. |
| 134 | pub fn kill(self: *ChildProcess) !Term { | 134 | pub fn kill(self: *ChildProcess) !Term { |
| 135 | if (builtin.os == .windows) { | 135 | if (builtin.os.tag == .windows) { |
| 136 | return self.killWindows(1); | 136 | return self.killWindows(1); |
| 137 | } else { | 137 | } else { |
| 138 | return self.killPosix(); | 138 | return self.killPosix(); |
| ... | @@ -162,7 +162,7 @@ pub const ChildProcess = struct { | ... | @@ -162,7 +162,7 @@ pub const ChildProcess = struct { |
| 162 | 162 | ||
| 163 | /// Blocks until child process terminates and then cleans up all resources. | 163 | /// Blocks until child process terminates and then cleans up all resources. |
| 164 | pub fn wait(self: *ChildProcess) !Term { | 164 | pub fn wait(self: *ChildProcess) !Term { |
| 165 | if (builtin.os == .windows) { | 165 | if (builtin.os.tag == .windows) { |
| 166 | return self.waitWindows(); | 166 | return self.waitWindows(); |
| 167 | } else { | 167 | } else { |
| 168 | return self.waitPosix(); | 168 | return self.waitPosix(); |
| ... | @@ -307,7 +307,7 @@ pub const ChildProcess = struct { | ... | @@ -307,7 +307,7 @@ pub const ChildProcess = struct { |
| 307 | fn cleanupAfterWait(self: *ChildProcess, status: u32) !Term { | 307 | fn cleanupAfterWait(self: *ChildProcess, status: u32) !Term { |
| 308 | defer destroyPipe(self.err_pipe); | 308 | defer destroyPipe(self.err_pipe); |
| 309 | 309 | ||
| 310 | if (builtin.os == .linux) { | 310 | if (builtin.os.tag == .linux) { |
| 311 | var fd = [1]std.os.pollfd{std.os.pollfd{ | 311 | var fd = [1]std.os.pollfd{std.os.pollfd{ |
| 312 | .fd = self.err_pipe[0], | 312 | .fd = self.err_pipe[0], |
| 313 | .events = std.os.POLLIN, | 313 | .events = std.os.POLLIN, |
| ... | @@ -402,7 +402,7 @@ pub const ChildProcess = struct { | ... | @@ -402,7 +402,7 @@ pub const ChildProcess = struct { |
| 402 | // This pipe is used to communicate errors between the time of fork | 402 | // This pipe is used to communicate errors between the time of fork |
| 403 | // and execve from the child process to the parent process. | 403 | // and execve from the child process to the parent process. |
| 404 | const err_pipe = blk: { | 404 | const err_pipe = blk: { |
| 405 | if (builtin.os == .linux) { | 405 | if (builtin.os.tag == .linux) { |
| 406 | const fd = try os.eventfd(0, 0); | 406 | const fd = try os.eventfd(0, 0); |
| 407 | // There's no distinction between the readable and the writeable | 407 | // There's no distinction between the readable and the writeable |
| 408 | // end with eventfd | 408 | // end with eventfd |
lib/std/cstr.zig+2-2| ... | @@ -4,8 +4,8 @@ const debug = std.debug; | ... | @@ -4,8 +4,8 @@ const debug = std.debug; |
| 4 | const mem = std.mem; | 4 | const mem = std.mem; |
| 5 | const testing = std.testing; | 5 | const testing = std.testing; |
| 6 | 6 | ||
| 7 | pub const line_sep = switch (builtin.os) { | 7 | pub const line_sep = switch (builtin.os.tag) { |
| 8 | builtin.Os.windows => "\r\n", | 8 | .windows => "\r\n", |
| 9 | else => "\n", | 9 | else => "\n", |
| 10 | }; | 10 | }; |
| 11 | 11 |
lib/std/debug.zig+12-12| ... | @@ -1,4 +1,5 @@ | ... | @@ -1,4 +1,5 @@ |
| 1 | const std = @import("std.zig"); | 1 | const std = @import("std.zig"); |
| 2 | const builtin = std.builtin; | ||
| 2 | const math = std.math; | 3 | const math = std.math; |
| 3 | const mem = std.mem; | 4 | const mem = std.mem; |
| 4 | const io = std.io; | 5 | const io = std.io; |
| ... | @@ -11,7 +12,6 @@ const macho = std.macho; | ... | @@ -11,7 +12,6 @@ const macho = std.macho; |
| 11 | const coff = std.coff; | 12 | const coff = std.coff; |
| 12 | const pdb = std.pdb; | 13 | const pdb = std.pdb; |
| 13 | const ArrayList = std.ArrayList; | 14 | const ArrayList = std.ArrayList; |
| 14 | const builtin = @import("builtin"); | ||
| 15 | const root = @import("root"); | 15 | const root = @import("root"); |
| 16 | const maxInt = std.math.maxInt; | 16 | const maxInt = std.math.maxInt; |
| 17 | const File = std.fs.File; | 17 | const File = std.fs.File; |
| ... | @@ -101,7 +101,7 @@ pub fn detectTTYConfig() TTY.Config { | ... | @@ -101,7 +101,7 @@ pub fn detectTTYConfig() TTY.Config { |
| 101 | } else |_| { | 101 | } else |_| { |
| 102 | if (stderr_file.supportsAnsiEscapeCodes()) { | 102 | if (stderr_file.supportsAnsiEscapeCodes()) { |
| 103 | return .escape_codes; | 103 | return .escape_codes; |
| 104 | } else if (builtin.os == .windows and stderr_file.isTty()) { | 104 | } else if (builtin.os.tag == .windows and stderr_file.isTty()) { |
| 105 | return .windows_api; | 105 | return .windows_api; |
| 106 | } else { | 106 | } else { |
| 107 | return .no_color; | 107 | return .no_color; |
| ... | @@ -155,7 +155,7 @@ pub fn dumpStackTraceFromBase(bp: usize, ip: usize) void { | ... | @@ -155,7 +155,7 @@ pub fn dumpStackTraceFromBase(bp: usize, ip: usize) void { |
| 155 | /// chopping off the irrelevant frames and shifting so that the returned addresses pointer | 155 | /// chopping off the irrelevant frames and shifting so that the returned addresses pointer |
| 156 | /// equals the passed in addresses pointer. | 156 | /// equals the passed in addresses pointer. |
| 157 | pub fn captureStackTrace(first_address: ?usize, stack_trace: *builtin.StackTrace) void { | 157 | pub fn captureStackTrace(first_address: ?usize, stack_trace: *builtin.StackTrace) void { |
| 158 | if (builtin.os == .windows) { | 158 | if (builtin.os.tag == .windows) { |
| 159 | const addrs = stack_trace.instruction_addresses; | 159 | const addrs = stack_trace.instruction_addresses; |
| 160 | const u32_addrs_len = @intCast(u32, addrs.len); | 160 | const u32_addrs_len = @intCast(u32, addrs.len); |
| 161 | const first_addr = first_address orelse { | 161 | const first_addr = first_address orelse { |
| ... | @@ -231,7 +231,7 @@ pub fn assert(ok: bool) void { | ... | @@ -231,7 +231,7 @@ pub fn assert(ok: bool) void { |
| 231 | pub fn panic(comptime format: []const u8, args: var) noreturn { | 231 | pub fn panic(comptime format: []const u8, args: var) noreturn { |
| 232 | @setCold(true); | 232 | @setCold(true); |
| 233 | // TODO: remove conditional once wasi / LLVM defines __builtin_return_address | 233 | // TODO: remove conditional once wasi / LLVM defines __builtin_return_address |
| 234 | const first_trace_addr = if (builtin.os == .wasi) null else @returnAddress(); | 234 | const first_trace_addr = if (builtin.os.tag == .wasi) null else @returnAddress(); |
| 235 | panicExtra(null, first_trace_addr, format, args); | 235 | panicExtra(null, first_trace_addr, format, args); |
| 236 | } | 236 | } |
| 237 | 237 | ||
| ... | @@ -361,7 +361,7 @@ pub fn writeCurrentStackTrace( | ... | @@ -361,7 +361,7 @@ pub fn writeCurrentStackTrace( |
| 361 | tty_config: TTY.Config, | 361 | tty_config: TTY.Config, |
| 362 | start_addr: ?usize, | 362 | start_addr: ?usize, |
| 363 | ) !void { | 363 | ) !void { |
| 364 | if (builtin.os == .windows) { | 364 | if (builtin.os.tag == .windows) { |
| 365 | return writeCurrentStackTraceWindows(out_stream, debug_info, tty_config, start_addr); | 365 | return writeCurrentStackTraceWindows(out_stream, debug_info, tty_config, start_addr); |
| 366 | } | 366 | } |
| 367 | var it = StackIterator.init(start_addr, null); | 367 | var it = StackIterator.init(start_addr, null); |
| ... | @@ -418,7 +418,7 @@ pub const TTY = struct { | ... | @@ -418,7 +418,7 @@ pub const TTY = struct { |
| 418 | .Dim => noasync out_stream.write(DIM) catch return, | 418 | .Dim => noasync out_stream.write(DIM) catch return, |
| 419 | .Reset => noasync out_stream.write(RESET) catch return, | 419 | .Reset => noasync out_stream.write(RESET) catch return, |
| 420 | }, | 420 | }, |
| 421 | .windows_api => if (builtin.os == .windows) { | 421 | .windows_api => if (builtin.os.tag == .windows) { |
| 422 | const S = struct { | 422 | const S = struct { |
| 423 | var attrs: windows.WORD = undefined; | 423 | var attrs: windows.WORD = undefined; |
| 424 | var init_attrs = false; | 424 | var init_attrs = false; |
| ... | @@ -617,7 +617,7 @@ pub fn openSelfDebugInfo(allocator: *mem.Allocator) anyerror!DebugInfo { | ... | @@ -617,7 +617,7 @@ pub fn openSelfDebugInfo(allocator: *mem.Allocator) anyerror!DebugInfo { |
| 617 | if (@hasDecl(root, "os") and @hasDecl(root.os, "debug") and @hasDecl(root.os.debug, "openSelfDebugInfo")) { | 617 | if (@hasDecl(root, "os") and @hasDecl(root.os, "debug") and @hasDecl(root.os.debug, "openSelfDebugInfo")) { |
| 618 | return noasync root.os.debug.openSelfDebugInfo(allocator); | 618 | return noasync root.os.debug.openSelfDebugInfo(allocator); |
| 619 | } | 619 | } |
| 620 | switch (builtin.os) { | 620 | switch (builtin.os.tag) { |
| 621 | .linux, | 621 | .linux, |
| 622 | .freebsd, | 622 | .freebsd, |
| 623 | .macosx, | 623 | .macosx, |
| ... | @@ -1019,7 +1019,7 @@ pub const DebugInfo = struct { | ... | @@ -1019,7 +1019,7 @@ pub const DebugInfo = struct { |
| 1019 | pub fn getModuleForAddress(self: *DebugInfo, address: usize) !*ModuleDebugInfo { | 1019 | pub fn getModuleForAddress(self: *DebugInfo, address: usize) !*ModuleDebugInfo { |
| 1020 | if (comptime std.Target.current.isDarwin()) | 1020 | if (comptime std.Target.current.isDarwin()) |
| 1021 | return self.lookupModuleDyld(address) | 1021 | return self.lookupModuleDyld(address) |
| 1022 | else if (builtin.os == .windows) | 1022 | else if (builtin.os.tag == .windows) |
| 1023 | return self.lookupModuleWin32(address) | 1023 | return self.lookupModuleWin32(address) |
| 1024 | else | 1024 | else |
| 1025 | return self.lookupModuleDl(address); | 1025 | return self.lookupModuleDl(address); |
| ... | @@ -1242,7 +1242,7 @@ const SymbolInfo = struct { | ... | @@ -1242,7 +1242,7 @@ const SymbolInfo = struct { |
| 1242 | } | 1242 | } |
| 1243 | }; | 1243 | }; |
| 1244 | 1244 | ||
| 1245 | pub const ModuleDebugInfo = switch (builtin.os) { | 1245 | pub const ModuleDebugInfo = switch (builtin.os.tag) { |
| 1246 | .macosx, .ios, .watchos, .tvos => struct { | 1246 | .macosx, .ios, .watchos, .tvos => struct { |
| 1247 | base_address: usize, | 1247 | base_address: usize, |
| 1248 | mapped_memory: []const u8, | 1248 | mapped_memory: []const u8, |
| ... | @@ -1602,7 +1602,7 @@ fn getDebugInfoAllocator() *mem.Allocator { | ... | @@ -1602,7 +1602,7 @@ fn getDebugInfoAllocator() *mem.Allocator { |
| 1602 | } | 1602 | } |
| 1603 | 1603 | ||
| 1604 | /// Whether or not the current target can print useful debug information when a segfault occurs. | 1604 | /// Whether or not the current target can print useful debug information when a segfault occurs. |
| 1605 | pub const have_segfault_handling_support = builtin.os == .linux or builtin.os == .windows; | 1605 | pub const have_segfault_handling_support = builtin.os.tag == .linux or builtin.os.tag == .windows; |
| 1606 | pub const enable_segfault_handler: bool = if (@hasDecl(root, "enable_segfault_handler")) | 1606 | pub const enable_segfault_handler: bool = if (@hasDecl(root, "enable_segfault_handler")) |
| 1607 | root.enable_segfault_handler | 1607 | root.enable_segfault_handler |
| 1608 | else | 1608 | else |
| ... | @@ -1621,7 +1621,7 @@ pub fn attachSegfaultHandler() void { | ... | @@ -1621,7 +1621,7 @@ pub fn attachSegfaultHandler() void { |
| 1621 | if (!have_segfault_handling_support) { | 1621 | if (!have_segfault_handling_support) { |
| 1622 | @compileError("segfault handler not supported for this target"); | 1622 | @compileError("segfault handler not supported for this target"); |
| 1623 | } | 1623 | } |
| 1624 | if (builtin.os == .windows) { | 1624 | if (builtin.os.tag == .windows) { |
| 1625 | windows_segfault_handle = windows.kernel32.AddVectoredExceptionHandler(0, handleSegfaultWindows); | 1625 | windows_segfault_handle = windows.kernel32.AddVectoredExceptionHandler(0, handleSegfaultWindows); |
| 1626 | return; | 1626 | return; |
| 1627 | } | 1627 | } |
| ... | @@ -1637,7 +1637,7 @@ pub fn attachSegfaultHandler() void { | ... | @@ -1637,7 +1637,7 @@ pub fn attachSegfaultHandler() void { |
| 1637 | } | 1637 | } |
| 1638 | 1638 | ||
| 1639 | fn resetSegfaultHandler() void { | 1639 | fn resetSegfaultHandler() void { |
| 1640 | if (builtin.os == .windows) { | 1640 | if (builtin.os.tag == .windows) { |
| 1641 | if (windows_segfault_handle) |handle| { | 1641 | if (windows_segfault_handle) |handle| { |
| 1642 | assert(windows.kernel32.RemoveVectoredExceptionHandler(handle) != 0); | 1642 | assert(windows.kernel32.RemoveVectoredExceptionHandler(handle) != 0); |
| 1643 | windows_segfault_handle = null; | 1643 | windows_segfault_handle = null; |
lib/std/dynamic_library.zig+2-2| ... | @@ -11,7 +11,7 @@ const system = std.os.system; | ... | @@ -11,7 +11,7 @@ const system = std.os.system; |
| 11 | const maxInt = std.math.maxInt; | 11 | const maxInt = std.math.maxInt; |
| 12 | const max = std.math.max; | 12 | const max = std.math.max; |
| 13 | 13 | ||
| 14 | pub const DynLib = switch (builtin.os) { | 14 | pub const DynLib = switch (builtin.os.tag) { |
| 15 | .linux => if (builtin.link_libc) DlDynlib else ElfDynLib, | 15 | .linux => if (builtin.link_libc) DlDynlib else ElfDynLib, |
| 16 | .windows => WindowsDynLib, | 16 | .windows => WindowsDynLib, |
| 17 | .macosx, .tvos, .watchos, .ios, .freebsd => DlDynlib, | 17 | .macosx, .tvos, .watchos, .ios, .freebsd => DlDynlib, |
| ... | @@ -390,7 +390,7 @@ pub const DlDynlib = struct { | ... | @@ -390,7 +390,7 @@ pub const DlDynlib = struct { |
| 390 | }; | 390 | }; |
| 391 | 391 | ||
| 392 | test "dynamic_library" { | 392 | test "dynamic_library" { |
| 393 | const libname = switch (builtin.os) { | 393 | const libname = switch (builtin.os.tag) { |
| 394 | .linux, .freebsd => "invalid_so.so", | 394 | .linux, .freebsd => "invalid_so.so", |
| 395 | .windows => "invalid_dll.dll", | 395 | .windows => "invalid_dll.dll", |
| 396 | .macosx, .tvos, .watchos, .ios => "invalid_dylib.dylib", | 396 | .macosx, .tvos, .watchos, .ios => "invalid_dylib.dylib", |
lib/std/elf.zig+15-10| ... | @@ -349,16 +349,6 @@ pub const Elf = struct { | ... | @@ -349,16 +349,6 @@ pub const Elf = struct { |
| 349 | program_headers: []ProgramHeader, | 349 | program_headers: []ProgramHeader, |
| 350 | allocator: *mem.Allocator, | 350 | allocator: *mem.Allocator, |
| 351 | 351 | ||
| 352 | /// Call close when done. | ||
| 353 | pub fn openPath(allocator: *mem.Allocator, path: []const u8) !Elf { | ||
| 354 | @compileError("TODO implement"); | ||
| 355 | } | ||
| 356 | |||
| 357 | /// Call close when done. | ||
| 358 | pub fn openFile(allocator: *mem.Allocator, file: File) !Elf { | ||
| 359 | @compileError("TODO implement"); | ||
| 360 | } | ||
| 361 | |||
| 362 | pub fn openStream( | 352 | pub fn openStream( |
| 363 | allocator: *mem.Allocator, | 353 | allocator: *mem.Allocator, |
| 364 | seekable_stream: *io.SeekableStream(anyerror, anyerror), | 354 | seekable_stream: *io.SeekableStream(anyerror, anyerror), |
| ... | @@ -554,6 +544,21 @@ pub const Elf = struct { | ... | @@ -554,6 +544,21 @@ pub const Elf = struct { |
| 554 | }; | 544 | }; |
| 555 | 545 | ||
| 556 | pub const EI_NIDENT = 16; | 546 | pub const EI_NIDENT = 16; |
| 547 | |||
| 548 | pub const EI_CLASS = 4; | ||
| 549 | pub const ELFCLASSNONE = 0; | ||
| 550 | pub const ELFCLASS32 = 1; | ||
| 551 | pub const ELFCLASS64 = 2; | ||
| 552 | pub const ELFCLASSNUM = 3; | ||
| 553 | |||
| 554 | pub const EI_DATA = 5; | ||
| 555 | pub const ELFDATANONE = 0; | ||
| 556 | pub const ELFDATA2LSB = 1; | ||
| 557 | pub const ELFDATA2MSB = 2; | ||
| 558 | pub const ELFDATANUM = 3; | ||
| 559 | |||
| 560 | pub const EI_VERSION = 6; | ||
| 561 | |||
| 557 | pub const Elf32_Half = u16; | 562 | pub const Elf32_Half = u16; |
| 558 | pub const Elf64_Half = u16; | 563 | pub const Elf64_Half = u16; |
| 559 | pub const Elf32_Word = u32; | 564 | pub const Elf32_Word = u32; |
lib/std/event/channel.zig+1-1| ... | @@ -273,7 +273,7 @@ test "std.event.Channel" { | ... | @@ -273,7 +273,7 @@ test "std.event.Channel" { |
| 273 | if (builtin.single_threaded) return error.SkipZigTest; | 273 | if (builtin.single_threaded) return error.SkipZigTest; |
| 274 | 274 | ||
| 275 | // https://github.com/ziglang/zig/issues/3251 | 275 | // https://github.com/ziglang/zig/issues/3251 |
| 276 | if (builtin.os == .freebsd) return error.SkipZigTest; | 276 | if (builtin.os.tag == .freebsd) return error.SkipZigTest; |
| 277 | 277 | ||
| 278 | var channel: Channel(i32) = undefined; | 278 | var channel: Channel(i32) = undefined; |
| 279 | channel.init(&[0]i32{}); | 279 | channel.init(&[0]i32{}); |
lib/std/event/future.zig+1-1| ... | @@ -86,7 +86,7 @@ test "std.event.Future" { | ... | @@ -86,7 +86,7 @@ test "std.event.Future" { |
| 86 | // https://github.com/ziglang/zig/issues/1908 | 86 | // https://github.com/ziglang/zig/issues/1908 |
| 87 | if (builtin.single_threaded) return error.SkipZigTest; | 87 | if (builtin.single_threaded) return error.SkipZigTest; |
| 88 | // https://github.com/ziglang/zig/issues/3251 | 88 | // https://github.com/ziglang/zig/issues/3251 |
| 89 | if (builtin.os == .freebsd) return error.SkipZigTest; | 89 | if (builtin.os.tag == .freebsd) return error.SkipZigTest; |
| 90 | // TODO provide a way to run tests in evented I/O mode | 90 | // TODO provide a way to run tests in evented I/O mode |
| 91 | if (!std.io.is_async) return error.SkipZigTest; | 91 | if (!std.io.is_async) return error.SkipZigTest; |
| 92 | 92 |
lib/std/event/lock.zig+1-1| ... | @@ -123,7 +123,7 @@ test "std.event.Lock" { | ... | @@ -123,7 +123,7 @@ test "std.event.Lock" { |
| 123 | if (builtin.single_threaded) return error.SkipZigTest; | 123 | if (builtin.single_threaded) return error.SkipZigTest; |
| 124 | 124 | ||
| 125 | // TODO https://github.com/ziglang/zig/issues/3251 | 125 | // TODO https://github.com/ziglang/zig/issues/3251 |
| 126 | if (builtin.os == .freebsd) return error.SkipZigTest; | 126 | if (builtin.os.tag == .freebsd) return error.SkipZigTest; |
| 127 | 127 | ||
| 128 | var lock = Lock.init(); | 128 | var lock = Lock.init(); |
| 129 | defer lock.deinit(); | 129 | defer lock.deinit(); |
lib/std/event/loop.zig+13-13| ... | @@ -34,7 +34,7 @@ pub const Loop = struct { | ... | @@ -34,7 +34,7 @@ pub const Loop = struct { |
| 34 | handle: anyframe, | 34 | handle: anyframe, |
| 35 | overlapped: Overlapped, | 35 | overlapped: Overlapped, |
| 36 | 36 | ||
| 37 | pub const overlapped_init = switch (builtin.os) { | 37 | pub const overlapped_init = switch (builtin.os.tag) { |
| 38 | .windows => windows.OVERLAPPED{ | 38 | .windows => windows.OVERLAPPED{ |
| 39 | .Internal = 0, | 39 | .Internal = 0, |
| 40 | .InternalHigh = 0, | 40 | .InternalHigh = 0, |
| ... | @@ -52,7 +52,7 @@ pub const Loop = struct { | ... | @@ -52,7 +52,7 @@ pub const Loop = struct { |
| 52 | EventFd, | 52 | EventFd, |
| 53 | }; | 53 | }; |
| 54 | 54 | ||
| 55 | pub const EventFd = switch (builtin.os) { | 55 | pub const EventFd = switch (builtin.os.tag) { |
| 56 | .macosx, .freebsd, .netbsd, .dragonfly => KEventFd, | 56 | .macosx, .freebsd, .netbsd, .dragonfly => KEventFd, |
| 57 | .linux => struct { | 57 | .linux => struct { |
| 58 | base: ResumeNode, | 58 | base: ResumeNode, |
| ... | @@ -71,7 +71,7 @@ pub const Loop = struct { | ... | @@ -71,7 +71,7 @@ pub const Loop = struct { |
| 71 | kevent: os.Kevent, | 71 | kevent: os.Kevent, |
| 72 | }; | 72 | }; |
| 73 | 73 | ||
| 74 | pub const Basic = switch (builtin.os) { | 74 | pub const Basic = switch (builtin.os.tag) { |
| 75 | .macosx, .freebsd, .netbsd, .dragonfly => KEventBasic, | 75 | .macosx, .freebsd, .netbsd, .dragonfly => KEventBasic, |
| 76 | .linux => struct { | 76 | .linux => struct { |
| 77 | base: ResumeNode, | 77 | base: ResumeNode, |
| ... | @@ -173,7 +173,7 @@ pub const Loop = struct { | ... | @@ -173,7 +173,7 @@ pub const Loop = struct { |
| 173 | const wakeup_bytes = [_]u8{0x1} ** 8; | 173 | const wakeup_bytes = [_]u8{0x1} ** 8; |
| 174 | 174 | ||
| 175 | fn initOsData(self: *Loop, extra_thread_count: usize) InitOsDataError!void { | 175 | fn initOsData(self: *Loop, extra_thread_count: usize) InitOsDataError!void { |
| 176 | switch (builtin.os) { | 176 | switch (builtin.os.tag) { |
| 177 | .linux => { | 177 | .linux => { |
| 178 | self.os_data.fs_queue = std.atomic.Queue(Request).init(); | 178 | self.os_data.fs_queue = std.atomic.Queue(Request).init(); |
| 179 | self.os_data.fs_queue_item = 0; | 179 | self.os_data.fs_queue_item = 0; |
| ... | @@ -404,7 +404,7 @@ pub const Loop = struct { | ... | @@ -404,7 +404,7 @@ pub const Loop = struct { |
| 404 | } | 404 | } |
| 405 | 405 | ||
| 406 | fn deinitOsData(self: *Loop) void { | 406 | fn deinitOsData(self: *Loop) void { |
| 407 | switch (builtin.os) { | 407 | switch (builtin.os.tag) { |
| 408 | .linux => { | 408 | .linux => { |
| 409 | noasync os.close(self.os_data.final_eventfd); | 409 | noasync os.close(self.os_data.final_eventfd); |
| 410 | while (self.available_eventfd_resume_nodes.pop()) |node| noasync os.close(node.data.eventfd); | 410 | while (self.available_eventfd_resume_nodes.pop()) |node| noasync os.close(node.data.eventfd); |
| ... | @@ -568,7 +568,7 @@ pub const Loop = struct { | ... | @@ -568,7 +568,7 @@ pub const Loop = struct { |
| 568 | }; | 568 | }; |
| 569 | const eventfd_node = &resume_stack_node.data; | 569 | const eventfd_node = &resume_stack_node.data; |
| 570 | eventfd_node.base.handle = next_tick_node.data; | 570 | eventfd_node.base.handle = next_tick_node.data; |
| 571 | switch (builtin.os) { | 571 | switch (builtin.os.tag) { |
| 572 | .macosx, .freebsd, .netbsd, .dragonfly => { | 572 | .macosx, .freebsd, .netbsd, .dragonfly => { |
| 573 | const kevent_array = @as(*const [1]os.Kevent, &eventfd_node.kevent); | 573 | const kevent_array = @as(*const [1]os.Kevent, &eventfd_node.kevent); |
| 574 | const empty_kevs = &[0]os.Kevent{}; | 574 | const empty_kevs = &[0]os.Kevent{}; |
| ... | @@ -628,7 +628,7 @@ pub const Loop = struct { | ... | @@ -628,7 +628,7 @@ pub const Loop = struct { |
| 628 | 628 | ||
| 629 | self.workerRun(); | 629 | self.workerRun(); |
| 630 | 630 | ||
| 631 | switch (builtin.os) { | 631 | switch (builtin.os.tag) { |
| 632 | .linux, | 632 | .linux, |
| 633 | .macosx, | 633 | .macosx, |
| 634 | .freebsd, | 634 | .freebsd, |
| ... | @@ -678,7 +678,7 @@ pub const Loop = struct { | ... | @@ -678,7 +678,7 @@ pub const Loop = struct { |
| 678 | const prev = @atomicRmw(usize, &self.pending_event_count, AtomicRmwOp.Sub, 1, AtomicOrder.SeqCst); | 678 | const prev = @atomicRmw(usize, &self.pending_event_count, AtomicRmwOp.Sub, 1, AtomicOrder.SeqCst); |
| 679 | if (prev == 1) { | 679 | if (prev == 1) { |
| 680 | // cause all the threads to stop | 680 | // cause all the threads to stop |
| 681 | switch (builtin.os) { | 681 | switch (builtin.os.tag) { |
| 682 | .linux => { | 682 | .linux => { |
| 683 | self.posixFsRequest(&self.os_data.fs_end_request); | 683 | self.posixFsRequest(&self.os_data.fs_end_request); |
| 684 | // writing 8 bytes to an eventfd cannot fail | 684 | // writing 8 bytes to an eventfd cannot fail |
| ... | @@ -902,7 +902,7 @@ pub const Loop = struct { | ... | @@ -902,7 +902,7 @@ pub const Loop = struct { |
| 902 | self.finishOneEvent(); | 902 | self.finishOneEvent(); |
| 903 | } | 903 | } |
| 904 | 904 | ||
| 905 | switch (builtin.os) { | 905 | switch (builtin.os.tag) { |
| 906 | .linux => { | 906 | .linux => { |
| 907 | // only process 1 event so we don't steal from other threads | 907 | // only process 1 event so we don't steal from other threads |
| 908 | var events: [1]os.linux.epoll_event = undefined; | 908 | var events: [1]os.linux.epoll_event = undefined; |
| ... | @@ -989,7 +989,7 @@ pub const Loop = struct { | ... | @@ -989,7 +989,7 @@ pub const Loop = struct { |
| 989 | fn posixFsRequest(self: *Loop, request_node: *Request.Node) void { | 989 | fn posixFsRequest(self: *Loop, request_node: *Request.Node) void { |
| 990 | self.beginOneEvent(); // finished in posixFsRun after processing the msg | 990 | self.beginOneEvent(); // finished in posixFsRun after processing the msg |
| 991 | self.os_data.fs_queue.put(request_node); | 991 | self.os_data.fs_queue.put(request_node); |
| 992 | switch (builtin.os) { | 992 | switch (builtin.os.tag) { |
| 993 | .macosx, .freebsd, .netbsd, .dragonfly => { | 993 | .macosx, .freebsd, .netbsd, .dragonfly => { |
| 994 | const fs_kevs = @as(*const [1]os.Kevent, &self.os_data.fs_kevent_wake); | 994 | const fs_kevs = @as(*const [1]os.Kevent, &self.os_data.fs_kevent_wake); |
| 995 | const empty_kevs = &[0]os.Kevent{}; | 995 | const empty_kevs = &[0]os.Kevent{}; |
| ... | @@ -1018,7 +1018,7 @@ pub const Loop = struct { | ... | @@ -1018,7 +1018,7 @@ pub const Loop = struct { |
| 1018 | // https://github.com/ziglang/zig/issues/3157 | 1018 | // https://github.com/ziglang/zig/issues/3157 |
| 1019 | fn posixFsRun(self: *Loop) void { | 1019 | fn posixFsRun(self: *Loop) void { |
| 1020 | while (true) { | 1020 | while (true) { |
| 1021 | if (builtin.os == .linux) { | 1021 | if (builtin.os.tag == .linux) { |
| 1022 | @atomicStore(i32, &self.os_data.fs_queue_item, 0, .SeqCst); | 1022 | @atomicStore(i32, &self.os_data.fs_queue_item, 0, .SeqCst); |
| 1023 | } | 1023 | } |
| 1024 | while (self.os_data.fs_queue.get()) |node| { | 1024 | while (self.os_data.fs_queue.get()) |node| { |
| ... | @@ -1053,7 +1053,7 @@ pub const Loop = struct { | ... | @@ -1053,7 +1053,7 @@ pub const Loop = struct { |
| 1053 | } | 1053 | } |
| 1054 | self.finishOneEvent(); | 1054 | self.finishOneEvent(); |
| 1055 | } | 1055 | } |
| 1056 | switch (builtin.os) { | 1056 | switch (builtin.os.tag) { |
| 1057 | .linux => { | 1057 | .linux => { |
| 1058 | const rc = os.linux.futex_wait(&self.os_data.fs_queue_item, os.linux.FUTEX_WAIT, 0, null); | 1058 | const rc = os.linux.futex_wait(&self.os_data.fs_queue_item, os.linux.FUTEX_WAIT, 0, null); |
| 1059 | switch (os.linux.getErrno(rc)) { | 1059 | switch (os.linux.getErrno(rc)) { |
| ... | @@ -1071,7 +1071,7 @@ pub const Loop = struct { | ... | @@ -1071,7 +1071,7 @@ pub const Loop = struct { |
| 1071 | } | 1071 | } |
| 1072 | } | 1072 | } |
| 1073 | 1073 | ||
| 1074 | const OsData = switch (builtin.os) { | 1074 | const OsData = switch (builtin.os.tag) { |
| 1075 | .linux => LinuxOsData, | 1075 | .linux => LinuxOsData, |
| 1076 | .macosx, .freebsd, .netbsd, .dragonfly => KEventData, | 1076 | .macosx, .freebsd, .netbsd, .dragonfly => KEventData, |
| 1077 | .windows => struct { | 1077 | .windows => struct { |
lib/std/fs.zig+23-23| ... | @@ -29,7 +29,7 @@ pub const Watch = @import("fs/watch.zig").Watch; | ... | @@ -29,7 +29,7 @@ pub const Watch = @import("fs/watch.zig").Watch; |
| 29 | /// All file system operations which return a path are guaranteed to | 29 | /// All file system operations which return a path are guaranteed to |
| 30 | /// fit into a UTF-8 encoded array of this length. | 30 | /// fit into a UTF-8 encoded array of this length. |
| 31 | /// The byte count includes room for a null sentinel byte. | 31 | /// The byte count includes room for a null sentinel byte. |
| 32 | pub const MAX_PATH_BYTES = switch (builtin.os) { | 32 | pub const MAX_PATH_BYTES = switch (builtin.os.tag) { |
| 33 | .linux, .macosx, .ios, .freebsd, .netbsd, .dragonfly => os.PATH_MAX, | 33 | .linux, .macosx, .ios, .freebsd, .netbsd, .dragonfly => os.PATH_MAX, |
| 34 | // Each UTF-16LE character may be expanded to 3 UTF-8 bytes. | 34 | // Each UTF-16LE character may be expanded to 3 UTF-8 bytes. |
| 35 | // If it would require 4 UTF-8 bytes, then there would be a surrogate | 35 | // If it would require 4 UTF-8 bytes, then there would be a surrogate |
| ... | @@ -47,7 +47,7 @@ pub const base64_encoder = base64.Base64Encoder.init( | ... | @@ -47,7 +47,7 @@ pub const base64_encoder = base64.Base64Encoder.init( |
| 47 | 47 | ||
| 48 | /// Whether or not async file system syscalls need a dedicated thread because the operating | 48 | /// Whether or not async file system syscalls need a dedicated thread because the operating |
| 49 | /// system does not support non-blocking I/O on the file system. | 49 | /// system does not support non-blocking I/O on the file system. |
| 50 | pub const need_async_thread = std.io.is_async and switch (builtin.os) { | 50 | pub const need_async_thread = std.io.is_async and switch (builtin.os.tag) { |
| 51 | .windows, .other => false, | 51 | .windows, .other => false, |
| 52 | else => true, | 52 | else => true, |
| 53 | }; | 53 | }; |
| ... | @@ -270,7 +270,7 @@ pub const AtomicFile = struct { | ... | @@ -270,7 +270,7 @@ pub const AtomicFile = struct { |
| 270 | assert(!self.finished); | 270 | assert(!self.finished); |
| 271 | self.file.close(); | 271 | self.file.close(); |
| 272 | self.finished = true; | 272 | self.finished = true; |
| 273 | if (builtin.os == .windows) { | 273 | if (builtin.os.tag == .windows) { |
| 274 | const dest_path_w = try os.windows.sliceToPrefixedFileW(self.dest_path); | 274 | const dest_path_w = try os.windows.sliceToPrefixedFileW(self.dest_path); |
| 275 | const tmp_path_w = try os.windows.cStrToPrefixedFileW(@ptrCast([*:0]u8, &self.tmp_path_buf)); | 275 | const tmp_path_w = try os.windows.cStrToPrefixedFileW(@ptrCast([*:0]u8, &self.tmp_path_buf)); |
| 276 | return os.renameW(&tmp_path_w, &dest_path_w); | 276 | return os.renameW(&tmp_path_w, &dest_path_w); |
| ... | @@ -394,7 +394,7 @@ pub const Dir = struct { | ... | @@ -394,7 +394,7 @@ pub const Dir = struct { |
| 394 | 394 | ||
| 395 | const IteratorError = error{AccessDenied} || os.UnexpectedError; | 395 | const IteratorError = error{AccessDenied} || os.UnexpectedError; |
| 396 | 396 | ||
| 397 | pub const Iterator = switch (builtin.os) { | 397 | pub const Iterator = switch (builtin.os.tag) { |
| 398 | .macosx, .ios, .freebsd, .netbsd, .dragonfly => struct { | 398 | .macosx, .ios, .freebsd, .netbsd, .dragonfly => struct { |
| 399 | dir: Dir, | 399 | dir: Dir, |
| 400 | seek: i64, | 400 | seek: i64, |
| ... | @@ -409,7 +409,7 @@ pub const Dir = struct { | ... | @@ -409,7 +409,7 @@ pub const Dir = struct { |
| 409 | /// Memory such as file names referenced in this returned entry becomes invalid | 409 | /// Memory such as file names referenced in this returned entry becomes invalid |
| 410 | /// with subsequent calls to `next`, as well as when this `Dir` is deinitialized. | 410 | /// with subsequent calls to `next`, as well as when this `Dir` is deinitialized. |
| 411 | pub fn next(self: *Self) Error!?Entry { | 411 | pub fn next(self: *Self) Error!?Entry { |
| 412 | switch (builtin.os) { | 412 | switch (builtin.os.tag) { |
| 413 | .macosx, .ios => return self.nextDarwin(), | 413 | .macosx, .ios => return self.nextDarwin(), |
| 414 | .freebsd, .netbsd, .dragonfly => return self.nextBsd(), | 414 | .freebsd, .netbsd, .dragonfly => return self.nextBsd(), |
| 415 | else => @compileError("unimplemented"), | 415 | else => @compileError("unimplemented"), |
| ... | @@ -644,7 +644,7 @@ pub const Dir = struct { | ... | @@ -644,7 +644,7 @@ pub const Dir = struct { |
| 644 | }; | 644 | }; |
| 645 | 645 | ||
| 646 | pub fn iterate(self: Dir) Iterator { | 646 | pub fn iterate(self: Dir) Iterator { |
| 647 | switch (builtin.os) { | 647 | switch (builtin.os.tag) { |
| 648 | .macosx, .ios, .freebsd, .netbsd, .dragonfly => return Iterator{ | 648 | .macosx, .ios, .freebsd, .netbsd, .dragonfly => return Iterator{ |
| 649 | .dir = self, | 649 | .dir = self, |
| 650 | .seek = 0, | 650 | .seek = 0, |
| ... | @@ -710,7 +710,7 @@ pub const Dir = struct { | ... | @@ -710,7 +710,7 @@ pub const Dir = struct { |
| 710 | /// Asserts that the path parameter has no null bytes. | 710 | /// Asserts that the path parameter has no null bytes. |
| 711 | pub fn openFile(self: Dir, sub_path: []const u8, flags: File.OpenFlags) File.OpenError!File { | 711 | pub fn openFile(self: Dir, sub_path: []const u8, flags: File.OpenFlags) File.OpenError!File { |
| 712 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); | 712 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); |
| 713 | if (builtin.os == .windows) { | 713 | if (builtin.os.tag == .windows) { |
| 714 | const path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 714 | const path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 715 | return self.openFileW(&path_w, flags); | 715 | return self.openFileW(&path_w, flags); |
| 716 | } | 716 | } |
| ... | @@ -720,7 +720,7 @@ pub const Dir = struct { | ... | @@ -720,7 +720,7 @@ pub const Dir = struct { |
| 720 | 720 | ||
| 721 | /// Same as `openFile` but the path parameter is null-terminated. | 721 | /// Same as `openFile` but the path parameter is null-terminated. |
| 722 | pub fn openFileC(self: Dir, sub_path: [*:0]const u8, flags: File.OpenFlags) File.OpenError!File { | 722 | pub fn openFileC(self: Dir, sub_path: [*:0]const u8, flags: File.OpenFlags) File.OpenError!File { |
| 723 | if (builtin.os == .windows) { | 723 | if (builtin.os.tag == .windows) { |
| 724 | const path_w = try os.windows.cStrToPrefixedFileW(sub_path); | 724 | const path_w = try os.windows.cStrToPrefixedFileW(sub_path); |
| 725 | return self.openFileW(&path_w, flags); | 725 | return self.openFileW(&path_w, flags); |
| 726 | } | 726 | } |
| ... | @@ -760,7 +760,7 @@ pub const Dir = struct { | ... | @@ -760,7 +760,7 @@ pub const Dir = struct { |
| 760 | /// Asserts that the path parameter has no null bytes. | 760 | /// Asserts that the path parameter has no null bytes. |
| 761 | pub fn createFile(self: Dir, sub_path: []const u8, flags: File.CreateFlags) File.OpenError!File { | 761 | pub fn createFile(self: Dir, sub_path: []const u8, flags: File.CreateFlags) File.OpenError!File { |
| 762 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); | 762 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); |
| 763 | if (builtin.os == .windows) { | 763 | if (builtin.os.tag == .windows) { |
| 764 | const path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 764 | const path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 765 | return self.createFileW(&path_w, flags); | 765 | return self.createFileW(&path_w, flags); |
| 766 | } | 766 | } |
| ... | @@ -770,7 +770,7 @@ pub const Dir = struct { | ... | @@ -770,7 +770,7 @@ pub const Dir = struct { |
| 770 | 770 | ||
| 771 | /// Same as `createFile` but the path parameter is null-terminated. | 771 | /// Same as `createFile` but the path parameter is null-terminated. |
| 772 | pub fn createFileC(self: Dir, sub_path_c: [*:0]const u8, flags: File.CreateFlags) File.OpenError!File { | 772 | pub fn createFileC(self: Dir, sub_path_c: [*:0]const u8, flags: File.CreateFlags) File.OpenError!File { |
| 773 | if (builtin.os == .windows) { | 773 | if (builtin.os.tag == .windows) { |
| 774 | const path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); | 774 | const path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); |
| 775 | return self.createFileW(&path_w, flags); | 775 | return self.createFileW(&path_w, flags); |
| 776 | } | 776 | } |
| ... | @@ -901,7 +901,7 @@ pub const Dir = struct { | ... | @@ -901,7 +901,7 @@ pub const Dir = struct { |
| 901 | /// Asserts that the path parameter has no null bytes. | 901 | /// Asserts that the path parameter has no null bytes. |
| 902 | pub fn openDirTraverse(self: Dir, sub_path: []const u8) OpenError!Dir { | 902 | pub fn openDirTraverse(self: Dir, sub_path: []const u8) OpenError!Dir { |
| 903 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); | 903 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); |
| 904 | if (builtin.os == .windows) { | 904 | if (builtin.os.tag == .windows) { |
| 905 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 905 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 906 | return self.openDirTraverseW(&sub_path_w); | 906 | return self.openDirTraverseW(&sub_path_w); |
| 907 | } | 907 | } |
| ... | @@ -919,7 +919,7 @@ pub const Dir = struct { | ... | @@ -919,7 +919,7 @@ pub const Dir = struct { |
| 919 | /// Asserts that the path parameter has no null bytes. | 919 | /// Asserts that the path parameter has no null bytes. |
| 920 | pub fn openDirList(self: Dir, sub_path: []const u8) OpenError!Dir { | 920 | pub fn openDirList(self: Dir, sub_path: []const u8) OpenError!Dir { |
| 921 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); | 921 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); |
| 922 | if (builtin.os == .windows) { | 922 | if (builtin.os.tag == .windows) { |
| 923 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 923 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 924 | return self.openDirListW(&sub_path_w); | 924 | return self.openDirListW(&sub_path_w); |
| 925 | } | 925 | } |
| ... | @@ -930,7 +930,7 @@ pub const Dir = struct { | ... | @@ -930,7 +930,7 @@ pub const Dir = struct { |
| 930 | 930 | ||
| 931 | /// Same as `openDirTraverse` except the parameter is null-terminated. | 931 | /// Same as `openDirTraverse` except the parameter is null-terminated. |
| 932 | pub fn openDirTraverseC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir { | 932 | pub fn openDirTraverseC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir { |
| 933 | if (builtin.os == .windows) { | 933 | if (builtin.os.tag == .windows) { |
| 934 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); | 934 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); |
| 935 | return self.openDirTraverseW(&sub_path_w); | 935 | return self.openDirTraverseW(&sub_path_w); |
| 936 | } else { | 936 | } else { |
| ... | @@ -941,7 +941,7 @@ pub const Dir = struct { | ... | @@ -941,7 +941,7 @@ pub const Dir = struct { |
| 941 | 941 | ||
| 942 | /// Same as `openDirList` except the parameter is null-terminated. | 942 | /// Same as `openDirList` except the parameter is null-terminated. |
| 943 | pub fn openDirListC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir { | 943 | pub fn openDirListC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir { |
| 944 | if (builtin.os == .windows) { | 944 | if (builtin.os.tag == .windows) { |
| 945 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); | 945 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c); |
| 946 | return self.openDirListW(&sub_path_w); | 946 | return self.openDirListW(&sub_path_w); |
| 947 | } else { | 947 | } else { |
| ... | @@ -1083,7 +1083,7 @@ pub const Dir = struct { | ... | @@ -1083,7 +1083,7 @@ pub const Dir = struct { |
| 1083 | /// Asserts that the path parameter has no null bytes. | 1083 | /// Asserts that the path parameter has no null bytes. |
| 1084 | pub fn deleteDir(self: Dir, sub_path: []const u8) DeleteDirError!void { | 1084 | pub fn deleteDir(self: Dir, sub_path: []const u8) DeleteDirError!void { |
| 1085 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); | 1085 | if (std.debug.runtime_safety) for (sub_path) |byte| assert(byte != 0); |
| 1086 | if (builtin.os == .windows) { | 1086 | if (builtin.os.tag == .windows) { |
| 1087 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 1087 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 1088 | return self.deleteDirW(&sub_path_w); | 1088 | return self.deleteDirW(&sub_path_w); |
| 1089 | } | 1089 | } |
| ... | @@ -1340,7 +1340,7 @@ pub const Dir = struct { | ... | @@ -1340,7 +1340,7 @@ pub const Dir = struct { |
| 1340 | /// For example, instead of testing if a file exists and then opening it, just | 1340 | /// For example, instead of testing if a file exists and then opening it, just |
| 1341 | /// open it and handle the error for file not found. | 1341 | /// open it and handle the error for file not found. |
| 1342 | pub fn access(self: Dir, sub_path: []const u8, flags: File.OpenFlags) AccessError!void { | 1342 | pub fn access(self: Dir, sub_path: []const u8, flags: File.OpenFlags) AccessError!void { |
| 1343 | if (builtin.os == .windows) { | 1343 | if (builtin.os.tag == .windows) { |
| 1344 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); | 1344 | const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path); |
| 1345 | return self.accessW(&sub_path_w, flags); | 1345 | return self.accessW(&sub_path_w, flags); |
| 1346 | } | 1346 | } |
| ... | @@ -1350,7 +1350,7 @@ pub const Dir = struct { | ... | @@ -1350,7 +1350,7 @@ pub const Dir = struct { |
| 1350 | 1350 | ||
| 1351 | /// Same as `access` except the path parameter is null-terminated. | 1351 | /// Same as `access` except the path parameter is null-terminated. |
| 1352 | pub fn accessZ(self: Dir, sub_path: [*:0]const u8, flags: File.OpenFlags) AccessError!void { | 1352 | pub fn accessZ(self: Dir, sub_path: [*:0]const u8, flags: File.OpenFlags) AccessError!void { |
| 1353 | if (builtin.os == .windows) { | 1353 | if (builtin.os.tag == .windows) { |
| 1354 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path); | 1354 | const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path); |
| 1355 | return self.accessW(&sub_path_w, flags); | 1355 | return self.accessW(&sub_path_w, flags); |
| 1356 | } | 1356 | } |
| ... | @@ -1381,7 +1381,7 @@ pub const Dir = struct { | ... | @@ -1381,7 +1381,7 @@ pub const Dir = struct { |
| 1381 | /// Closing the returned `Dir` is checked illegal behavior. Iterating over the result is illegal behavior. | 1381 | /// Closing the returned `Dir` is checked illegal behavior. Iterating over the result is illegal behavior. |
| 1382 | /// On POSIX targets, this function is comptime-callable. | 1382 | /// On POSIX targets, this function is comptime-callable. |
| 1383 | pub fn cwd() Dir { | 1383 | pub fn cwd() Dir { |
| 1384 | if (builtin.os == .windows) { | 1384 | if (builtin.os.tag == .windows) { |
| 1385 | return Dir{ .fd = os.windows.peb().ProcessParameters.CurrentDirectory.Handle }; | 1385 | return Dir{ .fd = os.windows.peb().ProcessParameters.CurrentDirectory.Handle }; |
| 1386 | } else { | 1386 | } else { |
| 1387 | return Dir{ .fd = os.AT_FDCWD }; | 1387 | return Dir{ .fd = os.AT_FDCWD }; |
| ... | @@ -1560,10 +1560,10 @@ pub fn readLinkC(pathname_c: [*]const u8, buffer: *[MAX_PATH_BYTES]u8) ![]u8 { | ... | @@ -1560,10 +1560,10 @@ pub fn readLinkC(pathname_c: [*]const u8, buffer: *[MAX_PATH_BYTES]u8) ![]u8 { |
| 1560 | pub const OpenSelfExeError = os.OpenError || os.windows.CreateFileError || SelfExePathError; | 1560 | pub const OpenSelfExeError = os.OpenError || os.windows.CreateFileError || SelfExePathError; |
| 1561 | 1561 | ||
| 1562 | pub fn openSelfExe() OpenSelfExeError!File { | 1562 | pub fn openSelfExe() OpenSelfExeError!File { |
| 1563 | if (builtin.os == .linux) { | 1563 | if (builtin.os.tag == .linux) { |
| 1564 | return openFileAbsoluteC("/proc/self/exe", .{}); | 1564 | return openFileAbsoluteC("/proc/self/exe", .{}); |
| 1565 | } | 1565 | } |
| 1566 | if (builtin.os == .windows) { | 1566 | if (builtin.os.tag == .windows) { |
| 1567 | const wide_slice = selfExePathW(); | 1567 | const wide_slice = selfExePathW(); |
| 1568 | const prefixed_path_w = try os.windows.wToPrefixedFileW(wide_slice); | 1568 | const prefixed_path_w = try os.windows.wToPrefixedFileW(wide_slice); |
| 1569 | return cwd().openReadW(&prefixed_path_w); | 1569 | return cwd().openReadW(&prefixed_path_w); |
| ... | @@ -1575,7 +1575,7 @@ pub fn openSelfExe() OpenSelfExeError!File { | ... | @@ -1575,7 +1575,7 @@ pub fn openSelfExe() OpenSelfExeError!File { |
| 1575 | } | 1575 | } |
| 1576 | 1576 | ||
| 1577 | test "openSelfExe" { | 1577 | test "openSelfExe" { |
| 1578 | switch (builtin.os) { | 1578 | switch (builtin.os.tag) { |
| 1579 | .linux, .macosx, .ios, .windows, .freebsd, .dragonfly => (try openSelfExe()).close(), | 1579 | .linux, .macosx, .ios, .windows, .freebsd, .dragonfly => (try openSelfExe()).close(), |
| 1580 | else => return error.SkipZigTest, // Unsupported OS. | 1580 | else => return error.SkipZigTest, // Unsupported OS. |
| 1581 | } | 1581 | } |
| ... | @@ -1600,7 +1600,7 @@ pub fn selfExePath(out_buffer: *[MAX_PATH_BYTES]u8) SelfExePathError![]u8 { | ... | @@ -1600,7 +1600,7 @@ pub fn selfExePath(out_buffer: *[MAX_PATH_BYTES]u8) SelfExePathError![]u8 { |
| 1600 | if (rc != 0) return error.NameTooLong; | 1600 | if (rc != 0) return error.NameTooLong; |
| 1601 | return mem.toSlice(u8, @ptrCast([*:0]u8, out_buffer)); | 1601 | return mem.toSlice(u8, @ptrCast([*:0]u8, out_buffer)); |
| 1602 | } | 1602 | } |
| 1603 | switch (builtin.os) { | 1603 | switch (builtin.os.tag) { |
| 1604 | .linux => return os.readlinkC("/proc/self/exe", out_buffer), | 1604 | .linux => return os.readlinkC("/proc/self/exe", out_buffer), |
| 1605 | .freebsd, .dragonfly => { | 1605 | .freebsd, .dragonfly => { |
| 1606 | var mib = [4]c_int{ os.CTL_KERN, os.KERN_PROC, os.KERN_PROC_PATHNAME, -1 }; | 1606 | var mib = [4]c_int{ os.CTL_KERN, os.KERN_PROC, os.KERN_PROC_PATHNAME, -1 }; |
| ... | @@ -1642,7 +1642,7 @@ pub fn selfExeDirPathAlloc(allocator: *Allocator) ![]u8 { | ... | @@ -1642,7 +1642,7 @@ pub fn selfExeDirPathAlloc(allocator: *Allocator) ![]u8 { |
| 1642 | /// Get the directory path that contains the current executable. | 1642 | /// Get the directory path that contains the current executable. |
| 1643 | /// Returned value is a slice of out_buffer. | 1643 | /// Returned value is a slice of out_buffer. |
| 1644 | pub fn selfExeDirPath(out_buffer: *[MAX_PATH_BYTES]u8) SelfExePathError![]const u8 { | 1644 | pub fn selfExeDirPath(out_buffer: *[MAX_PATH_BYTES]u8) SelfExePathError![]const u8 { |
| 1645 | if (builtin.os == .linux) { | 1645 | if (builtin.os.tag == .linux) { |
| 1646 | // If the currently executing binary has been deleted, | 1646 | // If the currently executing binary has been deleted, |
| 1647 | // the file path looks something like `/a/b/c/exe (deleted)` | 1647 | // the file path looks something like `/a/b/c/exe (deleted)` |
| 1648 | // This path cannot be opened, but it's valid for determining the directory | 1648 | // This path cannot be opened, but it's valid for determining the directory |
lib/std/fs/file.zig+6-6| ... | @@ -29,7 +29,7 @@ pub const File = struct { | ... | @@ -29,7 +29,7 @@ pub const File = struct { |
| 29 | 29 | ||
| 30 | pub const Mode = os.mode_t; | 30 | pub const Mode = os.mode_t; |
| 31 | 31 | ||
| 32 | pub const default_mode = switch (builtin.os) { | 32 | pub const default_mode = switch (builtin.os.tag) { |
| 33 | .windows => 0, | 33 | .windows => 0, |
| 34 | else => 0o666, | 34 | else => 0o666, |
| 35 | }; | 35 | }; |
| ... | @@ -83,7 +83,7 @@ pub const File = struct { | ... | @@ -83,7 +83,7 @@ pub const File = struct { |
| 83 | 83 | ||
| 84 | /// Test whether ANSI escape codes will be treated as such. | 84 | /// Test whether ANSI escape codes will be treated as such. |
| 85 | pub fn supportsAnsiEscapeCodes(self: File) bool { | 85 | pub fn supportsAnsiEscapeCodes(self: File) bool { |
| 86 | if (builtin.os == .windows) { | 86 | if (builtin.os.tag == .windows) { |
| 87 | return os.isCygwinPty(self.handle); | 87 | return os.isCygwinPty(self.handle); |
| 88 | } | 88 | } |
| 89 | if (self.isTty()) { | 89 | if (self.isTty()) { |
| ... | @@ -128,7 +128,7 @@ pub const File = struct { | ... | @@ -128,7 +128,7 @@ pub const File = struct { |
| 128 | 128 | ||
| 129 | /// TODO: integrate with async I/O | 129 | /// TODO: integrate with async I/O |
| 130 | pub fn getEndPos(self: File) GetPosError!u64 { | 130 | pub fn getEndPos(self: File) GetPosError!u64 { |
| 131 | if (builtin.os == .windows) { | 131 | if (builtin.os.tag == .windows) { |
| 132 | return windows.GetFileSizeEx(self.handle); | 132 | return windows.GetFileSizeEx(self.handle); |
| 133 | } | 133 | } |
| 134 | return (try self.stat()).size; | 134 | return (try self.stat()).size; |
| ... | @@ -138,7 +138,7 @@ pub const File = struct { | ... | @@ -138,7 +138,7 @@ pub const File = struct { |
| 138 | 138 | ||
| 139 | /// TODO: integrate with async I/O | 139 | /// TODO: integrate with async I/O |
| 140 | pub fn mode(self: File) ModeError!Mode { | 140 | pub fn mode(self: File) ModeError!Mode { |
| 141 | if (builtin.os == .windows) { | 141 | if (builtin.os.tag == .windows) { |
| 142 | return {}; | 142 | return {}; |
| 143 | } | 143 | } |
| 144 | return (try self.stat()).mode; | 144 | return (try self.stat()).mode; |
| ... | @@ -162,7 +162,7 @@ pub const File = struct { | ... | @@ -162,7 +162,7 @@ pub const File = struct { |
| 162 | 162 | ||
| 163 | /// TODO: integrate with async I/O | 163 | /// TODO: integrate with async I/O |
| 164 | pub fn stat(self: File) StatError!Stat { | 164 | pub fn stat(self: File) StatError!Stat { |
| 165 | if (builtin.os == .windows) { | 165 | if (builtin.os.tag == .windows) { |
| 166 | var io_status_block: windows.IO_STATUS_BLOCK = undefined; | 166 | var io_status_block: windows.IO_STATUS_BLOCK = undefined; |
| 167 | var info: windows.FILE_ALL_INFORMATION = undefined; | 167 | var info: windows.FILE_ALL_INFORMATION = undefined; |
| 168 | const rc = windows.ntdll.NtQueryInformationFile(self.handle, &io_status_block, &info, @sizeOf(windows.FILE_ALL_INFORMATION), .FileAllInformation); | 168 | const rc = windows.ntdll.NtQueryInformationFile(self.handle, &io_status_block, &info, @sizeOf(windows.FILE_ALL_INFORMATION), .FileAllInformation); |
| ... | @@ -209,7 +209,7 @@ pub const File = struct { | ... | @@ -209,7 +209,7 @@ pub const File = struct { |
| 209 | /// last modification timestamp in nanoseconds | 209 | /// last modification timestamp in nanoseconds |
| 210 | mtime: i64, | 210 | mtime: i64, |
| 211 | ) UpdateTimesError!void { | 211 | ) UpdateTimesError!void { |
| 212 | if (builtin.os == .windows) { | 212 | if (builtin.os.tag == .windows) { |
| 213 | const atime_ft = windows.nanoSecondsToFileTime(atime); | 213 | const atime_ft = windows.nanoSecondsToFileTime(atime); |
| 214 | const mtime_ft = windows.nanoSecondsToFileTime(mtime); | 214 | const mtime_ft = windows.nanoSecondsToFileTime(mtime); |
| 215 | return windows.SetFileTime(self.handle, null, &atime_ft, &mtime_ft); | 215 | return windows.SetFileTime(self.handle, null, &atime_ft, &mtime_ft); |
lib/std/fs/get_app_data_dir.zig+1-1| ... | @@ -13,7 +13,7 @@ pub const GetAppDataDirError = error{ | ... | @@ -13,7 +13,7 @@ pub const GetAppDataDirError = error{ |
| 13 | /// Caller owns returned memory. | 13 | /// Caller owns returned memory. |
| 14 | /// TODO determine if we can remove the allocator requirement | 14 | /// TODO determine if we can remove the allocator requirement |
| 15 | pub fn getAppDataDir(allocator: *mem.Allocator, appname: []const u8) GetAppDataDirError![]u8 { | 15 | pub fn getAppDataDir(allocator: *mem.Allocator, appname: []const u8) GetAppDataDirError![]u8 { |
| 16 | switch (builtin.os) { | 16 | switch (builtin.os.tag) { |
| 17 | .windows => { | 17 | .windows => { |
| 18 | var dir_path_ptr: [*:0]u16 = undefined; | 18 | var dir_path_ptr: [*:0]u16 = undefined; |
| 19 | switch (os.windows.shell32.SHGetKnownFolderPath( | 19 | switch (os.windows.shell32.SHGetKnownFolderPath( |
lib/std/fs/path.zig+19-19| ... | @@ -13,18 +13,18 @@ const process = std.process; | ... | @@ -13,18 +13,18 @@ const process = std.process; |
| 13 | 13 | ||
| 14 | pub const sep_windows = '\\'; | 14 | pub const sep_windows = '\\'; |
| 15 | pub const sep_posix = '/'; | 15 | pub const sep_posix = '/'; |
| 16 | pub const sep = if (builtin.os == .windows) sep_windows else sep_posix; | 16 | pub const sep = if (builtin.os.tag == .windows) sep_windows else sep_posix; |
| 17 | 17 | ||
| 18 | pub const sep_str_windows = "\\"; | 18 | pub const sep_str_windows = "\\"; |
| 19 | pub const sep_str_posix = "/"; | 19 | pub const sep_str_posix = "/"; |
| 20 | pub const sep_str = if (builtin.os == .windows) sep_str_windows else sep_str_posix; | 20 | pub const sep_str = if (builtin.os.tag == .windows) sep_str_windows else sep_str_posix; |
| 21 | 21 | ||
| 22 | pub const delimiter_windows = ';'; | 22 | pub const delimiter_windows = ';'; |
| 23 | pub const delimiter_posix = ':'; | 23 | pub const delimiter_posix = ':'; |
| 24 | pub const delimiter = if (builtin.os == .windows) delimiter_windows else delimiter_posix; | 24 | pub const delimiter = if (builtin.os.tag == .windows) delimiter_windows else delimiter_posix; |
| 25 | 25 | ||
| 26 | pub fn isSep(byte: u8) bool { | 26 | pub fn isSep(byte: u8) bool { |
| 27 | if (builtin.os == .windows) { | 27 | if (builtin.os.tag == .windows) { |
| 28 | return byte == '/' or byte == '\\'; | 28 | return byte == '/' or byte == '\\'; |
| 29 | } else { | 29 | } else { |
| 30 | return byte == '/'; | 30 | return byte == '/'; |
| ... | @@ -74,7 +74,7 @@ fn joinSep(allocator: *Allocator, separator: u8, paths: []const []const u8) ![]u | ... | @@ -74,7 +74,7 @@ fn joinSep(allocator: *Allocator, separator: u8, paths: []const []const u8) ![]u |
| 74 | return buf; | 74 | return buf; |
| 75 | } | 75 | } |
| 76 | 76 | ||
| 77 | pub const join = if (builtin.os == .windows) joinWindows else joinPosix; | 77 | pub const join = if (builtin.os.tag == .windows) joinWindows else joinPosix; |
| 78 | 78 | ||
| 79 | /// Naively combines a series of paths with the native path seperator. | 79 | /// Naively combines a series of paths with the native path seperator. |
| 80 | /// Allocates memory for the result, which must be freed by the caller. | 80 | /// Allocates memory for the result, which must be freed by the caller. |
| ... | @@ -129,7 +129,7 @@ test "join" { | ... | @@ -129,7 +129,7 @@ test "join" { |
| 129 | } | 129 | } |
| 130 | 130 | ||
| 131 | pub fn isAbsoluteC(path_c: [*:0]const u8) bool { | 131 | pub fn isAbsoluteC(path_c: [*:0]const u8) bool { |
| 132 | if (builtin.os == .windows) { | 132 | if (builtin.os.tag == .windows) { |
| 133 | return isAbsoluteWindowsC(path_c); | 133 | return isAbsoluteWindowsC(path_c); |
| 134 | } else { | 134 | } else { |
| 135 | return isAbsolutePosixC(path_c); | 135 | return isAbsolutePosixC(path_c); |
| ... | @@ -137,7 +137,7 @@ pub fn isAbsoluteC(path_c: [*:0]const u8) bool { | ... | @@ -137,7 +137,7 @@ pub fn isAbsoluteC(path_c: [*:0]const u8) bool { |
| 137 | } | 137 | } |
| 138 | 138 | ||
| 139 | pub fn isAbsolute(path: []const u8) bool { | 139 | pub fn isAbsolute(path: []const u8) bool { |
| 140 | if (builtin.os == .windows) { | 140 | if (builtin.os.tag == .windows) { |
| 141 | return isAbsoluteWindows(path); | 141 | return isAbsoluteWindows(path); |
| 142 | } else { | 142 | } else { |
| 143 | return isAbsolutePosix(path); | 143 | return isAbsolutePosix(path); |
| ... | @@ -318,7 +318,7 @@ test "windowsParsePath" { | ... | @@ -318,7 +318,7 @@ test "windowsParsePath" { |
| 318 | } | 318 | } |
| 319 | 319 | ||
| 320 | pub fn diskDesignator(path: []const u8) []const u8 { | 320 | pub fn diskDesignator(path: []const u8) []const u8 { |
| 321 | if (builtin.os == .windows) { | 321 | if (builtin.os.tag == .windows) { |
| 322 | return diskDesignatorWindows(path); | 322 | return diskDesignatorWindows(path); |
| 323 | } else { | 323 | } else { |
| 324 | return ""; | 324 | return ""; |
| ... | @@ -383,7 +383,7 @@ fn asciiEqlIgnoreCase(s1: []const u8, s2: []const u8) bool { | ... | @@ -383,7 +383,7 @@ fn asciiEqlIgnoreCase(s1: []const u8, s2: []const u8) bool { |
| 383 | 383 | ||
| 384 | /// On Windows, this calls `resolveWindows` and on POSIX it calls `resolvePosix`. | 384 | /// On Windows, this calls `resolveWindows` and on POSIX it calls `resolvePosix`. |
| 385 | pub fn resolve(allocator: *Allocator, paths: []const []const u8) ![]u8 { | 385 | pub fn resolve(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 386 | if (builtin.os == .windows) { | 386 | if (builtin.os.tag == .windows) { |
| 387 | return resolveWindows(allocator, paths); | 387 | return resolveWindows(allocator, paths); |
| 388 | } else { | 388 | } else { |
| 389 | return resolvePosix(allocator, paths); | 389 | return resolvePosix(allocator, paths); |
| ... | @@ -400,7 +400,7 @@ pub fn resolve(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -400,7 +400,7 @@ pub fn resolve(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 400 | /// Without performing actual syscalls, resolving `..` could be incorrect. | 400 | /// Without performing actual syscalls, resolving `..` could be incorrect. |
| 401 | pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { | 401 | pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 402 | if (paths.len == 0) { | 402 | if (paths.len == 0) { |
| 403 | assert(builtin.os == .windows); // resolveWindows called on non windows can't use getCwd | 403 | assert(builtin.os.tag == .windows); // resolveWindows called on non windows can't use getCwd |
| 404 | return process.getCwdAlloc(allocator); | 404 | return process.getCwdAlloc(allocator); |
| 405 | } | 405 | } |
| 406 | 406 | ||
| ... | @@ -495,7 +495,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -495,7 +495,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 495 | result_disk_designator = result[0..result_index]; | 495 | result_disk_designator = result[0..result_index]; |
| 496 | }, | 496 | }, |
| 497 | WindowsPath.Kind.None => { | 497 | WindowsPath.Kind.None => { |
| 498 | assert(builtin.os == .windows); // resolveWindows called on non windows can't use getCwd | 498 | assert(builtin.os.tag == .windows); // resolveWindows called on non windows can't use getCwd |
| 499 | const cwd = try process.getCwdAlloc(allocator); | 499 | const cwd = try process.getCwdAlloc(allocator); |
| 500 | defer allocator.free(cwd); | 500 | defer allocator.free(cwd); |
| 501 | const parsed_cwd = windowsParsePath(cwd); | 501 | const parsed_cwd = windowsParsePath(cwd); |
| ... | @@ -510,7 +510,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -510,7 +510,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 510 | }, | 510 | }, |
| 511 | } | 511 | } |
| 512 | } else { | 512 | } else { |
| 513 | assert(builtin.os == .windows); // resolveWindows called on non windows can't use getCwd | 513 | assert(builtin.os.tag == .windows); // resolveWindows called on non windows can't use getCwd |
| 514 | // TODO call get cwd for the result_disk_designator instead of the global one | 514 | // TODO call get cwd for the result_disk_designator instead of the global one |
| 515 | const cwd = try process.getCwdAlloc(allocator); | 515 | const cwd = try process.getCwdAlloc(allocator); |
| 516 | defer allocator.free(cwd); | 516 | defer allocator.free(cwd); |
| ... | @@ -581,7 +581,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -581,7 +581,7 @@ pub fn resolveWindows(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 581 | /// Without performing actual syscalls, resolving `..` could be incorrect. | 581 | /// Without performing actual syscalls, resolving `..` could be incorrect. |
| 582 | pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { | 582 | pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 583 | if (paths.len == 0) { | 583 | if (paths.len == 0) { |
| 584 | assert(builtin.os != .windows); // resolvePosix called on windows can't use getCwd | 584 | assert(builtin.os.tag != .windows); // resolvePosix called on windows can't use getCwd |
| 585 | return process.getCwdAlloc(allocator); | 585 | return process.getCwdAlloc(allocator); |
| 586 | } | 586 | } |
| 587 | 587 | ||
| ... | @@ -603,7 +603,7 @@ pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -603,7 +603,7 @@ pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 603 | if (have_abs) { | 603 | if (have_abs) { |
| 604 | result = try allocator.alloc(u8, max_size); | 604 | result = try allocator.alloc(u8, max_size); |
| 605 | } else { | 605 | } else { |
| 606 | assert(builtin.os != .windows); // resolvePosix called on windows can't use getCwd | 606 | assert(builtin.os.tag != .windows); // resolvePosix called on windows can't use getCwd |
| 607 | const cwd = try process.getCwdAlloc(allocator); | 607 | const cwd = try process.getCwdAlloc(allocator); |
| 608 | defer allocator.free(cwd); | 608 | defer allocator.free(cwd); |
| 609 | result = try allocator.alloc(u8, max_size + cwd.len + 1); | 609 | result = try allocator.alloc(u8, max_size + cwd.len + 1); |
| ... | @@ -645,7 +645,7 @@ pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { | ... | @@ -645,7 +645,7 @@ pub fn resolvePosix(allocator: *Allocator, paths: []const []const u8) ![]u8 { |
| 645 | test "resolve" { | 645 | test "resolve" { |
| 646 | const cwd = try process.getCwdAlloc(testing.allocator); | 646 | const cwd = try process.getCwdAlloc(testing.allocator); |
| 647 | defer testing.allocator.free(cwd); | 647 | defer testing.allocator.free(cwd); |
| 648 | if (builtin.os == .windows) { | 648 | if (builtin.os.tag == .windows) { |
| 649 | if (windowsParsePath(cwd).kind == WindowsPath.Kind.Drive) { | 649 | if (windowsParsePath(cwd).kind == WindowsPath.Kind.Drive) { |
| 650 | cwd[0] = asciiUpper(cwd[0]); | 650 | cwd[0] = asciiUpper(cwd[0]); |
| 651 | } | 651 | } |
| ... | @@ -661,7 +661,7 @@ test "resolveWindows" { | ... | @@ -661,7 +661,7 @@ test "resolveWindows" { |
| 661 | // TODO https://github.com/ziglang/zig/issues/3288 | 661 | // TODO https://github.com/ziglang/zig/issues/3288 |
| 662 | return error.SkipZigTest; | 662 | return error.SkipZigTest; |
| 663 | } | 663 | } |
| 664 | if (builtin.os == .windows) { | 664 | if (builtin.os.tag == .windows) { |
| 665 | const cwd = try process.getCwdAlloc(testing.allocator); | 665 | const cwd = try process.getCwdAlloc(testing.allocator); |
| 666 | defer testing.allocator.free(cwd); | 666 | defer testing.allocator.free(cwd); |
| 667 | const parsed_cwd = windowsParsePath(cwd); | 667 | const parsed_cwd = windowsParsePath(cwd); |
| ... | @@ -732,7 +732,7 @@ fn testResolvePosix(paths: []const []const u8, expected: []const u8) !void { | ... | @@ -732,7 +732,7 @@ fn testResolvePosix(paths: []const []const u8, expected: []const u8) !void { |
| 732 | /// If the path is a file in the current directory (no directory component) | 732 | /// If the path is a file in the current directory (no directory component) |
| 733 | /// then returns null | 733 | /// then returns null |
| 734 | pub fn dirname(path: []const u8) ?[]const u8 { | 734 | pub fn dirname(path: []const u8) ?[]const u8 { |
| 735 | if (builtin.os == .windows) { | 735 | if (builtin.os.tag == .windows) { |
| 736 | return dirnameWindows(path); | 736 | return dirnameWindows(path); |
| 737 | } else { | 737 | } else { |
| 738 | return dirnamePosix(path); | 738 | return dirnamePosix(path); |
| ... | @@ -864,7 +864,7 @@ fn testDirnameWindows(input: []const u8, expected_output: ?[]const u8) void { | ... | @@ -864,7 +864,7 @@ fn testDirnameWindows(input: []const u8, expected_output: ?[]const u8) void { |
| 864 | } | 864 | } |
| 865 | 865 | ||
| 866 | pub fn basename(path: []const u8) []const u8 { | 866 | pub fn basename(path: []const u8) []const u8 { |
| 867 | if (builtin.os == .windows) { | 867 | if (builtin.os.tag == .windows) { |
| 868 | return basenameWindows(path); | 868 | return basenameWindows(path); |
| 869 | } else { | 869 | } else { |
| 870 | return basenamePosix(path); | 870 | return basenamePosix(path); |
| ... | @@ -980,7 +980,7 @@ fn testBasenameWindows(input: []const u8, expected_output: []const u8) void { | ... | @@ -980,7 +980,7 @@ fn testBasenameWindows(input: []const u8, expected_output: []const u8) void { |
| 980 | /// string is returned. | 980 | /// string is returned. |
| 981 | /// On Windows this canonicalizes the drive to a capital letter and paths to `\\`. | 981 | /// On Windows this canonicalizes the drive to a capital letter and paths to `\\`. |
| 982 | pub fn relative(allocator: *Allocator, from: []const u8, to: []const u8) ![]u8 { | 982 | pub fn relative(allocator: *Allocator, from: []const u8, to: []const u8) ![]u8 { |
| 983 | if (builtin.os == .windows) { | 983 | if (builtin.os.tag == .windows) { |
| 984 | return relativeWindows(allocator, from, to); | 984 | return relativeWindows(allocator, from, to); |
| 985 | } else { | 985 | } else { |
| 986 | return relativePosix(allocator, from, to); | 986 | return relativePosix(allocator, from, to); |
lib/std/fs/watch.zig+4-4| ... | @@ -42,7 +42,7 @@ pub fn Watch(comptime V: type) type { | ... | @@ -42,7 +42,7 @@ pub fn Watch(comptime V: type) type { |
| 42 | os_data: OsData, | 42 | os_data: OsData, |
| 43 | allocator: *Allocator, | 43 | allocator: *Allocator, |
| 44 | 44 | ||
| 45 | const OsData = switch (builtin.os) { | 45 | const OsData = switch (builtin.os.tag) { |
| 46 | // TODO https://github.com/ziglang/zig/issues/3778 | 46 | // TODO https://github.com/ziglang/zig/issues/3778 |
| 47 | .macosx, .freebsd, .netbsd, .dragonfly => KqOsData, | 47 | .macosx, .freebsd, .netbsd, .dragonfly => KqOsData, |
| 48 | .linux => LinuxOsData, | 48 | .linux => LinuxOsData, |
| ... | @@ -121,7 +121,7 @@ pub fn Watch(comptime V: type) type { | ... | @@ -121,7 +121,7 @@ pub fn Watch(comptime V: type) type { |
| 121 | const self = try allocator.create(Self); | 121 | const self = try allocator.create(Self); |
| 122 | errdefer allocator.destroy(self); | 122 | errdefer allocator.destroy(self); |
| 123 | 123 | ||
| 124 | switch (builtin.os) { | 124 | switch (builtin.os.tag) { |
| 125 | .linux => { | 125 | .linux => { |
| 126 | const inotify_fd = try os.inotify_init1(os.linux.IN_NONBLOCK | os.linux.IN_CLOEXEC); | 126 | const inotify_fd = try os.inotify_init1(os.linux.IN_NONBLOCK | os.linux.IN_CLOEXEC); |
| 127 | errdefer os.close(inotify_fd); | 127 | errdefer os.close(inotify_fd); |
| ... | @@ -172,7 +172,7 @@ pub fn Watch(comptime V: type) type { | ... | @@ -172,7 +172,7 @@ pub fn Watch(comptime V: type) type { |
| 172 | 172 | ||
| 173 | /// All addFile calls and removeFile calls must have completed. | 173 | /// All addFile calls and removeFile calls must have completed. |
| 174 | pub fn deinit(self: *Self) void { | 174 | pub fn deinit(self: *Self) void { |
| 175 | switch (builtin.os) { | 175 | switch (builtin.os.tag) { |
| 176 | .macosx, .freebsd, .netbsd, .dragonfly => { | 176 | .macosx, .freebsd, .netbsd, .dragonfly => { |
| 177 | // TODO we need to cancel the frames before destroying the lock | 177 | // TODO we need to cancel the frames before destroying the lock |
| 178 | self.os_data.table_lock.deinit(); | 178 | self.os_data.table_lock.deinit(); |
| ... | @@ -223,7 +223,7 @@ pub fn Watch(comptime V: type) type { | ... | @@ -223,7 +223,7 @@ pub fn Watch(comptime V: type) type { |
| 223 | } | 223 | } |
| 224 | 224 | ||
| 225 | pub fn addFile(self: *Self, file_path: []const u8, value: V) !?V { | 225 | pub fn addFile(self: *Self, file_path: []const u8, value: V) !?V { |
| 226 | switch (builtin.os) { | 226 | switch (builtin.os.tag) { |
| 227 | .macosx, .freebsd, .netbsd, .dragonfly => return addFileKEvent(self, file_path, value), | 227 | .macosx, .freebsd, .netbsd, .dragonfly => return addFileKEvent(self, file_path, value), |
| 228 | .linux => return addFileLinux(self, file_path, value), | 228 | .linux => return addFileLinux(self, file_path, value), |
| 229 | .windows => return addFileWindows(self, file_path, value), | 229 | .windows => return addFileWindows(self, file_path, value), |
lib/std/heap.zig+7-7| ... | @@ -36,7 +36,7 @@ fn cShrink(self: *Allocator, old_mem: []u8, old_align: u29, new_size: usize, new | ... | @@ -36,7 +36,7 @@ fn cShrink(self: *Allocator, old_mem: []u8, old_align: u29, new_size: usize, new |
| 36 | /// Thread-safe and lock-free. | 36 | /// Thread-safe and lock-free. |
| 37 | pub const page_allocator = if (std.Target.current.isWasm()) | 37 | pub const page_allocator = if (std.Target.current.isWasm()) |
| 38 | &wasm_page_allocator_state | 38 | &wasm_page_allocator_state |
| 39 | else if (std.Target.current.getOs() == .freestanding) | 39 | else if (std.Target.current.os.tag == .freestanding) |
| 40 | root.os.heap.page_allocator | 40 | root.os.heap.page_allocator |
| 41 | else | 41 | else |
| 42 | &page_allocator_state; | 42 | &page_allocator_state; |
| ... | @@ -57,7 +57,7 @@ const PageAllocator = struct { | ... | @@ -57,7 +57,7 @@ const PageAllocator = struct { |
| 57 | fn alloc(allocator: *Allocator, n: usize, alignment: u29) error{OutOfMemory}![]u8 { | 57 | fn alloc(allocator: *Allocator, n: usize, alignment: u29) error{OutOfMemory}![]u8 { |
| 58 | if (n == 0) return &[0]u8{}; | 58 | if (n == 0) return &[0]u8{}; |
| 59 | 59 | ||
| 60 | if (builtin.os == .windows) { | 60 | if (builtin.os.tag == .windows) { |
| 61 | const w = os.windows; | 61 | const w = os.windows; |
| 62 | 62 | ||
| 63 | // Although officially it's at least aligned to page boundary, | 63 | // Although officially it's at least aligned to page boundary, |
| ... | @@ -143,7 +143,7 @@ const PageAllocator = struct { | ... | @@ -143,7 +143,7 @@ const PageAllocator = struct { |
| 143 | 143 | ||
| 144 | fn shrink(allocator: *Allocator, old_mem_unaligned: []u8, old_align: u29, new_size: usize, new_align: u29) []u8 { | 144 | fn shrink(allocator: *Allocator, old_mem_unaligned: []u8, old_align: u29, new_size: usize, new_align: u29) []u8 { |
| 145 | const old_mem = @alignCast(mem.page_size, old_mem_unaligned); | 145 | const old_mem = @alignCast(mem.page_size, old_mem_unaligned); |
| 146 | if (builtin.os == .windows) { | 146 | if (builtin.os.tag == .windows) { |
| 147 | const w = os.windows; | 147 | const w = os.windows; |
| 148 | if (new_size == 0) { | 148 | if (new_size == 0) { |
| 149 | // From the docs: | 149 | // From the docs: |
| ... | @@ -183,7 +183,7 @@ const PageAllocator = struct { | ... | @@ -183,7 +183,7 @@ const PageAllocator = struct { |
| 183 | 183 | ||
| 184 | fn realloc(allocator: *Allocator, old_mem_unaligned: []u8, old_align: u29, new_size: usize, new_align: u29) ![]u8 { | 184 | fn realloc(allocator: *Allocator, old_mem_unaligned: []u8, old_align: u29, new_size: usize, new_align: u29) ![]u8 { |
| 185 | const old_mem = @alignCast(mem.page_size, old_mem_unaligned); | 185 | const old_mem = @alignCast(mem.page_size, old_mem_unaligned); |
| 186 | if (builtin.os == .windows) { | 186 | if (builtin.os.tag == .windows) { |
| 187 | if (old_mem.len == 0) { | 187 | if (old_mem.len == 0) { |
| 188 | return alloc(allocator, new_size, new_align); | 188 | return alloc(allocator, new_size, new_align); |
| 189 | } | 189 | } |
| ... | @@ -412,7 +412,7 @@ const WasmPageAllocator = struct { | ... | @@ -412,7 +412,7 @@ const WasmPageAllocator = struct { |
| 412 | } | 412 | } |
| 413 | }; | 413 | }; |
| 414 | 414 | ||
| 415 | pub const HeapAllocator = switch (builtin.os) { | 415 | pub const HeapAllocator = switch (builtin.os.tag) { |
| 416 | .windows => struct { | 416 | .windows => struct { |
| 417 | allocator: Allocator, | 417 | allocator: Allocator, |
| 418 | heap_handle: ?HeapHandle, | 418 | heap_handle: ?HeapHandle, |
| ... | @@ -855,7 +855,7 @@ test "PageAllocator" { | ... | @@ -855,7 +855,7 @@ test "PageAllocator" { |
| 855 | try testAllocatorAlignedShrink(allocator); | 855 | try testAllocatorAlignedShrink(allocator); |
| 856 | } | 856 | } |
| 857 | 857 | ||
| 858 | if (builtin.os == .windows) { | 858 | if (builtin.os.tag == .windows) { |
| 859 | // Trying really large alignment. As mentionned in the implementation, | 859 | // Trying really large alignment. As mentionned in the implementation, |
| 860 | // VirtualAlloc returns 64K aligned addresses. We want to make sure | 860 | // VirtualAlloc returns 64K aligned addresses. We want to make sure |
| 861 | // PageAllocator works beyond that, as it's not tested by | 861 | // PageAllocator works beyond that, as it's not tested by |
| ... | @@ -868,7 +868,7 @@ test "PageAllocator" { | ... | @@ -868,7 +868,7 @@ test "PageAllocator" { |
| 868 | } | 868 | } |
| 869 | 869 | ||
| 870 | test "HeapAllocator" { | 870 | test "HeapAllocator" { |
| 871 | if (builtin.os == .windows) { | 871 | if (builtin.os.tag == .windows) { |
| 872 | var heap_allocator = HeapAllocator.init(); | 872 | var heap_allocator = HeapAllocator.init(); |
| 873 | defer heap_allocator.deinit(); | 873 | defer heap_allocator.deinit(); |
| 874 | 874 |
lib/std/io.zig+3-3| ... | @@ -35,7 +35,7 @@ else | ... | @@ -35,7 +35,7 @@ else |
| 35 | pub const is_async = mode != .blocking; | 35 | pub const is_async = mode != .blocking; |
| 36 | 36 | ||
| 37 | fn getStdOutHandle() os.fd_t { | 37 | fn getStdOutHandle() os.fd_t { |
| 38 | if (builtin.os == .windows) { | 38 | if (builtin.os.tag == .windows) { |
| 39 | return os.windows.peb().ProcessParameters.hStdOutput; | 39 | return os.windows.peb().ProcessParameters.hStdOutput; |
| 40 | } | 40 | } |
| 41 | 41 | ||
| ... | @@ -54,7 +54,7 @@ pub fn getStdOut() File { | ... | @@ -54,7 +54,7 @@ pub fn getStdOut() File { |
| 54 | } | 54 | } |
| 55 | 55 | ||
| 56 | fn getStdErrHandle() os.fd_t { | 56 | fn getStdErrHandle() os.fd_t { |
| 57 | if (builtin.os == .windows) { | 57 | if (builtin.os.tag == .windows) { |
| 58 | return os.windows.peb().ProcessParameters.hStdError; | 58 | return os.windows.peb().ProcessParameters.hStdError; |
| 59 | } | 59 | } |
| 60 | 60 | ||
| ... | @@ -74,7 +74,7 @@ pub fn getStdErr() File { | ... | @@ -74,7 +74,7 @@ pub fn getStdErr() File { |
| 74 | } | 74 | } |
| 75 | 75 | ||
| 76 | fn getStdInHandle() os.fd_t { | 76 | fn getStdInHandle() os.fd_t { |
| 77 | if (builtin.os == .windows) { | 77 | if (builtin.os.tag == .windows) { |
| 78 | return os.windows.peb().ProcessParameters.hStdInput; | 78 | return os.windows.peb().ProcessParameters.hStdInput; |
| 79 | } | 79 | } |
| 80 | 80 |
lib/std/mutex.zig+2-2| ... | @@ -73,7 +73,7 @@ pub const Mutex = if (builtin.single_threaded) | ... | @@ -73,7 +73,7 @@ pub const Mutex = if (builtin.single_threaded) |
| 73 | return self.tryAcquire() orelse @panic("deadlock detected"); | 73 | return self.tryAcquire() orelse @panic("deadlock detected"); |
| 74 | } | 74 | } |
| 75 | } | 75 | } |
| 76 | else if (builtin.os == .windows) | 76 | else if (builtin.os.tag == .windows) |
| 77 | // https://locklessinc.com/articles/keyed_events/ | 77 | // https://locklessinc.com/articles/keyed_events/ |
| 78 | extern union { | 78 | extern union { |
| 79 | locked: u8, | 79 | locked: u8, |
| ... | @@ -161,7 +161,7 @@ else if (builtin.os == .windows) | ... | @@ -161,7 +161,7 @@ else if (builtin.os == .windows) |
| 161 | } | 161 | } |
| 162 | }; | 162 | }; |
| 163 | } | 163 | } |
| 164 | else if (builtin.link_libc or builtin.os == .linux) | 164 | else if (builtin.link_libc or builtin.os.tag == .linux) |
| 165 | // stack-based version of https://github.com/Amanieu/parking_lot/blob/master/core/src/word_lock.rs | 165 | // stack-based version of https://github.com/Amanieu/parking_lot/blob/master/core/src/word_lock.rs |
| 166 | struct { | 166 | struct { |
| 167 | state: usize, | 167 | state: usize, |
lib/std/net.zig+1-1| ... | @@ -501,7 +501,7 @@ pub fn getAddressList(allocator: *mem.Allocator, name: []const u8, port: u16) !* | ... | @@ -501,7 +501,7 @@ pub fn getAddressList(allocator: *mem.Allocator, name: []const u8, port: u16) !* |
| 501 | 501 | ||
| 502 | return result; | 502 | return result; |
| 503 | } | 503 | } |
| 504 | if (builtin.os == .linux) { | 504 | if (builtin.os.tag == .linux) { |
| 505 | const flags = std.c.AI_NUMERICSERV; | 505 | const flags = std.c.AI_NUMERICSERV; |
| 506 | const family = os.AF_UNSPEC; | 506 | const family = os.AF_UNSPEC; |
| 507 | var lookup_addrs = std.ArrayList(LookupAddr).init(allocator); | 507 | var lookup_addrs = std.ArrayList(LookupAddr).init(allocator); |
lib/std/net/test.zig+2-2| ... | @@ -63,7 +63,7 @@ test "parse and render IPv4 addresses" { | ... | @@ -63,7 +63,7 @@ test "parse and render IPv4 addresses" { |
| 63 | } | 63 | } |
| 64 | 64 | ||
| 65 | test "resolve DNS" { | 65 | test "resolve DNS" { |
| 66 | if (std.builtin.os == .windows) { | 66 | if (std.builtin.os.tag == .windows) { |
| 67 | // DNS resolution not implemented on Windows yet. | 67 | // DNS resolution not implemented on Windows yet. |
| 68 | return error.SkipZigTest; | 68 | return error.SkipZigTest; |
| 69 | } | 69 | } |
| ... | @@ -81,7 +81,7 @@ test "resolve DNS" { | ... | @@ -81,7 +81,7 @@ test "resolve DNS" { |
| 81 | test "listen on a port, send bytes, receive bytes" { | 81 | test "listen on a port, send bytes, receive bytes" { |
| 82 | if (!std.io.is_async) return error.SkipZigTest; | 82 | if (!std.io.is_async) return error.SkipZigTest; |
| 83 | 83 | ||
| 84 | if (std.builtin.os != .linux) { | 84 | if (std.builtin.os.tag != .linux) { |
| 85 | // TODO build abstractions for other operating systems | 85 | // TODO build abstractions for other operating systems |
| 86 | return error.SkipZigTest; | 86 | return error.SkipZigTest; |
| 87 | } | 87 | } |
lib/std/os.zig+68-68| ... | @@ -56,7 +56,7 @@ pub const system = if (@hasDecl(root, "os") and root.os != @This()) | ... | @@ -56,7 +56,7 @@ pub const system = if (@hasDecl(root, "os") and root.os != @This()) |
| 56 | root.os.system | 56 | root.os.system |
| 57 | else if (builtin.link_libc) | 57 | else if (builtin.link_libc) |
| 58 | std.c | 58 | std.c |
| 59 | else switch (builtin.os) { | 59 | else switch (builtin.os.tag) { |
| 60 | .macosx, .ios, .watchos, .tvos => darwin, | 60 | .macosx, .ios, .watchos, .tvos => darwin, |
| 61 | .freebsd => freebsd, | 61 | .freebsd => freebsd, |
| 62 | .linux => linux, | 62 | .linux => linux, |
| ... | @@ -93,10 +93,10 @@ pub const errno = system.getErrno; | ... | @@ -93,10 +93,10 @@ pub const errno = system.getErrno; |
| 93 | /// must call `fsync` before `close`. | 93 | /// must call `fsync` before `close`. |
| 94 | /// Note: The Zig standard library does not support POSIX thread cancellation. | 94 | /// Note: The Zig standard library does not support POSIX thread cancellation. |
| 95 | pub fn close(fd: fd_t) void { | 95 | pub fn close(fd: fd_t) void { |
| 96 | if (builtin.os == .windows) { | 96 | if (builtin.os.tag == .windows) { |
| 97 | return windows.CloseHandle(fd); | 97 | return windows.CloseHandle(fd); |
| 98 | } | 98 | } |
| 99 | if (builtin.os == .wasi) { | 99 | if (builtin.os.tag == .wasi) { |
| 100 | _ = wasi.fd_close(fd); | 100 | _ = wasi.fd_close(fd); |
| 101 | } | 101 | } |
| 102 | if (comptime std.Target.current.isDarwin()) { | 102 | if (comptime std.Target.current.isDarwin()) { |
| ... | @@ -121,12 +121,12 @@ pub const GetRandomError = OpenError; | ... | @@ -121,12 +121,12 @@ pub const GetRandomError = OpenError; |
| 121 | /// appropriate OS-specific library call. Otherwise it uses the zig standard | 121 | /// appropriate OS-specific library call. Otherwise it uses the zig standard |
| 122 | /// library implementation. | 122 | /// library implementation. |
| 123 | pub fn getrandom(buffer: []u8) GetRandomError!void { | 123 | pub fn getrandom(buffer: []u8) GetRandomError!void { |
| 124 | if (builtin.os == .windows) { | 124 | if (builtin.os.tag == .windows) { |
| 125 | return windows.RtlGenRandom(buffer); | 125 | return windows.RtlGenRandom(buffer); |
| 126 | } | 126 | } |
| 127 | if (builtin.os == .linux or builtin.os == .freebsd) { | 127 | if (builtin.os.tag == .linux or builtin.os.tag == .freebsd) { |
| 128 | var buf = buffer; | 128 | var buf = buffer; |
| 129 | const use_c = builtin.os != .linux or | 129 | const use_c = builtin.os.tag != .linux or |
| 130 | std.c.versionCheck(builtin.Version{ .major = 2, .minor = 25, .patch = 0 }).ok; | 130 | std.c.versionCheck(builtin.Version{ .major = 2, .minor = 25, .patch = 0 }).ok; |
| 131 | 131 | ||
| 132 | while (buf.len != 0) { | 132 | while (buf.len != 0) { |
| ... | @@ -153,7 +153,7 @@ pub fn getrandom(buffer: []u8) GetRandomError!void { | ... | @@ -153,7 +153,7 @@ pub fn getrandom(buffer: []u8) GetRandomError!void { |
| 153 | } | 153 | } |
| 154 | return; | 154 | return; |
| 155 | } | 155 | } |
| 156 | if (builtin.os == .wasi) { | 156 | if (builtin.os.tag == .wasi) { |
| 157 | switch (wasi.random_get(buffer.ptr, buffer.len)) { | 157 | switch (wasi.random_get(buffer.ptr, buffer.len)) { |
| 158 | 0 => return, | 158 | 0 => return, |
| 159 | else => |err| return unexpectedErrno(err), | 159 | else => |err| return unexpectedErrno(err), |
| ... | @@ -188,13 +188,13 @@ pub fn abort() noreturn { | ... | @@ -188,13 +188,13 @@ pub fn abort() noreturn { |
| 188 | // MSVCRT abort() sometimes opens a popup window which is undesirable, so | 188 | // MSVCRT abort() sometimes opens a popup window which is undesirable, so |
| 189 | // even when linking libc on Windows we use our own abort implementation. | 189 | // even when linking libc on Windows we use our own abort implementation. |
| 190 | // See https://github.com/ziglang/zig/issues/2071 for more details. | 190 | // See https://github.com/ziglang/zig/issues/2071 for more details. |
| 191 | if (builtin.os == .windows) { | 191 | if (builtin.os.tag == .windows) { |
| 192 | if (builtin.mode == .Debug) { | 192 | if (builtin.mode == .Debug) { |
| 193 | @breakpoint(); | 193 | @breakpoint(); |
| 194 | } | 194 | } |
| 195 | windows.kernel32.ExitProcess(3); | 195 | windows.kernel32.ExitProcess(3); |
| 196 | } | 196 | } |
| 197 | if (!builtin.link_libc and builtin.os == .linux) { | 197 | if (!builtin.link_libc and builtin.os.tag == .linux) { |
| 198 | raise(SIGABRT) catch {}; | 198 | raise(SIGABRT) catch {}; |
| 199 | 199 | ||
| 200 | // TODO the rest of the implementation of abort() from musl libc here | 200 | // TODO the rest of the implementation of abort() from musl libc here |
| ... | @@ -202,10 +202,10 @@ pub fn abort() noreturn { | ... | @@ -202,10 +202,10 @@ pub fn abort() noreturn { |
| 202 | raise(SIGKILL) catch {}; | 202 | raise(SIGKILL) catch {}; |
| 203 | exit(127); | 203 | exit(127); |
| 204 | } | 204 | } |
| 205 | if (builtin.os == .uefi) { | 205 | if (builtin.os.tag == .uefi) { |
| 206 | exit(0); // TODO choose appropriate exit code | 206 | exit(0); // TODO choose appropriate exit code |
| 207 | } | 207 | } |
| 208 | if (builtin.os == .wasi) { | 208 | if (builtin.os.tag == .wasi) { |
| 209 | @breakpoint(); | 209 | @breakpoint(); |
| 210 | exit(1); | 210 | exit(1); |
| 211 | } | 211 | } |
| ... | @@ -223,7 +223,7 @@ pub fn raise(sig: u8) RaiseError!void { | ... | @@ -223,7 +223,7 @@ pub fn raise(sig: u8) RaiseError!void { |
| 223 | } | 223 | } |
| 224 | } | 224 | } |
| 225 | 225 | ||
| 226 | if (builtin.os == .linux) { | 226 | if (builtin.os.tag == .linux) { |
| 227 | var set: linux.sigset_t = undefined; | 227 | var set: linux.sigset_t = undefined; |
| 228 | // block application signals | 228 | // block application signals |
| 229 | _ = linux.sigprocmask(SIG_BLOCK, &linux.app_mask, &set); | 229 | _ = linux.sigprocmask(SIG_BLOCK, &linux.app_mask, &set); |
| ... | @@ -260,16 +260,16 @@ pub fn exit(status: u8) noreturn { | ... | @@ -260,16 +260,16 @@ pub fn exit(status: u8) noreturn { |
| 260 | if (builtin.link_libc) { | 260 | if (builtin.link_libc) { |
| 261 | system.exit(status); | 261 | system.exit(status); |
| 262 | } | 262 | } |
| 263 | if (builtin.os == .windows) { | 263 | if (builtin.os.tag == .windows) { |
| 264 | windows.kernel32.ExitProcess(status); | 264 | windows.kernel32.ExitProcess(status); |
| 265 | } | 265 | } |
| 266 | if (builtin.os == .wasi) { | 266 | if (builtin.os.tag == .wasi) { |
| 267 | wasi.proc_exit(status); | 267 | wasi.proc_exit(status); |
| 268 | } | 268 | } |
| 269 | if (builtin.os == .linux and !builtin.single_threaded) { | 269 | if (builtin.os.tag == .linux and !builtin.single_threaded) { |
| 270 | linux.exit_group(status); | 270 | linux.exit_group(status); |
| 271 | } | 271 | } |
| 272 | if (builtin.os == .uefi) { | 272 | if (builtin.os.tag == .uefi) { |
| 273 | // exit() is only avaliable if exitBootServices() has not been called yet. | 273 | // exit() is only avaliable if exitBootServices() has not been called yet. |
| 274 | // This call to exit should not fail, so we don't care about its return value. | 274 | // This call to exit should not fail, so we don't care about its return value. |
| 275 | if (uefi.system_table.boot_services) |bs| { | 275 | if (uefi.system_table.boot_services) |bs| { |
| ... | @@ -299,11 +299,11 @@ pub const ReadError = error{ | ... | @@ -299,11 +299,11 @@ pub const ReadError = error{ |
| 299 | /// If the application has a global event loop enabled, EAGAIN is handled | 299 | /// If the application has a global event loop enabled, EAGAIN is handled |
| 300 | /// via the event loop. Otherwise EAGAIN results in error.WouldBlock. | 300 | /// via the event loop. Otherwise EAGAIN results in error.WouldBlock. |
| 301 | pub fn read(fd: fd_t, buf: []u8) ReadError!usize { | 301 | pub fn read(fd: fd_t, buf: []u8) ReadError!usize { |
| 302 | if (builtin.os == .windows) { | 302 | if (builtin.os.tag == .windows) { |
| 303 | return windows.ReadFile(fd, buf, null); | 303 | return windows.ReadFile(fd, buf, null); |
| 304 | } | 304 | } |
| 305 | 305 | ||
| 306 | if (builtin.os == .wasi and !builtin.link_libc) { | 306 | if (builtin.os.tag == .wasi and !builtin.link_libc) { |
| 307 | const iovs = [1]iovec{iovec{ | 307 | const iovs = [1]iovec{iovec{ |
| 308 | .iov_base = buf.ptr, | 308 | .iov_base = buf.ptr, |
| 309 | .iov_len = buf.len, | 309 | .iov_len = buf.len, |
| ... | @@ -352,7 +352,7 @@ pub fn read(fd: fd_t, buf: []u8) ReadError!usize { | ... | @@ -352,7 +352,7 @@ pub fn read(fd: fd_t, buf: []u8) ReadError!usize { |
| 352 | /// * Windows | 352 | /// * Windows |
| 353 | /// On these systems, the read races with concurrent writes to the same file descriptor. | 353 | /// On these systems, the read races with concurrent writes to the same file descriptor. |
| 354 | pub fn readv(fd: fd_t, iov: []const iovec) ReadError!usize { | 354 | pub fn readv(fd: fd_t, iov: []const iovec) ReadError!usize { |
| 355 | if (builtin.os == .windows) { | 355 | if (builtin.os.tag == .windows) { |
| 356 | // TODO batch these into parallel requests | 356 | // TODO batch these into parallel requests |
| 357 | var off: usize = 0; | 357 | var off: usize = 0; |
| 358 | var iov_i: usize = 0; | 358 | var iov_i: usize = 0; |
| ... | @@ -406,7 +406,7 @@ pub fn readv(fd: fd_t, iov: []const iovec) ReadError!usize { | ... | @@ -406,7 +406,7 @@ pub fn readv(fd: fd_t, iov: []const iovec) ReadError!usize { |
| 406 | /// On Windows, if the application has a global event loop enabled, I/O Completion Ports are | 406 | /// On Windows, if the application has a global event loop enabled, I/O Completion Ports are |
| 407 | /// used to perform the I/O. `error.WouldBlock` is not possible on Windows. | 407 | /// used to perform the I/O. `error.WouldBlock` is not possible on Windows. |
| 408 | pub fn pread(fd: fd_t, buf: []u8, offset: u64) ReadError!usize { | 408 | pub fn pread(fd: fd_t, buf: []u8, offset: u64) ReadError!usize { |
| 409 | if (builtin.os == .windows) { | 409 | if (builtin.os.tag == .windows) { |
| 410 | return windows.ReadFile(fd, buf, offset); | 410 | return windows.ReadFile(fd, buf, offset); |
| 411 | } | 411 | } |
| 412 | 412 | ||
| ... | @@ -493,7 +493,7 @@ pub fn preadv(fd: fd_t, iov: []const iovec, offset: u64) ReadError!usize { | ... | @@ -493,7 +493,7 @@ pub fn preadv(fd: fd_t, iov: []const iovec, offset: u64) ReadError!usize { |
| 493 | } | 493 | } |
| 494 | } | 494 | } |
| 495 | 495 | ||
| 496 | if (builtin.os == .windows) { | 496 | if (builtin.os.tag == .windows) { |
| 497 | // TODO batch these into parallel requests | 497 | // TODO batch these into parallel requests |
| 498 | var off: usize = 0; | 498 | var off: usize = 0; |
| 499 | var iov_i: usize = 0; | 499 | var iov_i: usize = 0; |
| ... | @@ -557,11 +557,11 @@ pub const WriteError = error{ | ... | @@ -557,11 +557,11 @@ pub const WriteError = error{ |
| 557 | /// If the application has a global event loop enabled, EAGAIN is handled | 557 | /// If the application has a global event loop enabled, EAGAIN is handled |
| 558 | /// via the event loop. Otherwise EAGAIN results in error.WouldBlock. | 558 | /// via the event loop. Otherwise EAGAIN results in error.WouldBlock. |
| 559 | pub fn write(fd: fd_t, bytes: []const u8) WriteError!void { | 559 | pub fn write(fd: fd_t, bytes: []const u8) WriteError!void { |
| 560 | if (builtin.os == .windows) { | 560 | if (builtin.os.tag == .windows) { |
| 561 | return windows.WriteFile(fd, bytes, null); | 561 | return windows.WriteFile(fd, bytes, null); |
| 562 | } | 562 | } |
| 563 | 563 | ||
| 564 | if (builtin.os == .wasi and !builtin.link_libc) { | 564 | if (builtin.os.tag == .wasi and !builtin.link_libc) { |
| 565 | const ciovs = [1]iovec_const{iovec_const{ | 565 | const ciovs = [1]iovec_const{iovec_const{ |
| 566 | .iov_base = bytes.ptr, | 566 | .iov_base = bytes.ptr, |
| 567 | .iov_len = bytes.len, | 567 | .iov_len = bytes.len, |
| ... | @@ -1129,7 +1129,7 @@ pub fn getenv(key: []const u8) ?[]const u8 { | ... | @@ -1129,7 +1129,7 @@ pub fn getenv(key: []const u8) ?[]const u8 { |
| 1129 | } | 1129 | } |
| 1130 | return null; | 1130 | return null; |
| 1131 | } | 1131 | } |
| 1132 | if (builtin.os == .windows) { | 1132 | if (builtin.os.tag == .windows) { |
| 1133 | @compileError("std.os.getenv is unavailable for Windows because environment string is in WTF-16 format. See std.process.getEnvVarOwned for cross-platform API or std.os.getenvW for Windows-specific API."); | 1133 | @compileError("std.os.getenv is unavailable for Windows because environment string is in WTF-16 format. See std.process.getEnvVarOwned for cross-platform API or std.os.getenvW for Windows-specific API."); |
| 1134 | } | 1134 | } |
| 1135 | // TODO see https://github.com/ziglang/zig/issues/4524 | 1135 | // TODO see https://github.com/ziglang/zig/issues/4524 |
| ... | @@ -1158,7 +1158,7 @@ pub fn getenvZ(key: [*:0]const u8) ?[]const u8 { | ... | @@ -1158,7 +1158,7 @@ pub fn getenvZ(key: [*:0]const u8) ?[]const u8 { |
| 1158 | const value = system.getenv(key) orelse return null; | 1158 | const value = system.getenv(key) orelse return null; |
| 1159 | return mem.toSliceConst(u8, value); | 1159 | return mem.toSliceConst(u8, value); |
| 1160 | } | 1160 | } |
| 1161 | if (builtin.os == .windows) { | 1161 | if (builtin.os.tag == .windows) { |
| 1162 | @compileError("std.os.getenvZ is unavailable for Windows because environment string is in WTF-16 format. See std.process.getEnvVarOwned for cross-platform API or std.os.getenvW for Windows-specific API."); | 1162 | @compileError("std.os.getenvZ is unavailable for Windows because environment string is in WTF-16 format. See std.process.getEnvVarOwned for cross-platform API or std.os.getenvW for Windows-specific API."); |
| 1163 | } | 1163 | } |
| 1164 | return getenv(mem.toSliceConst(u8, key)); | 1164 | return getenv(mem.toSliceConst(u8, key)); |
| ... | @@ -1167,7 +1167,7 @@ pub fn getenvZ(key: [*:0]const u8) ?[]const u8 { | ... | @@ -1167,7 +1167,7 @@ pub fn getenvZ(key: [*:0]const u8) ?[]const u8 { |
| 1167 | /// Windows-only. Get an environment variable with a null-terminated, WTF-16 encoded name. | 1167 | /// Windows-only. Get an environment variable with a null-terminated, WTF-16 encoded name. |
| 1168 | /// See also `getenv`. | 1168 | /// See also `getenv`. |
| 1169 | pub fn getenvW(key: [*:0]const u16) ?[:0]const u16 { | 1169 | pub fn getenvW(key: [*:0]const u16) ?[:0]const u16 { |
| 1170 | if (builtin.os != .windows) { | 1170 | if (builtin.os.tag != .windows) { |
| 1171 | @compileError("std.os.getenvW is a Windows-only API"); | 1171 | @compileError("std.os.getenvW is a Windows-only API"); |
| 1172 | } | 1172 | } |
| 1173 | const key_slice = mem.toSliceConst(u16, key); | 1173 | const key_slice = mem.toSliceConst(u16, key); |
| ... | @@ -1199,7 +1199,7 @@ pub const GetCwdError = error{ | ... | @@ -1199,7 +1199,7 @@ pub const GetCwdError = error{ |
| 1199 | 1199 | ||
| 1200 | /// The result is a slice of out_buffer, indexed from 0. | 1200 | /// The result is a slice of out_buffer, indexed from 0. |
| 1201 | pub fn getcwd(out_buffer: []u8) GetCwdError![]u8 { | 1201 | pub fn getcwd(out_buffer: []u8) GetCwdError![]u8 { |
| 1202 | if (builtin.os == .windows) { | 1202 | if (builtin.os.tag == .windows) { |
| 1203 | return windows.GetCurrentDirectory(out_buffer); | 1203 | return windows.GetCurrentDirectory(out_buffer); |
| 1204 | } | 1204 | } |
| 1205 | 1205 | ||
| ... | @@ -1240,7 +1240,7 @@ pub const SymLinkError = error{ | ... | @@ -1240,7 +1240,7 @@ pub const SymLinkError = error{ |
| 1240 | /// If `sym_link_path` exists, it will not be overwritten. | 1240 | /// If `sym_link_path` exists, it will not be overwritten. |
| 1241 | /// See also `symlinkC` and `symlinkW`. | 1241 | /// See also `symlinkC` and `symlinkW`. |
| 1242 | pub fn symlink(target_path: []const u8, sym_link_path: []const u8) SymLinkError!void { | 1242 | pub fn symlink(target_path: []const u8, sym_link_path: []const u8) SymLinkError!void { |
| 1243 | if (builtin.os == .windows) { | 1243 | if (builtin.os.tag == .windows) { |
| 1244 | const target_path_w = try windows.sliceToPrefixedFileW(target_path); | 1244 | const target_path_w = try windows.sliceToPrefixedFileW(target_path); |
| 1245 | const sym_link_path_w = try windows.sliceToPrefixedFileW(sym_link_path); | 1245 | const sym_link_path_w = try windows.sliceToPrefixedFileW(sym_link_path); |
| 1246 | return windows.CreateSymbolicLinkW(&sym_link_path_w, &target_path_w, 0); | 1246 | return windows.CreateSymbolicLinkW(&sym_link_path_w, &target_path_w, 0); |
| ... | @@ -1254,7 +1254,7 @@ pub fn symlink(target_path: []const u8, sym_link_path: []const u8) SymLinkError! | ... | @@ -1254,7 +1254,7 @@ pub fn symlink(target_path: []const u8, sym_link_path: []const u8) SymLinkError! |
| 1254 | /// This is the same as `symlink` except the parameters are null-terminated pointers. | 1254 | /// This is the same as `symlink` except the parameters are null-terminated pointers. |
| 1255 | /// See also `symlink`. | 1255 | /// See also `symlink`. |
| 1256 | pub fn symlinkC(target_path: [*:0]const u8, sym_link_path: [*:0]const u8) SymLinkError!void { | 1256 | pub fn symlinkC(target_path: [*:0]const u8, sym_link_path: [*:0]const u8) SymLinkError!void { |
| 1257 | if (builtin.os == .windows) { | 1257 | if (builtin.os.tag == .windows) { |
| 1258 | const target_path_w = try windows.cStrToPrefixedFileW(target_path); | 1258 | const target_path_w = try windows.cStrToPrefixedFileW(target_path); |
| 1259 | const sym_link_path_w = try windows.cStrToPrefixedFileW(sym_link_path); | 1259 | const sym_link_path_w = try windows.cStrToPrefixedFileW(sym_link_path); |
| 1260 | return windows.CreateSymbolicLinkW(&sym_link_path_w, &target_path_w, 0); | 1260 | return windows.CreateSymbolicLinkW(&sym_link_path_w, &target_path_w, 0); |
| ... | @@ -1329,7 +1329,7 @@ pub const UnlinkError = error{ | ... | @@ -1329,7 +1329,7 @@ pub const UnlinkError = error{ |
| 1329 | /// Delete a name and possibly the file it refers to. | 1329 | /// Delete a name and possibly the file it refers to. |
| 1330 | /// See also `unlinkC`. | 1330 | /// See also `unlinkC`. |
| 1331 | pub fn unlink(file_path: []const u8) UnlinkError!void { | 1331 | pub fn unlink(file_path: []const u8) UnlinkError!void { |
| 1332 | if (builtin.os == .windows) { | 1332 | if (builtin.os.tag == .windows) { |
| 1333 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); | 1333 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); |
| 1334 | return windows.DeleteFileW(&file_path_w); | 1334 | return windows.DeleteFileW(&file_path_w); |
| 1335 | } else { | 1335 | } else { |
| ... | @@ -1340,7 +1340,7 @@ pub fn unlink(file_path: []const u8) UnlinkError!void { | ... | @@ -1340,7 +1340,7 @@ pub fn unlink(file_path: []const u8) UnlinkError!void { |
| 1340 | 1340 | ||
| 1341 | /// Same as `unlink` except the parameter is a null terminated UTF8-encoded string. | 1341 | /// Same as `unlink` except the parameter is a null terminated UTF8-encoded string. |
| 1342 | pub fn unlinkC(file_path: [*:0]const u8) UnlinkError!void { | 1342 | pub fn unlinkC(file_path: [*:0]const u8) UnlinkError!void { |
| 1343 | if (builtin.os == .windows) { | 1343 | if (builtin.os.tag == .windows) { |
| 1344 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); | 1344 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); |
| 1345 | return windows.DeleteFileW(&file_path_w); | 1345 | return windows.DeleteFileW(&file_path_w); |
| 1346 | } | 1346 | } |
| ... | @@ -1372,7 +1372,7 @@ pub const UnlinkatError = UnlinkError || error{ | ... | @@ -1372,7 +1372,7 @@ pub const UnlinkatError = UnlinkError || error{ |
| 1372 | /// Asserts that the path parameter has no null bytes. | 1372 | /// Asserts that the path parameter has no null bytes. |
| 1373 | pub fn unlinkat(dirfd: fd_t, file_path: []const u8, flags: u32) UnlinkatError!void { | 1373 | pub fn unlinkat(dirfd: fd_t, file_path: []const u8, flags: u32) UnlinkatError!void { |
| 1374 | if (std.debug.runtime_safety) for (file_path) |byte| assert(byte != 0); | 1374 | if (std.debug.runtime_safety) for (file_path) |byte| assert(byte != 0); |
| 1375 | if (builtin.os == .windows) { | 1375 | if (builtin.os.tag == .windows) { |
| 1376 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); | 1376 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); |
| 1377 | return unlinkatW(dirfd, &file_path_w, flags); | 1377 | return unlinkatW(dirfd, &file_path_w, flags); |
| 1378 | } | 1378 | } |
| ... | @@ -1382,7 +1382,7 @@ pub fn unlinkat(dirfd: fd_t, file_path: []const u8, flags: u32) UnlinkatError!vo | ... | @@ -1382,7 +1382,7 @@ pub fn unlinkat(dirfd: fd_t, file_path: []const u8, flags: u32) UnlinkatError!vo |
| 1382 | 1382 | ||
| 1383 | /// Same as `unlinkat` but `file_path` is a null-terminated string. | 1383 | /// Same as `unlinkat` but `file_path` is a null-terminated string. |
| 1384 | pub fn unlinkatC(dirfd: fd_t, file_path_c: [*:0]const u8, flags: u32) UnlinkatError!void { | 1384 | pub fn unlinkatC(dirfd: fd_t, file_path_c: [*:0]const u8, flags: u32) UnlinkatError!void { |
| 1385 | if (builtin.os == .windows) { | 1385 | if (builtin.os.tag == .windows) { |
| 1386 | const file_path_w = try windows.cStrToPrefixedFileW(file_path_c); | 1386 | const file_path_w = try windows.cStrToPrefixedFileW(file_path_c); |
| 1387 | return unlinkatW(dirfd, &file_path_w, flags); | 1387 | return unlinkatW(dirfd, &file_path_w, flags); |
| 1388 | } | 1388 | } |
| ... | @@ -1493,7 +1493,7 @@ const RenameError = error{ | ... | @@ -1493,7 +1493,7 @@ const RenameError = error{ |
| 1493 | 1493 | ||
| 1494 | /// Change the name or location of a file. | 1494 | /// Change the name or location of a file. |
| 1495 | pub fn rename(old_path: []const u8, new_path: []const u8) RenameError!void { | 1495 | pub fn rename(old_path: []const u8, new_path: []const u8) RenameError!void { |
| 1496 | if (builtin.os == .windows) { | 1496 | if (builtin.os.tag == .windows) { |
| 1497 | const old_path_w = try windows.sliceToPrefixedFileW(old_path); | 1497 | const old_path_w = try windows.sliceToPrefixedFileW(old_path); |
| 1498 | const new_path_w = try windows.sliceToPrefixedFileW(new_path); | 1498 | const new_path_w = try windows.sliceToPrefixedFileW(new_path); |
| 1499 | return renameW(&old_path_w, &new_path_w); | 1499 | return renameW(&old_path_w, &new_path_w); |
| ... | @@ -1506,7 +1506,7 @@ pub fn rename(old_path: []const u8, new_path: []const u8) RenameError!void { | ... | @@ -1506,7 +1506,7 @@ pub fn rename(old_path: []const u8, new_path: []const u8) RenameError!void { |
| 1506 | 1506 | ||
| 1507 | /// Same as `rename` except the parameters are null-terminated byte arrays. | 1507 | /// Same as `rename` except the parameters are null-terminated byte arrays. |
| 1508 | pub fn renameC(old_path: [*:0]const u8, new_path: [*:0]const u8) RenameError!void { | 1508 | pub fn renameC(old_path: [*:0]const u8, new_path: [*:0]const u8) RenameError!void { |
| 1509 | if (builtin.os == .windows) { | 1509 | if (builtin.os.tag == .windows) { |
| 1510 | const old_path_w = try windows.cStrToPrefixedFileW(old_path); | 1510 | const old_path_w = try windows.cStrToPrefixedFileW(old_path); |
| 1511 | const new_path_w = try windows.cStrToPrefixedFileW(new_path); | 1511 | const new_path_w = try windows.cStrToPrefixedFileW(new_path); |
| 1512 | return renameW(&old_path_w, &new_path_w); | 1512 | return renameW(&old_path_w, &new_path_w); |
| ... | @@ -1561,7 +1561,7 @@ pub const MakeDirError = error{ | ... | @@ -1561,7 +1561,7 @@ pub const MakeDirError = error{ |
| 1561 | /// Create a directory. | 1561 | /// Create a directory. |
| 1562 | /// `mode` is ignored on Windows. | 1562 | /// `mode` is ignored on Windows. |
| 1563 | pub fn mkdir(dir_path: []const u8, mode: u32) MakeDirError!void { | 1563 | pub fn mkdir(dir_path: []const u8, mode: u32) MakeDirError!void { |
| 1564 | if (builtin.os == .windows) { | 1564 | if (builtin.os.tag == .windows) { |
| 1565 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); | 1565 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); |
| 1566 | return windows.CreateDirectoryW(&dir_path_w, null); | 1566 | return windows.CreateDirectoryW(&dir_path_w, null); |
| 1567 | } else { | 1567 | } else { |
| ... | @@ -1572,7 +1572,7 @@ pub fn mkdir(dir_path: []const u8, mode: u32) MakeDirError!void { | ... | @@ -1572,7 +1572,7 @@ pub fn mkdir(dir_path: []const u8, mode: u32) MakeDirError!void { |
| 1572 | 1572 | ||
| 1573 | /// Same as `mkdir` but the parameter is a null-terminated UTF8-encoded string. | 1573 | /// Same as `mkdir` but the parameter is a null-terminated UTF8-encoded string. |
| 1574 | pub fn mkdirC(dir_path: [*:0]const u8, mode: u32) MakeDirError!void { | 1574 | pub fn mkdirC(dir_path: [*:0]const u8, mode: u32) MakeDirError!void { |
| 1575 | if (builtin.os == .windows) { | 1575 | if (builtin.os.tag == .windows) { |
| 1576 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); | 1576 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); |
| 1577 | return windows.CreateDirectoryW(&dir_path_w, null); | 1577 | return windows.CreateDirectoryW(&dir_path_w, null); |
| 1578 | } | 1578 | } |
| ... | @@ -1611,7 +1611,7 @@ pub const DeleteDirError = error{ | ... | @@ -1611,7 +1611,7 @@ pub const DeleteDirError = error{ |
| 1611 | 1611 | ||
| 1612 | /// Deletes an empty directory. | 1612 | /// Deletes an empty directory. |
| 1613 | pub fn rmdir(dir_path: []const u8) DeleteDirError!void { | 1613 | pub fn rmdir(dir_path: []const u8) DeleteDirError!void { |
| 1614 | if (builtin.os == .windows) { | 1614 | if (builtin.os.tag == .windows) { |
| 1615 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); | 1615 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); |
| 1616 | return windows.RemoveDirectoryW(&dir_path_w); | 1616 | return windows.RemoveDirectoryW(&dir_path_w); |
| 1617 | } else { | 1617 | } else { |
| ... | @@ -1622,7 +1622,7 @@ pub fn rmdir(dir_path: []const u8) DeleteDirError!void { | ... | @@ -1622,7 +1622,7 @@ pub fn rmdir(dir_path: []const u8) DeleteDirError!void { |
| 1622 | 1622 | ||
| 1623 | /// Same as `rmdir` except the parameter is null-terminated. | 1623 | /// Same as `rmdir` except the parameter is null-terminated. |
| 1624 | pub fn rmdirC(dir_path: [*:0]const u8) DeleteDirError!void { | 1624 | pub fn rmdirC(dir_path: [*:0]const u8) DeleteDirError!void { |
| 1625 | if (builtin.os == .windows) { | 1625 | if (builtin.os.tag == .windows) { |
| 1626 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); | 1626 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); |
| 1627 | return windows.RemoveDirectoryW(&dir_path_w); | 1627 | return windows.RemoveDirectoryW(&dir_path_w); |
| 1628 | } | 1628 | } |
| ... | @@ -1658,7 +1658,7 @@ pub const ChangeCurDirError = error{ | ... | @@ -1658,7 +1658,7 @@ pub const ChangeCurDirError = error{ |
| 1658 | /// Changes the current working directory of the calling process. | 1658 | /// Changes the current working directory of the calling process. |
| 1659 | /// `dir_path` is recommended to be a UTF-8 encoded string. | 1659 | /// `dir_path` is recommended to be a UTF-8 encoded string. |
| 1660 | pub fn chdir(dir_path: []const u8) ChangeCurDirError!void { | 1660 | pub fn chdir(dir_path: []const u8) ChangeCurDirError!void { |
| 1661 | if (builtin.os == .windows) { | 1661 | if (builtin.os.tag == .windows) { |
| 1662 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); | 1662 | const dir_path_w = try windows.sliceToPrefixedFileW(dir_path); |
| 1663 | @compileError("TODO implement chdir for Windows"); | 1663 | @compileError("TODO implement chdir for Windows"); |
| 1664 | } else { | 1664 | } else { |
| ... | @@ -1669,7 +1669,7 @@ pub fn chdir(dir_path: []const u8) ChangeCurDirError!void { | ... | @@ -1669,7 +1669,7 @@ pub fn chdir(dir_path: []const u8) ChangeCurDirError!void { |
| 1669 | 1669 | ||
| 1670 | /// Same as `chdir` except the parameter is null-terminated. | 1670 | /// Same as `chdir` except the parameter is null-terminated. |
| 1671 | pub fn chdirC(dir_path: [*:0]const u8) ChangeCurDirError!void { | 1671 | pub fn chdirC(dir_path: [*:0]const u8) ChangeCurDirError!void { |
| 1672 | if (builtin.os == .windows) { | 1672 | if (builtin.os.tag == .windows) { |
| 1673 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); | 1673 | const dir_path_w = try windows.cStrToPrefixedFileW(dir_path); |
| 1674 | @compileError("TODO implement chdir for Windows"); | 1674 | @compileError("TODO implement chdir for Windows"); |
| 1675 | } | 1675 | } |
| ... | @@ -1700,7 +1700,7 @@ pub const ReadLinkError = error{ | ... | @@ -1700,7 +1700,7 @@ pub const ReadLinkError = error{ |
| 1700 | /// Read value of a symbolic link. | 1700 | /// Read value of a symbolic link. |
| 1701 | /// The return value is a slice of `out_buffer` from index 0. | 1701 | /// The return value is a slice of `out_buffer` from index 0. |
| 1702 | pub fn readlink(file_path: []const u8, out_buffer: []u8) ReadLinkError![]u8 { | 1702 | pub fn readlink(file_path: []const u8, out_buffer: []u8) ReadLinkError![]u8 { |
| 1703 | if (builtin.os == .windows) { | 1703 | if (builtin.os.tag == .windows) { |
| 1704 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); | 1704 | const file_path_w = try windows.sliceToPrefixedFileW(file_path); |
| 1705 | @compileError("TODO implement readlink for Windows"); | 1705 | @compileError("TODO implement readlink for Windows"); |
| 1706 | } else { | 1706 | } else { |
| ... | @@ -1711,7 +1711,7 @@ pub fn readlink(file_path: []const u8, out_buffer: []u8) ReadLinkError![]u8 { | ... | @@ -1711,7 +1711,7 @@ pub fn readlink(file_path: []const u8, out_buffer: []u8) ReadLinkError![]u8 { |
| 1711 | 1711 | ||
| 1712 | /// Same as `readlink` except `file_path` is null-terminated. | 1712 | /// Same as `readlink` except `file_path` is null-terminated. |
| 1713 | pub fn readlinkC(file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 { | 1713 | pub fn readlinkC(file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 { |
| 1714 | if (builtin.os == .windows) { | 1714 | if (builtin.os.tag == .windows) { |
| 1715 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); | 1715 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); |
| 1716 | @compileError("TODO implement readlink for Windows"); | 1716 | @compileError("TODO implement readlink for Windows"); |
| 1717 | } | 1717 | } |
| ... | @@ -1732,7 +1732,7 @@ pub fn readlinkC(file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 | ... | @@ -1732,7 +1732,7 @@ pub fn readlinkC(file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 |
| 1732 | } | 1732 | } |
| 1733 | 1733 | ||
| 1734 | pub fn readlinkatC(dirfd: fd_t, file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 { | 1734 | pub fn readlinkatC(dirfd: fd_t, file_path: [*:0]const u8, out_buffer: []u8) ReadLinkError![]u8 { |
| 1735 | if (builtin.os == .windows) { | 1735 | if (builtin.os.tag == .windows) { |
| 1736 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); | 1736 | const file_path_w = try windows.cStrToPrefixedFileW(file_path); |
| 1737 | @compileError("TODO implement readlink for Windows"); | 1737 | @compileError("TODO implement readlink for Windows"); |
| 1738 | } | 1738 | } |
| ... | @@ -1800,7 +1800,7 @@ pub fn setregid(rgid: u32, egid: u32) SetIdError!void { | ... | @@ -1800,7 +1800,7 @@ pub fn setregid(rgid: u32, egid: u32) SetIdError!void { |
| 1800 | 1800 | ||
| 1801 | /// Test whether a file descriptor refers to a terminal. | 1801 | /// Test whether a file descriptor refers to a terminal. |
| 1802 | pub fn isatty(handle: fd_t) bool { | 1802 | pub fn isatty(handle: fd_t) bool { |
| 1803 | if (builtin.os == .windows) { | 1803 | if (builtin.os.tag == .windows) { |
| 1804 | if (isCygwinPty(handle)) | 1804 | if (isCygwinPty(handle)) |
| 1805 | return true; | 1805 | return true; |
| 1806 | 1806 | ||
| ... | @@ -1810,7 +1810,7 @@ pub fn isatty(handle: fd_t) bool { | ... | @@ -1810,7 +1810,7 @@ pub fn isatty(handle: fd_t) bool { |
| 1810 | if (builtin.link_libc) { | 1810 | if (builtin.link_libc) { |
| 1811 | return system.isatty(handle) != 0; | 1811 | return system.isatty(handle) != 0; |
| 1812 | } | 1812 | } |
| 1813 | if (builtin.os == .wasi) { | 1813 | if (builtin.os.tag == .wasi) { |
| 1814 | var statbuf: fdstat_t = undefined; | 1814 | var statbuf: fdstat_t = undefined; |
| 1815 | const err = system.fd_fdstat_get(handle, &statbuf); | 1815 | const err = system.fd_fdstat_get(handle, &statbuf); |
| 1816 | if (err != 0) { | 1816 | if (err != 0) { |
| ... | @@ -1828,7 +1828,7 @@ pub fn isatty(handle: fd_t) bool { | ... | @@ -1828,7 +1828,7 @@ pub fn isatty(handle: fd_t) bool { |
| 1828 | 1828 | ||
| 1829 | return true; | 1829 | return true; |
| 1830 | } | 1830 | } |
| 1831 | if (builtin.os == .linux) { | 1831 | if (builtin.os.tag == .linux) { |
| 1832 | var wsz: linux.winsize = undefined; | 1832 | var wsz: linux.winsize = undefined; |
| 1833 | return linux.syscall3(linux.SYS_ioctl, @bitCast(usize, @as(isize, handle)), linux.TIOCGWINSZ, @ptrToInt(&wsz)) == 0; | 1833 | return linux.syscall3(linux.SYS_ioctl, @bitCast(usize, @as(isize, handle)), linux.TIOCGWINSZ, @ptrToInt(&wsz)) == 0; |
| 1834 | } | 1834 | } |
| ... | @@ -1836,7 +1836,7 @@ pub fn isatty(handle: fd_t) bool { | ... | @@ -1836,7 +1836,7 @@ pub fn isatty(handle: fd_t) bool { |
| 1836 | } | 1836 | } |
| 1837 | 1837 | ||
| 1838 | pub fn isCygwinPty(handle: fd_t) bool { | 1838 | pub fn isCygwinPty(handle: fd_t) bool { |
| 1839 | if (builtin.os != .windows) return false; | 1839 | if (builtin.os.tag != .windows) return false; |
| 1840 | 1840 | ||
| 1841 | const size = @sizeOf(windows.FILE_NAME_INFO); | 1841 | const size = @sizeOf(windows.FILE_NAME_INFO); |
| 1842 | var name_info_bytes align(@alignOf(windows.FILE_NAME_INFO)) = [_]u8{0} ** (size + windows.MAX_PATH); | 1842 | var name_info_bytes align(@alignOf(windows.FILE_NAME_INFO)) = [_]u8{0} ** (size + windows.MAX_PATH); |
| ... | @@ -2589,7 +2589,7 @@ pub const AccessError = error{ | ... | @@ -2589,7 +2589,7 @@ pub const AccessError = error{ |
| 2589 | /// check user's permissions for a file | 2589 | /// check user's permissions for a file |
| 2590 | /// TODO currently this assumes `mode` is `F_OK` on Windows. | 2590 | /// TODO currently this assumes `mode` is `F_OK` on Windows. |
| 2591 | pub fn access(path: []const u8, mode: u32) AccessError!void { | 2591 | pub fn access(path: []const u8, mode: u32) AccessError!void { |
| 2592 | if (builtin.os == .windows) { | 2592 | if (builtin.os.tag == .windows) { |
| 2593 | const path_w = try windows.sliceToPrefixedFileW(path); | 2593 | const path_w = try windows.sliceToPrefixedFileW(path); |
| 2594 | _ = try windows.GetFileAttributesW(&path_w); | 2594 | _ = try windows.GetFileAttributesW(&path_w); |
| 2595 | return; | 2595 | return; |
| ... | @@ -2603,7 +2603,7 @@ pub const accessC = accessZ; | ... | @@ -2603,7 +2603,7 @@ pub const accessC = accessZ; |
| 2603 | 2603 | ||
| 2604 | /// Same as `access` except `path` is null-terminated. | 2604 | /// Same as `access` except `path` is null-terminated. |
| 2605 | pub fn accessZ(path: [*:0]const u8, mode: u32) AccessError!void { | 2605 | pub fn accessZ(path: [*:0]const u8, mode: u32) AccessError!void { |
| 2606 | if (builtin.os == .windows) { | 2606 | if (builtin.os.tag == .windows) { |
| 2607 | const path_w = try windows.cStrToPrefixedFileW(path); | 2607 | const path_w = try windows.cStrToPrefixedFileW(path); |
| 2608 | _ = try windows.GetFileAttributesW(&path_w); | 2608 | _ = try windows.GetFileAttributesW(&path_w); |
| 2609 | return; | 2609 | return; |
| ... | @@ -2644,7 +2644,7 @@ pub fn accessW(path: [*:0]const u16, mode: u32) windows.GetFileAttributesError!v | ... | @@ -2644,7 +2644,7 @@ pub fn accessW(path: [*:0]const u16, mode: u32) windows.GetFileAttributesError!v |
| 2644 | /// Check user's permissions for a file, based on an open directory handle. | 2644 | /// Check user's permissions for a file, based on an open directory handle. |
| 2645 | /// TODO currently this ignores `mode` and `flags` on Windows. | 2645 | /// TODO currently this ignores `mode` and `flags` on Windows. |
| 2646 | pub fn faccessat(dirfd: fd_t, path: []const u8, mode: u32, flags: u32) AccessError!void { | 2646 | pub fn faccessat(dirfd: fd_t, path: []const u8, mode: u32, flags: u32) AccessError!void { |
| 2647 | if (builtin.os == .windows) { | 2647 | if (builtin.os.tag == .windows) { |
| 2648 | const path_w = try windows.sliceToPrefixedFileW(path); | 2648 | const path_w = try windows.sliceToPrefixedFileW(path); |
| 2649 | return faccessatW(dirfd, &path_w, mode, flags); | 2649 | return faccessatW(dirfd, &path_w, mode, flags); |
| 2650 | } | 2650 | } |
| ... | @@ -2654,7 +2654,7 @@ pub fn faccessat(dirfd: fd_t, path: []const u8, mode: u32, flags: u32) AccessErr | ... | @@ -2654,7 +2654,7 @@ pub fn faccessat(dirfd: fd_t, path: []const u8, mode: u32, flags: u32) AccessErr |
| 2654 | 2654 | ||
| 2655 | /// Same as `faccessat` except the path parameter is null-terminated. | 2655 | /// Same as `faccessat` except the path parameter is null-terminated. |
| 2656 | pub fn faccessatZ(dirfd: fd_t, path: [*:0]const u8, mode: u32, flags: u32) AccessError!void { | 2656 | pub fn faccessatZ(dirfd: fd_t, path: [*:0]const u8, mode: u32, flags: u32) AccessError!void { |
| 2657 | if (builtin.os == .windows) { | 2657 | if (builtin.os.tag == .windows) { |
| 2658 | const path_w = try windows.cStrToPrefixedFileW(path); | 2658 | const path_w = try windows.cStrToPrefixedFileW(path); |
| 2659 | return faccessatW(dirfd, &path_w, mode, flags); | 2659 | return faccessatW(dirfd, &path_w, mode, flags); |
| 2660 | } | 2660 | } |
| ... | @@ -2811,7 +2811,7 @@ pub const SeekError = error{Unseekable} || UnexpectedError; | ... | @@ -2811,7 +2811,7 @@ pub const SeekError = error{Unseekable} || UnexpectedError; |
| 2811 | 2811 | ||
| 2812 | /// Repositions read/write file offset relative to the beginning. | 2812 | /// Repositions read/write file offset relative to the beginning. |
| 2813 | pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { | 2813 | pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { |
| 2814 | if (builtin.os == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { | 2814 | if (builtin.os.tag == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { |
| 2815 | var result: u64 = undefined; | 2815 | var result: u64 = undefined; |
| 2816 | switch (errno(system.llseek(fd, offset, &result, SEEK_SET))) { | 2816 | switch (errno(system.llseek(fd, offset, &result, SEEK_SET))) { |
| 2817 | 0 => return, | 2817 | 0 => return, |
| ... | @@ -2823,7 +2823,7 @@ pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { | ... | @@ -2823,7 +2823,7 @@ pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { |
| 2823 | else => |err| return unexpectedErrno(err), | 2823 | else => |err| return unexpectedErrno(err), |
| 2824 | } | 2824 | } |
| 2825 | } | 2825 | } |
| 2826 | if (builtin.os == .windows) { | 2826 | if (builtin.os.tag == .windows) { |
| 2827 | return windows.SetFilePointerEx_BEGIN(fd, offset); | 2827 | return windows.SetFilePointerEx_BEGIN(fd, offset); |
| 2828 | } | 2828 | } |
| 2829 | const ipos = @bitCast(i64, offset); // the OS treats this as unsigned | 2829 | const ipos = @bitCast(i64, offset); // the OS treats this as unsigned |
| ... | @@ -2840,7 +2840,7 @@ pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { | ... | @@ -2840,7 +2840,7 @@ pub fn lseek_SET(fd: fd_t, offset: u64) SeekError!void { |
| 2840 | 2840 | ||
| 2841 | /// Repositions read/write file offset relative to the current offset. | 2841 | /// Repositions read/write file offset relative to the current offset. |
| 2842 | pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { | 2842 | pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { |
| 2843 | if (builtin.os == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { | 2843 | if (builtin.os.tag == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { |
| 2844 | var result: u64 = undefined; | 2844 | var result: u64 = undefined; |
| 2845 | switch (errno(system.llseek(fd, @bitCast(u64, offset), &result, SEEK_CUR))) { | 2845 | switch (errno(system.llseek(fd, @bitCast(u64, offset), &result, SEEK_CUR))) { |
| 2846 | 0 => return, | 2846 | 0 => return, |
| ... | @@ -2852,7 +2852,7 @@ pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { | ... | @@ -2852,7 +2852,7 @@ pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { |
| 2852 | else => |err| return unexpectedErrno(err), | 2852 | else => |err| return unexpectedErrno(err), |
| 2853 | } | 2853 | } |
| 2854 | } | 2854 | } |
| 2855 | if (builtin.os == .windows) { | 2855 | if (builtin.os.tag == .windows) { |
| 2856 | return windows.SetFilePointerEx_CURRENT(fd, offset); | 2856 | return windows.SetFilePointerEx_CURRENT(fd, offset); |
| 2857 | } | 2857 | } |
| 2858 | switch (errno(system.lseek(fd, offset, SEEK_CUR))) { | 2858 | switch (errno(system.lseek(fd, offset, SEEK_CUR))) { |
| ... | @@ -2868,7 +2868,7 @@ pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { | ... | @@ -2868,7 +2868,7 @@ pub fn lseek_CUR(fd: fd_t, offset: i64) SeekError!void { |
| 2868 | 2868 | ||
| 2869 | /// Repositions read/write file offset relative to the end. | 2869 | /// Repositions read/write file offset relative to the end. |
| 2870 | pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { | 2870 | pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { |
| 2871 | if (builtin.os == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { | 2871 | if (builtin.os.tag == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { |
| 2872 | var result: u64 = undefined; | 2872 | var result: u64 = undefined; |
| 2873 | switch (errno(system.llseek(fd, @bitCast(u64, offset), &result, SEEK_END))) { | 2873 | switch (errno(system.llseek(fd, @bitCast(u64, offset), &result, SEEK_END))) { |
| 2874 | 0 => return, | 2874 | 0 => return, |
| ... | @@ -2880,7 +2880,7 @@ pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { | ... | @@ -2880,7 +2880,7 @@ pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { |
| 2880 | else => |err| return unexpectedErrno(err), | 2880 | else => |err| return unexpectedErrno(err), |
| 2881 | } | 2881 | } |
| 2882 | } | 2882 | } |
| 2883 | if (builtin.os == .windows) { | 2883 | if (builtin.os.tag == .windows) { |
| 2884 | return windows.SetFilePointerEx_END(fd, offset); | 2884 | return windows.SetFilePointerEx_END(fd, offset); |
| 2885 | } | 2885 | } |
| 2886 | switch (errno(system.lseek(fd, offset, SEEK_END))) { | 2886 | switch (errno(system.lseek(fd, offset, SEEK_END))) { |
| ... | @@ -2896,7 +2896,7 @@ pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { | ... | @@ -2896,7 +2896,7 @@ pub fn lseek_END(fd: fd_t, offset: i64) SeekError!void { |
| 2896 | 2896 | ||
| 2897 | /// Returns the read/write file offset relative to the beginning. | 2897 | /// Returns the read/write file offset relative to the beginning. |
| 2898 | pub fn lseek_CUR_get(fd: fd_t) SeekError!u64 { | 2898 | pub fn lseek_CUR_get(fd: fd_t) SeekError!u64 { |
| 2899 | if (builtin.os == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { | 2899 | if (builtin.os.tag == .linux and !builtin.link_libc and @sizeOf(usize) == 4) { |
| 2900 | var result: u64 = undefined; | 2900 | var result: u64 = undefined; |
| 2901 | switch (errno(system.llseek(fd, 0, &result, SEEK_CUR))) { | 2901 | switch (errno(system.llseek(fd, 0, &result, SEEK_CUR))) { |
| 2902 | 0 => return result, | 2902 | 0 => return result, |
| ... | @@ -2908,7 +2908,7 @@ pub fn lseek_CUR_get(fd: fd_t) SeekError!u64 { | ... | @@ -2908,7 +2908,7 @@ pub fn lseek_CUR_get(fd: fd_t) SeekError!u64 { |
| 2908 | else => |err| return unexpectedErrno(err), | 2908 | else => |err| return unexpectedErrno(err), |
| 2909 | } | 2909 | } |
| 2910 | } | 2910 | } |
| 2911 | if (builtin.os == .windows) { | 2911 | if (builtin.os.tag == .windows) { |
| 2912 | return windows.SetFilePointerEx_CURRENT_get(fd); | 2912 | return windows.SetFilePointerEx_CURRENT_get(fd); |
| 2913 | } | 2913 | } |
| 2914 | const rc = system.lseek(fd, 0, SEEK_CUR); | 2914 | const rc = system.lseek(fd, 0, SEEK_CUR); |
| ... | @@ -2957,7 +2957,7 @@ pub const RealPathError = error{ | ... | @@ -2957,7 +2957,7 @@ pub const RealPathError = error{ |
| 2957 | /// The return value is a slice of `out_buffer`, but not necessarily from the beginning. | 2957 | /// The return value is a slice of `out_buffer`, but not necessarily from the beginning. |
| 2958 | /// See also `realpathC` and `realpathW`. | 2958 | /// See also `realpathC` and `realpathW`. |
| 2959 | pub fn realpath(pathname: []const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathError![]u8 { | 2959 | pub fn realpath(pathname: []const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathError![]u8 { |
| 2960 | if (builtin.os == .windows) { | 2960 | if (builtin.os.tag == .windows) { |
| 2961 | const pathname_w = try windows.sliceToPrefixedFileW(pathname); | 2961 | const pathname_w = try windows.sliceToPrefixedFileW(pathname); |
| 2962 | return realpathW(&pathname_w, out_buffer); | 2962 | return realpathW(&pathname_w, out_buffer); |
| 2963 | } | 2963 | } |
| ... | @@ -2967,11 +2967,11 @@ pub fn realpath(pathname: []const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathE | ... | @@ -2967,11 +2967,11 @@ pub fn realpath(pathname: []const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathE |
| 2967 | 2967 | ||
| 2968 | /// Same as `realpath` except `pathname` is null-terminated. | 2968 | /// Same as `realpath` except `pathname` is null-terminated. |
| 2969 | pub fn realpathC(pathname: [*:0]const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathError![]u8 { | 2969 | pub fn realpathC(pathname: [*:0]const u8, out_buffer: *[MAX_PATH_BYTES]u8) RealPathError![]u8 { |
| 2970 | if (builtin.os == .windows) { | 2970 | if (builtin.os.tag == .windows) { |
| 2971 | const pathname_w = try windows.cStrToPrefixedFileW(pathname); | 2971 | const pathname_w = try windows.cStrToPrefixedFileW(pathname); |
| 2972 | return realpathW(&pathname_w, out_buffer); | 2972 | return realpathW(&pathname_w, out_buffer); |
| 2973 | } | 2973 | } |
| 2974 | if (builtin.os == .linux and !builtin.link_libc) { | 2974 | if (builtin.os.tag == .linux and !builtin.link_libc) { |
| 2975 | const fd = try openC(pathname, linux.O_PATH | linux.O_NONBLOCK | linux.O_CLOEXEC, 0); | 2975 | const fd = try openC(pathname, linux.O_PATH | linux.O_NONBLOCK | linux.O_CLOEXEC, 0); |
| 2976 | defer close(fd); | 2976 | defer close(fd); |
| 2977 | 2977 | ||
| ... | @@ -3121,7 +3121,7 @@ pub fn dl_iterate_phdr( | ... | @@ -3121,7 +3121,7 @@ pub fn dl_iterate_phdr( |
| 3121 | pub const ClockGetTimeError = error{UnsupportedClock} || UnexpectedError; | 3121 | pub const ClockGetTimeError = error{UnsupportedClock} || UnexpectedError; |
| 3122 | 3122 | ||
| 3123 | pub fn clock_gettime(clk_id: i32, tp: *timespec) ClockGetTimeError!void { | 3123 | pub fn clock_gettime(clk_id: i32, tp: *timespec) ClockGetTimeError!void { |
| 3124 | if (comptime std.Target.current.getOs() == .wasi) { | 3124 | if (std.Target.current.os.tag == .wasi) { |
| 3125 | var ts: timestamp_t = undefined; | 3125 | var ts: timestamp_t = undefined; |
| 3126 | switch (system.clock_time_get(@bitCast(u32, clk_id), 1, &ts)) { | 3126 | switch (system.clock_time_get(@bitCast(u32, clk_id), 1, &ts)) { |
| 3127 | 0 => { | 3127 | 0 => { |
| ... | @@ -3144,7 +3144,7 @@ pub fn clock_gettime(clk_id: i32, tp: *timespec) ClockGetTimeError!void { | ... | @@ -3144,7 +3144,7 @@ pub fn clock_gettime(clk_id: i32, tp: *timespec) ClockGetTimeError!void { |
| 3144 | } | 3144 | } |
| 3145 | 3145 | ||
| 3146 | pub fn clock_getres(clk_id: i32, res: *timespec) ClockGetTimeError!void { | 3146 | pub fn clock_getres(clk_id: i32, res: *timespec) ClockGetTimeError!void { |
| 3147 | if (comptime std.Target.current.getOs() == .wasi) { | 3147 | if (std.Target.current.os.tag == .wasi) { |
| 3148 | var ts: timestamp_t = undefined; | 3148 | var ts: timestamp_t = undefined; |
| 3149 | switch (system.clock_res_get(@bitCast(u32, clk_id), &ts)) { | 3149 | switch (system.clock_res_get(@bitCast(u32, clk_id), &ts)) { |
| 3150 | 0 => res.* = .{ | 3150 | 0 => res.* = .{ |
| ... | @@ -3222,7 +3222,7 @@ pub const SigaltstackError = error{ | ... | @@ -3222,7 +3222,7 @@ pub const SigaltstackError = error{ |
| 3222 | } || UnexpectedError; | 3222 | } || UnexpectedError; |
| 3223 | 3223 | ||
| 3224 | pub fn sigaltstack(ss: ?*stack_t, old_ss: ?*stack_t) SigaltstackError!void { | 3224 | pub fn sigaltstack(ss: ?*stack_t, old_ss: ?*stack_t) SigaltstackError!void { |
| 3225 | if (builtin.os == .windows or builtin.os == .uefi or builtin.os == .wasi) | 3225 | if (builtin.os.tag == .windows or builtin.os.tag == .uefi or builtin.os.tag == .wasi) |
| 3226 | @compileError("std.os.sigaltstack not available for this target"); | 3226 | @compileError("std.os.sigaltstack not available for this target"); |
| 3227 | 3227 | ||
| 3228 | switch (errno(system.sigaltstack(ss, old_ss))) { | 3228 | switch (errno(system.sigaltstack(ss, old_ss))) { |
| ... | @@ -3294,7 +3294,7 @@ pub fn gethostname(name_buffer: *[HOST_NAME_MAX]u8) GetHostNameError![]u8 { | ... | @@ -3294,7 +3294,7 @@ pub fn gethostname(name_buffer: *[HOST_NAME_MAX]u8) GetHostNameError![]u8 { |
| 3294 | else => |err| return unexpectedErrno(err), | 3294 | else => |err| return unexpectedErrno(err), |
| 3295 | } | 3295 | } |
| 3296 | } | 3296 | } |
| 3297 | if (builtin.os == .linux) { | 3297 | if (builtin.os.tag == .linux) { |
| 3298 | var uts: utsname = undefined; | 3298 | var uts: utsname = undefined; |
| 3299 | switch (errno(system.uname(&uts))) { | 3299 | switch (errno(system.uname(&uts))) { |
| 3300 | 0 => { | 3300 | 0 => { |
| ... | @@ -3611,7 +3611,7 @@ pub const SchedYieldError = error{ | ... | @@ -3611,7 +3611,7 @@ pub const SchedYieldError = error{ |
| 3611 | }; | 3611 | }; |
| 3612 | 3612 | ||
| 3613 | pub fn sched_yield() SchedYieldError!void { | 3613 | pub fn sched_yield() SchedYieldError!void { |
| 3614 | if (builtin.os == .windows) { | 3614 | if (builtin.os.tag == .windows) { |
| 3615 | // The return value has to do with how many other threads there are; it is not | 3615 | // The return value has to do with how many other threads there are; it is not |
| 3616 | // an error condition on Windows. | 3616 | // an error condition on Windows. |
| 3617 | _ = windows.kernel32.SwitchToThread(); | 3617 | _ = windows.kernel32.SwitchToThread(); |
lib/std/os/bits.zig+2-2| ... | @@ -3,10 +3,10 @@ | ... | @@ -3,10 +3,10 @@ |
| 3 | //! Root source files can define `os.bits` and these will additionally be added | 3 | //! Root source files can define `os.bits` and these will additionally be added |
| 4 | //! to the namespace. | 4 | //! to the namespace. |
| 5 | 5 | ||
| 6 | const builtin = @import("builtin"); | 6 | const std = @import("std"); |
| 7 | const root = @import("root"); | 7 | const root = @import("root"); |
| 8 | 8 | ||
| 9 | pub usingnamespace switch (builtin.os) { | 9 | pub usingnamespace switch (std.Target.current.os.tag) { |
| 10 | .macosx, .ios, .tvos, .watchos => @import("bits/darwin.zig"), | 10 | .macosx, .ios, .tvos, .watchos => @import("bits/darwin.zig"), |
| 11 | .dragonfly => @import("bits/dragonfly.zig"), | 11 | .dragonfly => @import("bits/dragonfly.zig"), |
| 12 | .freebsd => @import("bits/freebsd.zig"), | 12 | .freebsd => @import("bits/freebsd.zig"), |
lib/std/os/linux.zig+1-1| ... | @@ -1070,7 +1070,7 @@ pub fn tcsetattr(fd: fd_t, optional_action: TCSA, termios_p: *const termios) usi | ... | @@ -1070,7 +1070,7 @@ pub fn tcsetattr(fd: fd_t, optional_action: TCSA, termios_p: *const termios) usi |
| 1070 | } | 1070 | } |
| 1071 | 1071 | ||
| 1072 | test "" { | 1072 | test "" { |
| 1073 | if (builtin.os == .linux) { | 1073 | if (builtin.os.tag == .linux) { |
| 1074 | _ = @import("linux/test.zig"); | 1074 | _ = @import("linux/test.zig"); |
| 1075 | } | 1075 | } |
| 1076 | } | 1076 | } |
lib/std/os/test.zig+8-8| ... | @@ -53,7 +53,7 @@ test "std.Thread.getCurrentId" { | ... | @@ -53,7 +53,7 @@ test "std.Thread.getCurrentId" { |
| 53 | thread.wait(); | 53 | thread.wait(); |
| 54 | if (Thread.use_pthreads) { | 54 | if (Thread.use_pthreads) { |
| 55 | expect(thread_current_id == thread_id); | 55 | expect(thread_current_id == thread_id); |
| 56 | } else if (builtin.os == .windows) { | 56 | } else if (builtin.os.tag == .windows) { |
| 57 | expect(Thread.getCurrentId() != thread_current_id); | 57 | expect(Thread.getCurrentId() != thread_current_id); |
| 58 | } else { | 58 | } else { |
| 59 | // If the thread completes very quickly, then thread_id can be 0. See the | 59 | // If the thread completes very quickly, then thread_id can be 0. See the |
| ... | @@ -151,7 +151,7 @@ test "realpath" { | ... | @@ -151,7 +151,7 @@ test "realpath" { |
| 151 | } | 151 | } |
| 152 | 152 | ||
| 153 | test "sigaltstack" { | 153 | test "sigaltstack" { |
| 154 | if (builtin.os == .windows or builtin.os == .wasi) return error.SkipZigTest; | 154 | if (builtin.os.tag == .windows or builtin.os.tag == .wasi) return error.SkipZigTest; |
| 155 | 155 | ||
| 156 | var st: os.stack_t = undefined; | 156 | var st: os.stack_t = undefined; |
| 157 | try os.sigaltstack(null, &st); | 157 | try os.sigaltstack(null, &st); |
| ... | @@ -204,7 +204,7 @@ fn iter_fn(info: *dl_phdr_info, size: usize, counter: *usize) IterFnError!void { | ... | @@ -204,7 +204,7 @@ fn iter_fn(info: *dl_phdr_info, size: usize, counter: *usize) IterFnError!void { |
| 204 | } | 204 | } |
| 205 | 205 | ||
| 206 | test "dl_iterate_phdr" { | 206 | test "dl_iterate_phdr" { |
| 207 | if (builtin.os == .windows or builtin.os == .wasi or builtin.os == .macosx) | 207 | if (builtin.os.tag == .windows or builtin.os.tag == .wasi or builtin.os.tag == .macosx) |
| 208 | return error.SkipZigTest; | 208 | return error.SkipZigTest; |
| 209 | 209 | ||
| 210 | var counter: usize = 0; | 210 | var counter: usize = 0; |
| ... | @@ -213,7 +213,7 @@ test "dl_iterate_phdr" { | ... | @@ -213,7 +213,7 @@ test "dl_iterate_phdr" { |
| 213 | } | 213 | } |
| 214 | 214 | ||
| 215 | test "gethostname" { | 215 | test "gethostname" { |
| 216 | if (builtin.os == .windows) | 216 | if (builtin.os.tag == .windows) |
| 217 | return error.SkipZigTest; | 217 | return error.SkipZigTest; |
| 218 | 218 | ||
| 219 | var buf: [os.HOST_NAME_MAX]u8 = undefined; | 219 | var buf: [os.HOST_NAME_MAX]u8 = undefined; |
| ... | @@ -222,7 +222,7 @@ test "gethostname" { | ... | @@ -222,7 +222,7 @@ test "gethostname" { |
| 222 | } | 222 | } |
| 223 | 223 | ||
| 224 | test "pipe" { | 224 | test "pipe" { |
| 225 | if (builtin.os == .windows) | 225 | if (builtin.os.tag == .windows) |
| 226 | return error.SkipZigTest; | 226 | return error.SkipZigTest; |
| 227 | 227 | ||
| 228 | var fds = try os.pipe(); | 228 | var fds = try os.pipe(); |
| ... | @@ -241,7 +241,7 @@ test "argsAlloc" { | ... | @@ -241,7 +241,7 @@ test "argsAlloc" { |
| 241 | 241 | ||
| 242 | test "memfd_create" { | 242 | test "memfd_create" { |
| 243 | // memfd_create is linux specific. | 243 | // memfd_create is linux specific. |
| 244 | if (builtin.os != .linux) return error.SkipZigTest; | 244 | if (builtin.os.tag != .linux) return error.SkipZigTest; |
| 245 | const fd = std.os.memfd_create("test", 0) catch |err| switch (err) { | 245 | const fd = std.os.memfd_create("test", 0) catch |err| switch (err) { |
| 246 | // Related: https://github.com/ziglang/zig/issues/4019 | 246 | // Related: https://github.com/ziglang/zig/issues/4019 |
| 247 | error.SystemOutdated => return error.SkipZigTest, | 247 | error.SystemOutdated => return error.SkipZigTest, |
| ... | @@ -258,7 +258,7 @@ test "memfd_create" { | ... | @@ -258,7 +258,7 @@ test "memfd_create" { |
| 258 | } | 258 | } |
| 259 | 259 | ||
| 260 | test "mmap" { | 260 | test "mmap" { |
| 261 | if (builtin.os == .windows) | 261 | if (builtin.os.tag == .windows) |
| 262 | return error.SkipZigTest; | 262 | return error.SkipZigTest; |
| 263 | 263 | ||
| 264 | // Simple mmap() call with non page-aligned size | 264 | // Simple mmap() call with non page-aligned size |
| ... | @@ -353,7 +353,7 @@ test "mmap" { | ... | @@ -353,7 +353,7 @@ test "mmap" { |
| 353 | } | 353 | } |
| 354 | 354 | ||
| 355 | test "getenv" { | 355 | test "getenv" { |
| 356 | if (builtin.os == .windows) { | 356 | if (builtin.os.tag == .windows) { |
| 357 | expect(os.getenvW(&[_:0]u16{ 'B', 'O', 'G', 'U', 'S', 0x11, 0x22, 0x33, 0x44, 0x55 }) == null); | 357 | expect(os.getenvW(&[_:0]u16{ 'B', 'O', 'G', 'U', 'S', 0x11, 0x22, 0x33, 0x44, 0x55 }) == null); |
| 358 | } else { | 358 | } else { |
| 359 | expect(os.getenvZ("BOGUSDOESNOTEXISTENVVAR") == null); | 359 | expect(os.getenvZ("BOGUSDOESNOTEXISTENVVAR") == null); |
lib/std/packed_int_array.zig+2-2| ... | @@ -593,7 +593,7 @@ test "PackedInt(Array/Slice)Endian" { | ... | @@ -593,7 +593,7 @@ test "PackedInt(Array/Slice)Endian" { |
| 593 | // after this one is not mapped and will cause a segfault if we | 593 | // after this one is not mapped and will cause a segfault if we |
| 594 | // don't account for the bounds. | 594 | // don't account for the bounds. |
| 595 | test "PackedIntArray at end of available memory" { | 595 | test "PackedIntArray at end of available memory" { |
| 596 | switch (builtin.os) { | 596 | switch (builtin.os.tag) { |
| 597 | .linux, .macosx, .ios, .freebsd, .netbsd, .windows => {}, | 597 | .linux, .macosx, .ios, .freebsd, .netbsd, .windows => {}, |
| 598 | else => return, | 598 | else => return, |
| 599 | } | 599 | } |
| ... | @@ -612,7 +612,7 @@ test "PackedIntArray at end of available memory" { | ... | @@ -612,7 +612,7 @@ test "PackedIntArray at end of available memory" { |
| 612 | } | 612 | } |
| 613 | 613 | ||
| 614 | test "PackedIntSlice at end of available memory" { | 614 | test "PackedIntSlice at end of available memory" { |
| 615 | switch (builtin.os) { | 615 | switch (builtin.os.tag) { |
| 616 | .linux, .macosx, .ios, .freebsd, .netbsd, .windows => {}, | 616 | .linux, .macosx, .ios, .freebsd, .netbsd, .windows => {}, |
| 617 | else => return, | 617 | else => return, |
| 618 | } | 618 | } |
lib/std/process.zig+11-11| ... | @@ -36,7 +36,7 @@ pub fn getEnvMap(allocator: *Allocator) !BufMap { | ... | @@ -36,7 +36,7 @@ pub fn getEnvMap(allocator: *Allocator) !BufMap { |
| 36 | var result = BufMap.init(allocator); | 36 | var result = BufMap.init(allocator); |
| 37 | errdefer result.deinit(); | 37 | errdefer result.deinit(); |
| 38 | 38 | ||
| 39 | if (builtin.os == .windows) { | 39 | if (builtin.os.tag == .windows) { |
| 40 | const ptr = os.windows.peb().ProcessParameters.Environment; | 40 | const ptr = os.windows.peb().ProcessParameters.Environment; |
| 41 | 41 | ||
| 42 | var i: usize = 0; | 42 | var i: usize = 0; |
| ... | @@ -61,7 +61,7 @@ pub fn getEnvMap(allocator: *Allocator) !BufMap { | ... | @@ -61,7 +61,7 @@ pub fn getEnvMap(allocator: *Allocator) !BufMap { |
| 61 | try result.setMove(key, value); | 61 | try result.setMove(key, value); |
| 62 | } | 62 | } |
| 63 | return result; | 63 | return result; |
| 64 | } else if (builtin.os == .wasi) { | 64 | } else if (builtin.os.tag == .wasi) { |
| 65 | var environ_count: usize = undefined; | 65 | var environ_count: usize = undefined; |
| 66 | var environ_buf_size: usize = undefined; | 66 | var environ_buf_size: usize = undefined; |
| 67 | 67 | ||
| ... | @@ -137,7 +137,7 @@ pub const GetEnvVarOwnedError = error{ | ... | @@ -137,7 +137,7 @@ pub const GetEnvVarOwnedError = error{ |
| 137 | 137 | ||
| 138 | /// Caller must free returned memory. | 138 | /// Caller must free returned memory. |
| 139 | pub fn getEnvVarOwned(allocator: *mem.Allocator, key: []const u8) GetEnvVarOwnedError![]u8 { | 139 | pub fn getEnvVarOwned(allocator: *mem.Allocator, key: []const u8) GetEnvVarOwnedError![]u8 { |
| 140 | if (builtin.os == .windows) { | 140 | if (builtin.os.tag == .windows) { |
| 141 | const result_w = blk: { | 141 | const result_w = blk: { |
| 142 | const key_w = try std.unicode.utf8ToUtf16LeWithNull(allocator, key); | 142 | const key_w = try std.unicode.utf8ToUtf16LeWithNull(allocator, key); |
| 143 | defer allocator.free(key_w); | 143 | defer allocator.free(key_w); |
| ... | @@ -338,12 +338,12 @@ pub const ArgIteratorWindows = struct { | ... | @@ -338,12 +338,12 @@ pub const ArgIteratorWindows = struct { |
| 338 | }; | 338 | }; |
| 339 | 339 | ||
| 340 | pub const ArgIterator = struct { | 340 | pub const ArgIterator = struct { |
| 341 | const InnerType = if (builtin.os == .windows) ArgIteratorWindows else ArgIteratorPosix; | 341 | const InnerType = if (builtin.os.tag == .windows) ArgIteratorWindows else ArgIteratorPosix; |
| 342 | 342 | ||
| 343 | inner: InnerType, | 343 | inner: InnerType, |
| 344 | 344 | ||
| 345 | pub fn init() ArgIterator { | 345 | pub fn init() ArgIterator { |
| 346 | if (builtin.os == .wasi) { | 346 | if (builtin.os.tag == .wasi) { |
| 347 | // TODO: Figure out a compatible interface accomodating WASI | 347 | // TODO: Figure out a compatible interface accomodating WASI |
| 348 | @compileError("ArgIterator is not yet supported in WASI. Use argsAlloc and argsFree instead."); | 348 | @compileError("ArgIterator is not yet supported in WASI. Use argsAlloc and argsFree instead."); |
| 349 | } | 349 | } |
| ... | @@ -355,7 +355,7 @@ pub const ArgIterator = struct { | ... | @@ -355,7 +355,7 @@ pub const ArgIterator = struct { |
| 355 | 355 | ||
| 356 | /// You must free the returned memory when done. | 356 | /// You must free the returned memory when done. |
| 357 | pub fn next(self: *ArgIterator, allocator: *Allocator) ?(NextError![]u8) { | 357 | pub fn next(self: *ArgIterator, allocator: *Allocator) ?(NextError![]u8) { |
| 358 | if (builtin.os == .windows) { | 358 | if (builtin.os.tag == .windows) { |
| 359 | return self.inner.next(allocator); | 359 | return self.inner.next(allocator); |
| 360 | } else { | 360 | } else { |
| 361 | return mem.dupe(allocator, u8, self.inner.next() orelse return null); | 361 | return mem.dupe(allocator, u8, self.inner.next() orelse return null); |
| ... | @@ -380,7 +380,7 @@ pub fn args() ArgIterator { | ... | @@ -380,7 +380,7 @@ pub fn args() ArgIterator { |
| 380 | 380 | ||
| 381 | /// Caller must call argsFree on result. | 381 | /// Caller must call argsFree on result. |
| 382 | pub fn argsAlloc(allocator: *mem.Allocator) ![][]u8 { | 382 | pub fn argsAlloc(allocator: *mem.Allocator) ![][]u8 { |
| 383 | if (builtin.os == .wasi) { | 383 | if (builtin.os.tag == .wasi) { |
| 384 | var count: usize = undefined; | 384 | var count: usize = undefined; |
| 385 | var buf_size: usize = undefined; | 385 | var buf_size: usize = undefined; |
| 386 | 386 | ||
| ... | @@ -445,7 +445,7 @@ pub fn argsAlloc(allocator: *mem.Allocator) ![][]u8 { | ... | @@ -445,7 +445,7 @@ pub fn argsAlloc(allocator: *mem.Allocator) ![][]u8 { |
| 445 | } | 445 | } |
| 446 | 446 | ||
| 447 | pub fn argsFree(allocator: *mem.Allocator, args_alloc: []const []u8) void { | 447 | pub fn argsFree(allocator: *mem.Allocator, args_alloc: []const []u8) void { |
| 448 | if (builtin.os == .wasi) { | 448 | if (builtin.os.tag == .wasi) { |
| 449 | const last_item = args_alloc[args_alloc.len - 1]; | 449 | const last_item = args_alloc[args_alloc.len - 1]; |
| 450 | const last_byte_addr = @ptrToInt(last_item.ptr) + last_item.len + 1; // null terminated | 450 | const last_byte_addr = @ptrToInt(last_item.ptr) + last_item.len + 1; // null terminated |
| 451 | const first_item_ptr = args_alloc[0].ptr; | 451 | const first_item_ptr = args_alloc[0].ptr; |
| ... | @@ -498,7 +498,7 @@ pub const UserInfo = struct { | ... | @@ -498,7 +498,7 @@ pub const UserInfo = struct { |
| 498 | 498 | ||
| 499 | /// POSIX function which gets a uid from username. | 499 | /// POSIX function which gets a uid from username. |
| 500 | pub fn getUserInfo(name: []const u8) !UserInfo { | 500 | pub fn getUserInfo(name: []const u8) !UserInfo { |
| 501 | return switch (builtin.os) { | 501 | return switch (builtin.os.tag) { |
| 502 | .linux, .macosx, .watchos, .tvos, .ios, .freebsd, .netbsd => posixGetUserInfo(name), | 502 | .linux, .macosx, .watchos, .tvos, .ios, .freebsd, .netbsd => posixGetUserInfo(name), |
| 503 | else => @compileError("Unsupported OS"), | 503 | else => @compileError("Unsupported OS"), |
| 504 | }; | 504 | }; |
| ... | @@ -591,7 +591,7 @@ pub fn posixGetUserInfo(name: []const u8) !UserInfo { | ... | @@ -591,7 +591,7 @@ pub fn posixGetUserInfo(name: []const u8) !UserInfo { |
| 591 | } | 591 | } |
| 592 | 592 | ||
| 593 | pub fn getBaseAddress() usize { | 593 | pub fn getBaseAddress() usize { |
| 594 | switch (builtin.os) { | 594 | switch (builtin.os.tag) { |
| 595 | .linux => { | 595 | .linux => { |
| 596 | const base = os.system.getauxval(std.elf.AT_BASE); | 596 | const base = os.system.getauxval(std.elf.AT_BASE); |
| 597 | if (base != 0) { | 597 | if (base != 0) { |
| ... | @@ -615,7 +615,7 @@ pub fn getSelfExeSharedLibPaths(allocator: *Allocator) error{OutOfMemory}![][:0] | ... | @@ -615,7 +615,7 @@ pub fn getSelfExeSharedLibPaths(allocator: *Allocator) error{OutOfMemory}![][:0] |
| 615 | .Dynamic => {}, | 615 | .Dynamic => {}, |
| 616 | } | 616 | } |
| 617 | const List = std.ArrayList([:0]u8); | 617 | const List = std.ArrayList([:0]u8); |
| 618 | switch (builtin.os) { | 618 | switch (builtin.os.tag) { |
| 619 | .linux, | 619 | .linux, |
| 620 | .freebsd, | 620 | .freebsd, |
| 621 | .netbsd, | 621 | .netbsd, |
lib/std/reset_event.zig+3-3| ... | @@ -16,7 +16,7 @@ pub const ResetEvent = struct { | ... | @@ -16,7 +16,7 @@ pub const ResetEvent = struct { |
| 16 | 16 | ||
| 17 | pub const OsEvent = if (builtin.single_threaded) | 17 | pub const OsEvent = if (builtin.single_threaded) |
| 18 | DebugEvent | 18 | DebugEvent |
| 19 | else if (builtin.link_libc and builtin.os != .windows and builtin.os != .linux) | 19 | else if (builtin.link_libc and builtin.os.tag != .windows and builtin.os.tag != .linux) |
| 20 | PosixEvent | 20 | PosixEvent |
| 21 | else | 21 | else |
| 22 | AtomicEvent; | 22 | AtomicEvent; |
| ... | @@ -106,7 +106,7 @@ const PosixEvent = struct { | ... | @@ -106,7 +106,7 @@ const PosixEvent = struct { |
| 106 | fn deinit(self: *PosixEvent) void { | 106 | fn deinit(self: *PosixEvent) void { |
| 107 | // on dragonfly, *destroy() functions can return EINVAL | 107 | // on dragonfly, *destroy() functions can return EINVAL |
| 108 | // for statically initialized pthread structures | 108 | // for statically initialized pthread structures |
| 109 | const err = if (builtin.os == .dragonfly) os.EINVAL else 0; | 109 | const err = if (builtin.os.tag == .dragonfly) os.EINVAL else 0; |
| 110 | 110 | ||
| 111 | const retm = c.pthread_mutex_destroy(&self.mutex); | 111 | const retm = c.pthread_mutex_destroy(&self.mutex); |
| 112 | assert(retm == 0 or retm == err); | 112 | assert(retm == 0 or retm == err); |
| ... | @@ -215,7 +215,7 @@ const AtomicEvent = struct { | ... | @@ -215,7 +215,7 @@ const AtomicEvent = struct { |
| 215 | } | 215 | } |
| 216 | } | 216 | } |
| 217 | 217 | ||
| 218 | pub const Futex = switch (builtin.os) { | 218 | pub const Futex = switch (builtin.os.tag) { |
| 219 | .windows => WindowsFutex, | 219 | .windows => WindowsFutex, |
| 220 | .linux => LinuxFutex, | 220 | .linux => LinuxFutex, |
| 221 | else => SpinFutex, | 221 | else => SpinFutex, |
lib/std/special/c.zig+4-4| ... | @@ -17,7 +17,7 @@ const is_msvc = switch (builtin.abi) { | ... | @@ -17,7 +17,7 @@ const is_msvc = switch (builtin.abi) { |
| 17 | .msvc => true, | 17 | .msvc => true, |
| 18 | else => false, | 18 | else => false, |
| 19 | }; | 19 | }; |
| 20 | const is_freestanding = switch (builtin.os) { | 20 | const is_freestanding = switch (builtin.os.tag) { |
| 21 | .freestanding => true, | 21 | .freestanding => true, |
| 22 | else => false, | 22 | else => false, |
| 23 | }; | 23 | }; |
| ... | @@ -81,7 +81,7 @@ pub fn panic(msg: []const u8, error_return_trace: ?*builtin.StackTrace) noreturn | ... | @@ -81,7 +81,7 @@ pub fn panic(msg: []const u8, error_return_trace: ?*builtin.StackTrace) noreturn |
| 81 | @setCold(true); | 81 | @setCold(true); |
| 82 | std.debug.panic("{}", .{msg}); | 82 | std.debug.panic("{}", .{msg}); |
| 83 | } | 83 | } |
| 84 | if (builtin.os != .freestanding and builtin.os != .other) { | 84 | if (builtin.os.tag != .freestanding and builtin.os.tag != .other) { |
| 85 | std.os.abort(); | 85 | std.os.abort(); |
| 86 | } | 86 | } |
| 87 | while (true) {} | 87 | while (true) {} |
| ... | @@ -178,11 +178,11 @@ test "test_bcmp" { | ... | @@ -178,11 +178,11 @@ test "test_bcmp" { |
| 178 | comptime { | 178 | comptime { |
| 179 | if (builtin.mode != builtin.Mode.ReleaseFast and | 179 | if (builtin.mode != builtin.Mode.ReleaseFast and |
| 180 | builtin.mode != builtin.Mode.ReleaseSmall and | 180 | builtin.mode != builtin.Mode.ReleaseSmall and |
| 181 | builtin.os != builtin.Os.windows) | 181 | builtin.os.tag != .windows) |
| 182 | { | 182 | { |
| 183 | @export(__stack_chk_fail, .{ .name = "__stack_chk_fail" }); | 183 | @export(__stack_chk_fail, .{ .name = "__stack_chk_fail" }); |
| 184 | } | 184 | } |
| 185 | if (builtin.os == builtin.Os.linux) { | 185 | if (builtin.os.tag == .linux) { |
| 186 | @export(clone, .{ .name = "clone" }); | 186 | @export(clone, .{ .name = "clone" }); |
| 187 | } | 187 | } |
| 188 | } | 188 | } |
lib/std/special/compiler_rt.zig+7-6| ... | @@ -1,11 +1,12 @@ | ... | @@ -1,11 +1,12 @@ |
| 1 | const builtin = @import("builtin"); | 1 | const std = @import("std"); |
| 2 | const builtin = std.builtin; | ||
| 2 | const is_test = builtin.is_test; | 3 | const is_test = builtin.is_test; |
| 3 | 4 | ||
| 4 | const is_gnu = switch (builtin.abi) { | 5 | const is_gnu = switch (builtin.abi) { |
| 5 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => true, | 6 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => true, |
| 6 | else => false, | 7 | else => false, |
| 7 | }; | 8 | }; |
| 8 | const is_mingw = builtin.os == .windows and is_gnu; | 9 | const is_mingw = builtin.os.tag == .windows and is_gnu; |
| 9 | 10 | ||
| 10 | comptime { | 11 | comptime { |
| 11 | const linkage = if (is_test) builtin.GlobalLinkage.Internal else builtin.GlobalLinkage.Weak; | 12 | const linkage = if (is_test) builtin.GlobalLinkage.Internal else builtin.GlobalLinkage.Weak; |
| ... | @@ -180,7 +181,7 @@ comptime { | ... | @@ -180,7 +181,7 @@ comptime { |
| 180 | @export(@import("compiler_rt/arm.zig").__aeabi_memclr, .{ .name = "__aeabi_memclr4", .linkage = linkage }); | 181 | @export(@import("compiler_rt/arm.zig").__aeabi_memclr, .{ .name = "__aeabi_memclr4", .linkage = linkage }); |
| 181 | @export(@import("compiler_rt/arm.zig").__aeabi_memclr, .{ .name = "__aeabi_memclr8", .linkage = linkage }); | 182 | @export(@import("compiler_rt/arm.zig").__aeabi_memclr, .{ .name = "__aeabi_memclr8", .linkage = linkage }); |
| 182 | 183 | ||
| 183 | if (builtin.os == .linux) { | 184 | if (builtin.os.tag == .linux) { |
| 184 | @export(@import("compiler_rt/arm.zig").__aeabi_read_tp, .{ .name = "__aeabi_read_tp", .linkage = linkage }); | 185 | @export(@import("compiler_rt/arm.zig").__aeabi_read_tp, .{ .name = "__aeabi_read_tp", .linkage = linkage }); |
| 185 | } | 186 | } |
| 186 | 187 | ||
| ... | @@ -250,7 +251,7 @@ comptime { | ... | @@ -250,7 +251,7 @@ comptime { |
| 250 | @export(@import("compiler_rt/aullrem.zig")._aullrem, .{ .name = "\x01__aullrem", .linkage = strong_linkage }); | 251 | @export(@import("compiler_rt/aullrem.zig")._aullrem, .{ .name = "\x01__aullrem", .linkage = strong_linkage }); |
| 251 | } | 252 | } |
| 252 | 253 | ||
| 253 | if (builtin.os == .windows) { | 254 | if (builtin.os.tag == .windows) { |
| 254 | // Default stack-probe functions emitted by LLVM | 255 | // Default stack-probe functions emitted by LLVM |
| 255 | if (is_mingw) { | 256 | if (is_mingw) { |
| 256 | @export(@import("compiler_rt/stack_probe.zig")._chkstk, .{ .name = "_alloca", .linkage = strong_linkage }); | 257 | @export(@import("compiler_rt/stack_probe.zig")._chkstk, .{ .name = "_alloca", .linkage = strong_linkage }); |
| ... | @@ -288,7 +289,7 @@ comptime { | ... | @@ -288,7 +289,7 @@ comptime { |
| 288 | else => {}, | 289 | else => {}, |
| 289 | } | 290 | } |
| 290 | } else { | 291 | } else { |
| 291 | if (builtin.glibc_version != null) { | 292 | if (std.Target.current.isGnuLibC()) { |
| 292 | @export(__stack_chk_guard, .{ .name = "__stack_chk_guard", .linkage = linkage }); | 293 | @export(__stack_chk_guard, .{ .name = "__stack_chk_guard", .linkage = linkage }); |
| 293 | } | 294 | } |
| 294 | @export(@import("compiler_rt/divti3.zig").__divti3, .{ .name = "__divti3", .linkage = linkage }); | 295 | @export(@import("compiler_rt/divti3.zig").__divti3, .{ .name = "__divti3", .linkage = linkage }); |
| ... | @@ -307,7 +308,7 @@ comptime { | ... | @@ -307,7 +308,7 @@ comptime { |
| 307 | pub fn panic(msg: []const u8, error_return_trace: ?*builtin.StackTrace) noreturn { | 308 | pub fn panic(msg: []const u8, error_return_trace: ?*builtin.StackTrace) noreturn { |
| 308 | @setCold(true); | 309 | @setCold(true); |
| 309 | if (is_test) { | 310 | if (is_test) { |
| 310 | @import("std").debug.panic("{}", .{msg}); | 311 | std.debug.panic("{}", .{msg}); |
| 311 | } else { | 312 | } else { |
| 312 | unreachable; | 313 | unreachable; |
| 313 | } | 314 | } |
lib/std/special/compiler_rt/extendXfYf2_test.zig+1-1| ... | @@ -90,7 +90,7 @@ test "extendhfsf2" { | ... | @@ -90,7 +90,7 @@ test "extendhfsf2" { |
| 90 | test__extendhfsf2(0x7f00, 0x7fe00000); // sNaN | 90 | test__extendhfsf2(0x7f00, 0x7fe00000); // sNaN |
| 91 | // On x86 the NaN becomes quiet because the return is pushed on the x87 | 91 | // On x86 the NaN becomes quiet because the return is pushed on the x87 |
| 92 | // stack due to ABI requirements | 92 | // stack due to ABI requirements |
| 93 | if (builtin.arch != .i386 and builtin.os == .windows) | 93 | if (builtin.arch != .i386 and builtin.os.tag == .windows) |
| 94 | test__extendhfsf2(0x7c01, 0x7f802000); // sNaN | 94 | test__extendhfsf2(0x7c01, 0x7f802000); // sNaN |
| 95 | 95 | ||
| 96 | test__extendhfsf2(0, 0); // 0 | 96 | test__extendhfsf2(0, 0); // 0 |
lib/std/spinlock.zig+1-1| ... | @@ -46,7 +46,7 @@ pub const SpinLock = struct { | ... | @@ -46,7 +46,7 @@ pub const SpinLock = struct { |
| 46 | // and yielding for 380-410 iterations was found to be | 46 | // and yielding for 380-410 iterations was found to be |
| 47 | // a nice sweet spot. Posix systems on the other hand, | 47 | // a nice sweet spot. Posix systems on the other hand, |
| 48 | // especially linux, perform better by yielding the thread. | 48 | // especially linux, perform better by yielding the thread. |
| 49 | switch (builtin.os) { | 49 | switch (builtin.os.tag) { |
| 50 | .windows => loopHint(400), | 50 | .windows => loopHint(400), |
| 51 | else => std.os.sched_yield() catch loopHint(1), | 51 | else => std.os.sched_yield() catch loopHint(1), |
| 52 | } | 52 | } |
lib/std/start.zig+8-8| ... | @@ -12,7 +12,7 @@ const start_sym_name = if (builtin.arch.isMIPS()) "__start" else "_start"; | ... | @@ -12,7 +12,7 @@ const start_sym_name = if (builtin.arch.isMIPS()) "__start" else "_start"; |
| 12 | 12 | ||
| 13 | comptime { | 13 | comptime { |
| 14 | if (builtin.output_mode == .Lib and builtin.link_mode == .Dynamic) { | 14 | if (builtin.output_mode == .Lib and builtin.link_mode == .Dynamic) { |
| 15 | if (builtin.os == .windows and !@hasDecl(root, "_DllMainCRTStartup")) { | 15 | if (builtin.os.tag == .windows and !@hasDecl(root, "_DllMainCRTStartup")) { |
| 16 | @export(_DllMainCRTStartup, .{ .name = "_DllMainCRTStartup" }); | 16 | @export(_DllMainCRTStartup, .{ .name = "_DllMainCRTStartup" }); |
| 17 | } | 17 | } |
| 18 | } else if (builtin.output_mode == .Exe or @hasDecl(root, "main")) { | 18 | } else if (builtin.output_mode == .Exe or @hasDecl(root, "main")) { |
| ... | @@ -20,17 +20,17 @@ comptime { | ... | @@ -20,17 +20,17 @@ comptime { |
| 20 | if (@typeInfo(@TypeOf(root.main)).Fn.calling_convention != .C) { | 20 | if (@typeInfo(@TypeOf(root.main)).Fn.calling_convention != .C) { |
| 21 | @export(main, .{ .name = "main", .linkage = .Weak }); | 21 | @export(main, .{ .name = "main", .linkage = .Weak }); |
| 22 | } | 22 | } |
| 23 | } else if (builtin.os == .windows) { | 23 | } else if (builtin.os.tag == .windows) { |
| 24 | if (!@hasDecl(root, "WinMain") and !@hasDecl(root, "WinMainCRTStartup") and | 24 | if (!@hasDecl(root, "WinMain") and !@hasDecl(root, "WinMainCRTStartup") and |
| 25 | !@hasDecl(root, "wWinMain") and !@hasDecl(root, "wWinMainCRTStartup")) | 25 | !@hasDecl(root, "wWinMain") and !@hasDecl(root, "wWinMainCRTStartup")) |
| 26 | { | 26 | { |
| 27 | @export(WinMainCRTStartup, .{ .name = "WinMainCRTStartup" }); | 27 | @export(WinMainCRTStartup, .{ .name = "WinMainCRTStartup" }); |
| 28 | } | 28 | } |
| 29 | } else if (builtin.os == .uefi) { | 29 | } else if (builtin.os.tag == .uefi) { |
| 30 | if (!@hasDecl(root, "EfiMain")) @export(EfiMain, .{ .name = "EfiMain" }); | 30 | if (!@hasDecl(root, "EfiMain")) @export(EfiMain, .{ .name = "EfiMain" }); |
| 31 | } else if (builtin.arch.isWasm() and builtin.os == .freestanding) { | 31 | } else if (builtin.arch.isWasm() and builtin.os.tag == .freestanding) { |
| 32 | if (!@hasDecl(root, start_sym_name)) @export(wasm_freestanding_start, .{ .name = start_sym_name }); | 32 | if (!@hasDecl(root, start_sym_name)) @export(wasm_freestanding_start, .{ .name = start_sym_name }); |
| 33 | } else if (builtin.os != .other and builtin.os != .freestanding) { | 33 | } else if (builtin.os.tag != .other and builtin.os.tag != .freestanding) { |
| 34 | if (!@hasDecl(root, start_sym_name)) @export(_start, .{ .name = start_sym_name }); | 34 | if (!@hasDecl(root, start_sym_name)) @export(_start, .{ .name = start_sym_name }); |
| 35 | } | 35 | } |
| 36 | } | 36 | } |
| ... | @@ -78,7 +78,7 @@ fn EfiMain(handle: uefi.Handle, system_table: *uefi.tables.SystemTable) callconv | ... | @@ -78,7 +78,7 @@ fn EfiMain(handle: uefi.Handle, system_table: *uefi.tables.SystemTable) callconv |
| 78 | } | 78 | } |
| 79 | 79 | ||
| 80 | fn _start() callconv(.Naked) noreturn { | 80 | fn _start() callconv(.Naked) noreturn { |
| 81 | if (builtin.os == builtin.Os.wasi) { | 81 | if (builtin.os.tag == .wasi) { |
| 82 | // This is marked inline because for some reason LLVM in release mode fails to inline it, | 82 | // This is marked inline because for some reason LLVM in release mode fails to inline it, |
| 83 | // and we want fewer call frames in stack traces. | 83 | // and we want fewer call frames in stack traces. |
| 84 | std.os.wasi.proc_exit(@call(.{ .modifier = .always_inline }, callMain, .{})); | 84 | std.os.wasi.proc_exit(@call(.{ .modifier = .always_inline }, callMain, .{})); |
| ... | @@ -133,7 +133,7 @@ fn WinMainCRTStartup() callconv(.Stdcall) noreturn { | ... | @@ -133,7 +133,7 @@ fn WinMainCRTStartup() callconv(.Stdcall) noreturn { |
| 133 | 133 | ||
| 134 | // TODO https://github.com/ziglang/zig/issues/265 | 134 | // TODO https://github.com/ziglang/zig/issues/265 |
| 135 | fn posixCallMainAndExit() noreturn { | 135 | fn posixCallMainAndExit() noreturn { |
| 136 | if (builtin.os == builtin.Os.freebsd) { | 136 | if (builtin.os.tag == .freebsd) { |
| 137 | @setAlignStack(16); | 137 | @setAlignStack(16); |
| 138 | } | 138 | } |
| 139 | const argc = starting_stack_ptr[0]; | 139 | const argc = starting_stack_ptr[0]; |
| ... | @@ -144,7 +144,7 @@ fn posixCallMainAndExit() noreturn { | ... | @@ -144,7 +144,7 @@ fn posixCallMainAndExit() noreturn { |
| 144 | while (envp_optional[envp_count]) |_| : (envp_count += 1) {} | 144 | while (envp_optional[envp_count]) |_| : (envp_count += 1) {} |
| 145 | const envp = @ptrCast([*][*:0]u8, envp_optional)[0..envp_count]; | 145 | const envp = @ptrCast([*][*:0]u8, envp_optional)[0..envp_count]; |
| 146 | 146 | ||
| 147 | if (builtin.os == .linux) { | 147 | if (builtin.os.tag == .linux) { |
| 148 | // Find the beginning of the auxiliary vector | 148 | // Find the beginning of the auxiliary vector |
| 149 | const auxv = @ptrCast([*]std.elf.Auxv, @alignCast(@alignOf(usize), envp.ptr + envp_count + 1)); | 149 | const auxv = @ptrCast([*]std.elf.Auxv, @alignCast(@alignOf(usize), envp.ptr + envp_count + 1)); |
| 150 | std.os.linux.elf_aux_maybe = auxv; | 150 | std.os.linux.elf_aux_maybe = auxv; |
lib/std/target.zig+308-291| ... | @@ -11,143 +11,48 @@ pub const Target = struct { | ... | @@ -11,143 +11,48 @@ pub const Target = struct { |
| 11 | os: Os, | 11 | os: Os, |
| 12 | abi: Abi, | 12 | abi: Abi, |
| 13 | 13 | ||
| 14 | /// The version ranges here represent the minimum OS version to be supported | 14 | pub const Os = struct { |
| 15 | /// and the maximum OS version to be supported. The default values represent | 15 | tag: Tag, |
| 16 | /// the range that the Zig Standard Library bases its abstractions on. | 16 | version_range: VersionRange, |
| 17 | /// | 17 | |
| 18 | /// The minimum version of the range is the main setting to tweak for a target. | 18 | pub const Tag = enum { |
| 19 | /// Usually, the maximum target OS version will remain the default, which is | 19 | freestanding, |
| 20 | /// the latest released version of the OS. | 20 | ananas, |
| 21 | /// | 21 | cloudabi, |
| 22 | /// To test at compile time if the target is guaranteed to support a given OS feature, | 22 | dragonfly, |
| 23 | /// one should check that the minimum version of the range is greater than or equal to | 23 | freebsd, |
| 24 | /// the version the feature was introduced in. | 24 | fuchsia, |
| 25 | /// | 25 | ios, |
| 26 | /// To test at compile time if the target certainly will not support a given OS feature, | 26 | kfreebsd, |
| 27 | /// one should check that the maximum version of the range is less than the version the | 27 | linux, |
| 28 | /// feature was introduced in. | 28 | lv2, |
| 29 | /// | 29 | macosx, |
| 30 | /// If neither of these cases apply, a runtime check should be used to determine if the | 30 | netbsd, |
| 31 | /// target supports a given OS feature. | 31 | openbsd, |
| 32 | /// | 32 | solaris, |
| 33 | /// Binaries built with a given maximum version will continue to function on newer operating system | 33 | windows, |
| 34 | /// versions. However, such a binary may not take full advantage of the newer operating system APIs. | 34 | haiku, |
| 35 | pub const Os = union(enum) { | 35 | minix, |
| 36 | freestanding, | 36 | rtems, |
| 37 | ananas, | 37 | nacl, |
| 38 | cloudabi, | 38 | cnk, |
| 39 | dragonfly, | 39 | aix, |
| 40 | freebsd: Version.Range, | 40 | cuda, |
| 41 | fuchsia, | 41 | nvcl, |
| 42 | ios, | 42 | amdhsa, |
| 43 | kfreebsd, | 43 | ps4, |
| 44 | linux: LinuxVersionRange, | 44 | elfiamcu, |
| 45 | lv2, | 45 | tvos, |
| 46 | macosx: Version.Range, | 46 | watchos, |
| 47 | netbsd: Version.Range, | 47 | mesa3d, |
| 48 | openbsd: Version.Range, | 48 | contiki, |
| 49 | solaris, | 49 | amdpal, |
| 50 | windows: WindowsVersion.Range, | 50 | hermit, |
| 51 | haiku, | 51 | hurd, |
| 52 | minix, | 52 | wasi, |
| 53 | rtems, | 53 | emscripten, |
| 54 | nacl, | 54 | uefi, |
| 55 | cnk, | 55 | other, |
| 56 | aix, | ||
| 57 | cuda, | ||
| 58 | nvcl, | ||
| 59 | amdhsa, | ||
| 60 | ps4, | ||
| 61 | elfiamcu, | ||
| 62 | tvos, | ||
| 63 | watchos, | ||
| 64 | mesa3d, | ||
| 65 | contiki, | ||
| 66 | amdpal, | ||
| 67 | hermit, | ||
| 68 | hurd, | ||
| 69 | wasi, | ||
| 70 | emscripten, | ||
| 71 | uefi, | ||
| 72 | other, | ||
| 73 | |||
| 74 | /// See the documentation for `Os` for an explanation of the default version range. | ||
| 75 | pub fn defaultVersionRange(tag: @TagType(Os)) Os { | ||
| 76 | switch (tag) { | ||
| 77 | .freestanding => return .freestanding, | ||
| 78 | .ananas => return .ananas, | ||
| 79 | .cloudabi => return .cloudabi, | ||
| 80 | .dragonfly => return .dragonfly, | ||
| 81 | .freebsd => return .{ | ||
| 82 | .freebsd = Version.Range{ | ||
| 83 | .min = .{ .major = 12, .minor = 0 }, | ||
| 84 | .max = .{ .major = 12, .minor = 1 }, | ||
| 85 | }, | ||
| 86 | }, | ||
| 87 | .fuchsia => return .fuchsia, | ||
| 88 | .ios => return .ios, | ||
| 89 | .kfreebsd => return .kfreebsd, | ||
| 90 | .linux => return .{ | ||
| 91 | .linux = .{ | ||
| 92 | .range = .{ | ||
| 93 | .min = .{ .major = 3, .minor = 16 }, | ||
| 94 | .max = .{ .major = 5, .minor = 5, .patch = 5 }, | ||
| 95 | }, | ||
| 96 | .glibc = .{ .major = 2, .minor = 17 }, | ||
| 97 | }, | ||
| 98 | }, | ||
| 99 | .lv2 => return .lv2, | ||
| 100 | .macosx => return .{ | ||
| 101 | .min = .{ .major = 10, .minor = 13 }, | ||
| 102 | .max = .{ .major = 10, .minor = 15, .patch = 3 }, | ||
| 103 | }, | ||
| 104 | .netbsd => return .{ | ||
| 105 | .min = .{ .major = 8, .minor = 0 }, | ||
| 106 | .max = .{ .major = 9, .minor = 0 }, | ||
| 107 | }, | ||
| 108 | .openbsd => return .{ | ||
| 109 | .min = .{ .major = 6, .minor = 6 }, | ||
| 110 | .max = .{ .major = 6, .minor = 6 }, | ||
| 111 | }, | ||
| 112 | solaris => return .solaris, | ||
| 113 | windows => return .{ | ||
| 114 | .windows = .{ | ||
| 115 | .min = .win8_1, | ||
| 116 | .max = .win10_19h1, | ||
| 117 | }, | ||
| 118 | }, | ||
| 119 | haiku => return .haiku, | ||
| 120 | minix => return .minix, | ||
| 121 | rtems => return .rtems, | ||
| 122 | nacl => return .nacl, | ||
| 123 | cnk => return .cnk, | ||
| 124 | aix => return .aix, | ||
| 125 | cuda => return .cuda, | ||
| 126 | nvcl => return .nvcl, | ||
| 127 | amdhsa => return .amdhsa, | ||
| 128 | ps4 => return .ps4, | ||
| 129 | elfiamcu => return .elfiamcu, | ||
| 130 | tvos => return .tvos, | ||
| 131 | watchos => return .watchos, | ||
| 132 | mesa3d => return .mesa3d, | ||
| 133 | contiki => return .contiki, | ||
| 134 | amdpal => return .amdpal, | ||
| 135 | hermit => return .hermit, | ||
| 136 | hurd => return .hurd, | ||
| 137 | wasi => return .wasi, | ||
| 138 | emscripten => return .emscripten, | ||
| 139 | uefi => return .uefi, | ||
| 140 | other => return .other, | ||
| 141 | } | ||
| 142 | } | ||
| 143 | |||
| 144 | pub const LinuxVersionRange = struct { | ||
| 145 | range: Version.Range, | ||
| 146 | glibc: Version, | ||
| 147 | |||
| 148 | pub fn includesVersion(self: LinuxVersionRange, ver: Version) bool { | ||
| 149 | return self.range.includesVersion(ver); | ||
| 150 | } | ||
| 151 | }; | 56 | }; |
| 152 | 57 | ||
| 153 | /// Based on NTDDI version constants from | 58 | /// Based on NTDDI version constants from |
| ... | @@ -178,29 +83,137 @@ pub const Target = struct { | ... | @@ -178,29 +83,137 @@ pub const Target = struct { |
| 178 | return @enumToInt(ver) >= @enumToInt(self.min) and @enumToInt(ver) <= @enumToInt(self.max); | 83 | return @enumToInt(ver) >= @enumToInt(self.min) and @enumToInt(ver) <= @enumToInt(self.max); |
| 179 | } | 84 | } |
| 180 | }; | 85 | }; |
| 86 | }; | ||
| 181 | 87 | ||
| 182 | pub fn nameToTag(name: []const u8) ?WindowsVersion { | 88 | pub const LinuxVersionRange = struct { |
| 183 | const info = @typeInfo(WindowsVersion); | 89 | range: Version.Range, |
| 184 | inline for (info.Enum.fields) |field| { | 90 | glibc: Version, |
| 185 | if (mem.eql(u8, name, field.name)) { | 91 | |
| 186 | return @field(WindowsVersion, field.name); | 92 | pub fn includesVersion(self: LinuxVersionRange, ver: Version) bool { |
| 187 | } | 93 | return self.range.includesVersion(ver); |
| 94 | } | ||
| 95 | }; | ||
| 96 | |||
| 97 | /// The version ranges here represent the minimum OS version to be supported | ||
| 98 | /// and the maximum OS version to be supported. The default values represent | ||
| 99 | /// the range that the Zig Standard Library bases its abstractions on. | ||
| 100 | /// | ||
| 101 | /// The minimum version of the range is the main setting to tweak for a target. | ||
| 102 | /// Usually, the maximum target OS version will remain the default, which is | ||
| 103 | /// the latest released version of the OS. | ||
| 104 | /// | ||
| 105 | /// To test at compile time if the target is guaranteed to support a given OS feature, | ||
| 106 | /// one should check that the minimum version of the range is greater than or equal to | ||
| 107 | /// the version the feature was introduced in. | ||
| 108 | /// | ||
| 109 | /// To test at compile time if the target certainly will not support a given OS feature, | ||
| 110 | /// one should check that the maximum version of the range is less than the version the | ||
| 111 | /// feature was introduced in. | ||
| 112 | /// | ||
| 113 | /// If neither of these cases apply, a runtime check should be used to determine if the | ||
| 114 | /// target supports a given OS feature. | ||
| 115 | /// | ||
| 116 | /// Binaries built with a given maximum version will continue to function on newer operating system | ||
| 117 | /// versions. However, such a binary may not take full advantage of the newer operating system APIs. | ||
| 118 | pub const VersionRange = union { | ||
| 119 | none: void, | ||
| 120 | semver: Version.Range, | ||
| 121 | linux: LinuxVersionRange, | ||
| 122 | windows: WindowsVersion.Range, | ||
| 123 | |||
| 124 | /// The default `VersionRange` represents the range that the Zig Standard Library | ||
| 125 | /// bases its abstractions on. | ||
| 126 | pub fn default(tag: Tag) VersionRange { | ||
| 127 | switch (tag) { | ||
| 128 | .freestanding, | ||
| 129 | .ananas, | ||
| 130 | .cloudabi, | ||
| 131 | .dragonfly, | ||
| 132 | .fuchsia, | ||
| 133 | .ios, | ||
| 134 | .kfreebsd, | ||
| 135 | .lv2, | ||
| 136 | .solaris, | ||
| 137 | .haiku, | ||
| 138 | .minix, | ||
| 139 | .rtems, | ||
| 140 | .nacl, | ||
| 141 | .cnk, | ||
| 142 | .aix, | ||
| 143 | .cuda, | ||
| 144 | .nvcl, | ||
| 145 | .amdhsa, | ||
| 146 | .ps4, | ||
| 147 | .elfiamcu, | ||
| 148 | .tvos, | ||
| 149 | .watchos, | ||
| 150 | .mesa3d, | ||
| 151 | .contiki, | ||
| 152 | .amdpal, | ||
| 153 | .hermit, | ||
| 154 | .hurd, | ||
| 155 | .wasi, | ||
| 156 | .emscripten, | ||
| 157 | .uefi, | ||
| 158 | .other, | ||
| 159 | => return .{ .none = {} }, | ||
| 160 | |||
| 161 | .freebsd => return .{ | ||
| 162 | .semver = Version.Range{ | ||
| 163 | .min = .{ .major = 12, .minor = 0 }, | ||
| 164 | .max = .{ .major = 12, .minor = 1 }, | ||
| 165 | }, | ||
| 166 | }, | ||
| 167 | .macosx => return .{ | ||
| 168 | .semver = .{ | ||
| 169 | .min = .{ .major = 10, .minor = 13 }, | ||
| 170 | .max = .{ .major = 10, .minor = 15, .patch = 3 }, | ||
| 171 | }, | ||
| 172 | }, | ||
| 173 | .netbsd => return .{ | ||
| 174 | .semver = .{ | ||
| 175 | .min = .{ .major = 8, .minor = 0 }, | ||
| 176 | .max = .{ .major = 9, .minor = 0 }, | ||
| 177 | }, | ||
| 178 | }, | ||
| 179 | .openbsd => return .{ | ||
| 180 | .semver = .{ | ||
| 181 | .min = .{ .major = 6, .minor = 6 }, | ||
| 182 | .max = .{ .major = 6, .minor = 6 }, | ||
| 183 | }, | ||
| 184 | }, | ||
| 185 | |||
| 186 | .linux => return .{ | ||
| 187 | .linux = .{ | ||
| 188 | .range = .{ | ||
| 189 | .min = .{ .major = 3, .minor = 16 }, | ||
| 190 | .max = .{ .major = 5, .minor = 5, .patch = 5 }, | ||
| 191 | }, | ||
| 192 | .glibc = .{ .major = 2, .minor = 17 }, | ||
| 193 | }, | ||
| 194 | }, | ||
| 195 | |||
| 196 | .windows => return .{ | ||
| 197 | .windows = .{ | ||
| 198 | .min = .win8_1, | ||
| 199 | .max = .win10_19h1, | ||
| 200 | }, | ||
| 201 | }, | ||
| 188 | } | 202 | } |
| 189 | return null; | ||
| 190 | } | 203 | } |
| 191 | }; | 204 | }; |
| 192 | 205 | ||
| 193 | pub fn parse(text: []const u8) !Os { | 206 | pub fn parse(text: []const u8) !Os { |
| 194 | var it = mem.separate(text, "."); | 207 | var it = mem.separate(text, "."); |
| 195 | const os_name = it.next().?; | 208 | const os_name = it.next().?; |
| 196 | const tag = nameToTag(os_name) orelse return error.UnknownOperatingSystem; | 209 | const tag = std.meta.stringToEnum(Tag, os_name) orelse return error.UnknownOperatingSystem; |
| 197 | const version_text = it.rest(); | 210 | const version_text = it.rest(); |
| 198 | const S = struct { | 211 | const S = struct { |
| 199 | fn parseNone(s: []const u8) !void { | 212 | fn parseNone(s: []const u8) !void { |
| 200 | if (s.len != 0) return error.InvalidOperatingSystemVersion; | 213 | if (s.len != 0) return error.InvalidOperatingSystemVersion; |
| 201 | } | 214 | } |
| 202 | fn parseSemVer(s: []const u8, default: Version.Range) !Version.Range { | 215 | fn parseSemVer(s: []const u8, d_range: Version.Range) !Version.Range { |
| 203 | if (s.len == 0) return default; | 216 | if (s.len == 0) return d_range; |
| 204 | var range_it = mem.separate(s, "..."); | 217 | var range_it = mem.separate(s, "..."); |
| 205 | 218 | ||
| 206 | const min_text = range_it.next().?; | 219 | const min_text = range_it.next().?; |
| ... | @@ -212,7 +225,7 @@ pub const Target = struct { | ... | @@ -212,7 +225,7 @@ pub const Target = struct { |
| 212 | 225 | ||
| 213 | const max_text = range_it.next() orelse return Version.Range{ | 226 | const max_text = range_it.next() orelse return Version.Range{ |
| 214 | .min = min_ver, | 227 | .min = min_ver, |
| 215 | .max = default.max, | 228 | .max = d_range.max, |
| 216 | }; | 229 | }; |
| 217 | const max_ver = Version.parse(max_text) catch |err| switch (err) { | 230 | const max_ver = Version.parse(max_text) catch |err| switch (err) { |
| 218 | error.Overflow => return error.InvalidOperatingSystemVersion, | 231 | error.Overflow => return error.InvalidOperatingSystemVersion, |
| ... | @@ -222,79 +235,93 @@ pub const Target = struct { | ... | @@ -222,79 +235,93 @@ pub const Target = struct { |
| 222 | 235 | ||
| 223 | return Version.Range{ .min = min_ver, .max = max_ver }; | 236 | return Version.Range{ .min = min_ver, .max = max_ver }; |
| 224 | } | 237 | } |
| 225 | fn parseWindows(s: []const u8, default: WindowsVersion.Range) !WindowsVersion.Range { | 238 | fn parseWindows(s: []const u8, d_range: WindowsVersion.Range) !WindowsVersion.Range { |
| 226 | if (s.len == 0) return default; | 239 | if (s.len == 0) return d_range; |
| 227 | var range_it = mem.separate(s, "..."); | 240 | var range_it = mem.separate(s, "..."); |
| 228 | 241 | ||
| 229 | const min_text = range_it.next().?; | 242 | const min_text = range_it.next().?; |
| 230 | const min_ver = WindowsVersion.nameToTag(min_text) orelse | 243 | const min_ver = std.meta.stringToEnum(WindowsVersion, min_text) orelse |
| 231 | return error.InvalidOperatingSystemVersion; | 244 | return error.InvalidOperatingSystemVersion; |
| 232 | 245 | ||
| 233 | const max_text = range_it.next() orelse return WindowsVersion.Range{ | 246 | const max_text = range_it.next() orelse return WindowsVersion.Range{ |
| 234 | .min = min_ver, | 247 | .min = min_ver, |
| 235 | .max = default.max, | 248 | .max = d_range.max, |
| 236 | }; | 249 | }; |
| 237 | const max_ver = WindowsVersion.nameToTag(max_text) orelse | 250 | const max_ver = std.meta.stringToEnum(WindowsVersion, max_text) orelse |
| 238 | return error.InvalidOperatingSystemVersion; | 251 | return error.InvalidOperatingSystemVersion; |
| 239 | 252 | ||
| 240 | return WindowsVersion.Range{ .min = min_ver, .max = max_ver }; | 253 | return WindowsVersion.Range{ .min = min_ver, .max = max_ver }; |
| 241 | } | 254 | } |
| 242 | }; | 255 | }; |
| 243 | const default = defaultVersionRange(tag); | 256 | const d_range = VersionRange.default(tag); |
| 244 | switch (tag) { | 257 | switch (tag) { |
| 245 | .freestanding => return Os{ .freestanding = try S.parseNone(version_text) }, | 258 | .freestanding, |
| 246 | .ananas => return Os{ .ananas = try S.parseNone(version_text) }, | 259 | .ananas, |
| 247 | .cloudabi => return Os{ .cloudabi = try S.parseNone(version_text) }, | 260 | .cloudabi, |
| 248 | .dragonfly => return Os{ .dragonfly = try S.parseNone(version_text) }, | 261 | .dragonfly, |
| 249 | .freebsd => return Os{ .freebsd = try S.parseSemVer(version_text, default.freebsd) }, | 262 | .fuchsia, |
| 250 | .fuchsia => return Os{ .fuchsia = try S.parseNone(version_text) }, | 263 | .ios, |
| 251 | .ios => return Os{ .ios = try S.parseNone(version_text) }, | 264 | .kfreebsd, |
| 252 | .kfreebsd => return Os{ .kfreebsd = try S.parseNone(version_text) }, | 265 | .lv2, |
| 266 | .solaris, | ||
| 267 | .haiku, | ||
| 268 | .minix, | ||
| 269 | .rtems, | ||
| 270 | .nacl, | ||
| 271 | .cnk, | ||
| 272 | .aix, | ||
| 273 | .cuda, | ||
| 274 | .nvcl, | ||
| 275 | .amdhsa, | ||
| 276 | .ps4, | ||
| 277 | .elfiamcu, | ||
| 278 | .tvos, | ||
| 279 | .watchos, | ||
| 280 | .mesa3d, | ||
| 281 | .contiki, | ||
| 282 | .amdpal, | ||
| 283 | .hermit, | ||
| 284 | .hurd, | ||
| 285 | .wasi, | ||
| 286 | .emscripten, | ||
| 287 | .uefi, | ||
| 288 | .other, | ||
| 289 | => return Os{ | ||
| 290 | .tag = tag, | ||
| 291 | .version_range = .{ .none = try S.parseNone(version_text) }, | ||
| 292 | }, | ||
| 293 | |||
| 294 | .freebsd, | ||
| 295 | .macosx, | ||
| 296 | .netbsd, | ||
| 297 | .openbsd, | ||
| 298 | => return Os{ | ||
| 299 | .tag = tag, | ||
| 300 | .version_range = .{ .semver = try S.parseSemVer(version_text, d_range.semver) }, | ||
| 301 | }, | ||
| 302 | |||
| 253 | .linux => return Os{ | 303 | .linux => return Os{ |
| 254 | .linux = .{ | 304 | .tag = tag, |
| 255 | .range = try S.parseSemVer(version_text, default.linux.range), | 305 | .version_range = .{ |
| 256 | .glibc = default.linux.glibc, | 306 | .linux = .{ |
| 307 | .range = try S.parseSemVer(version_text, d_range.linux.range), | ||
| 308 | .glibc = d_range.linux.glibc, | ||
| 309 | }, | ||
| 257 | }, | 310 | }, |
| 258 | }, | 311 | }, |
| 259 | .lv2 => return Os{ .lv2 = try S.parseNone(version_text) }, | 312 | |
| 260 | .macosx => return Os{ .macosx = try S.parseSemVer(version_text, default.macosx) }, | 313 | .windows => return Os{ |
| 261 | .netbsd => return Os{ .netbsd = try S.parseSemVer(version_text, default.netbsd) }, | 314 | .tag = tag, |
| 262 | .openbsd => return Os{ .openbsd = try S.parseSemVer(version_text, default.openbsd) }, | 315 | .version_range = .{ .windows = try S.parseWindows(version_text, d_range.windows) }, |
| 263 | .solaris => return Os{ .solaris = try S.parseNone(version_text) }, | 316 | }, |
| 264 | .windows => return Os{ .windows = try S.parseWindows(version_text, default.windows) }, | ||
| 265 | .haiku => return Os{ .haiku = try S.parseNone(version_text) }, | ||
| 266 | .minix => return Os{ .minix = try S.parseNone(version_text) }, | ||
| 267 | .rtems => return Os{ .rtems = try S.parseNone(version_text) }, | ||
| 268 | .nacl => return Os{ .nacl = try S.parseNone(version_text) }, | ||
| 269 | .cnk => return Os{ .cnk = try S.parseNone(version_text) }, | ||
| 270 | .aix => return Os{ .aix = try S.parseNone(version_text) }, | ||
| 271 | .cuda => return Os{ .cuda = try S.parseNone(version_text) }, | ||
| 272 | .nvcl => return Os{ .nvcl = try S.parseNone(version_text) }, | ||
| 273 | .amdhsa => return Os{ .amdhsa = try S.parseNone(version_text) }, | ||
| 274 | .ps4 => return Os{ .ps4 = try S.parseNone(version_text) }, | ||
| 275 | .elfiamcu => return Os{ .elfiamcu = try S.parseNone(version_text) }, | ||
| 276 | .tvos => return Os{ .tvos = try S.parseNone(version_text) }, | ||
| 277 | .watchos => return Os{ .watchos = try S.parseNone(version_text) }, | ||
| 278 | .mesa3d => return Os{ .mesa3d = try S.parseNone(version_text) }, | ||
| 279 | .contiki => return Os{ .contiki = try S.parseNone(version_text) }, | ||
| 280 | .amdpal => return Os{ .amdpal = try S.parseNone(version_text) }, | ||
| 281 | .hermit => return Os{ .hermit = try S.parseNone(version_text) }, | ||
| 282 | .hurd => return Os{ .hurd = try S.parseNone(version_text) }, | ||
| 283 | .wasi => return Os{ .wasi = try S.parseNone(version_text) }, | ||
| 284 | .emscripten => return Os{ .emscripten = try S.parseNone(version_text) }, | ||
| 285 | .uefi => return Os{ .uefi = try S.parseNone(version_text) }, | ||
| 286 | .other => return Os{ .other = try S.parseNone(version_text) }, | ||
| 287 | } | 317 | } |
| 288 | } | 318 | } |
| 289 | 319 | ||
| 290 | pub fn nameToTag(name: []const u8) ?@TagType(Os) { | 320 | pub fn defaultVersionRange(tag: Tag) Os { |
| 291 | const info = @typeInfo(Os); | 321 | return .{ |
| 292 | inline for (info.Union.fields) |field| { | 322 | .tag = tag, |
| 293 | if (mem.eql(u8, name, field.name)) { | 323 | .version_range = VersionRange.default(tag), |
| 294 | return @field(Os, field.name); | 324 | }; |
| 295 | } | ||
| 296 | } | ||
| 297 | return null; | ||
| 298 | } | 325 | } |
| 299 | }; | 326 | }; |
| 300 | 327 | ||
| ... | @@ -339,11 +366,10 @@ pub const Target = struct { | ... | @@ -339,11 +366,10 @@ pub const Target = struct { |
| 339 | macabi, | 366 | macabi, |
| 340 | 367 | ||
| 341 | pub fn default(arch: Cpu.Arch, target_os: Os) Abi { | 368 | pub fn default(arch: Cpu.Arch, target_os: Os) Abi { |
| 342 | switch (arch) { | 369 | if (arch.isWasm()) { |
| 343 | .wasm32, .wasm64 => return .musl, | 370 | return .musl; |
| 344 | else => {}, | ||
| 345 | } | 371 | } |
| 346 | switch (target_os) { | 372 | switch (target_os.tag) { |
| 347 | .freestanding, | 373 | .freestanding, |
| 348 | .ananas, | 374 | .ananas, |
| 349 | .cloudabi, | 375 | .cloudabi, |
| ... | @@ -388,40 +414,19 @@ pub const Target = struct { | ... | @@ -388,40 +414,19 @@ pub const Target = struct { |
| 388 | } | 414 | } |
| 389 | } | 415 | } |
| 390 | 416 | ||
| 391 | pub fn nameToTag(text: []const u8) ?Abi { | ||
| 392 | const info = @typeInfo(Abi); | ||
| 393 | inline for (info.Enum.fields) |field| { | ||
| 394 | if (mem.eql(u8, text, field.name)) { | ||
| 395 | return @field(Abi, field.name); | ||
| 396 | } | ||
| 397 | } | ||
| 398 | return null; | ||
| 399 | } | ||
| 400 | |||
| 401 | pub fn parse(text: []const u8, os: *Os) !Abi { | ||
| 402 | var it = mem.separate(text, "."); | ||
| 403 | const tag = nameToTag(it.next().?) orelse return error.UnknownApplicationBinaryInterface; | ||
| 404 | const version_text = it.rest(); | ||
| 405 | if (version_text.len != 0) { | ||
| 406 | if (@as(@TagType(Os), os.*) == .linux and tag.isGnu()) { | ||
| 407 | os.linux.glibc = Version.parse(version_text) catch |err| switch (err) { | ||
| 408 | error.Overflow => return error.InvalidGlibcVersion, | ||
| 409 | error.InvalidCharacter => return error.InvalidGlibcVersion, | ||
| 410 | error.InvalidVersion => return error.InvalidGlibcVersion, | ||
| 411 | }; | ||
| 412 | } else { | ||
| 413 | return error.InvalidAbiVersion; | ||
| 414 | } | ||
| 415 | } | ||
| 416 | return tag; | ||
| 417 | } | ||
| 418 | |||
| 419 | pub fn isGnu(abi: Abi) bool { | 417 | pub fn isGnu(abi: Abi) bool { |
| 420 | return switch (abi) { | 418 | return switch (abi) { |
| 421 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => true, | 419 | .gnu, .gnuabin32, .gnuabi64, .gnueabi, .gnueabihf, .gnux32 => true, |
| 422 | else => false, | 420 | else => false, |
| 423 | }; | 421 | }; |
| 424 | } | 422 | } |
| 423 | |||
| 424 | pub fn isMusl(abi: Abi) bool { | ||
| 425 | return switch (abi) { | ||
| 426 | .musl, .musleabi, .musleabihf => true, | ||
| 427 | else => false, | ||
| 428 | }; | ||
| 429 | } | ||
| 425 | }; | 430 | }; |
| 426 | 431 | ||
| 427 | pub const ObjectFormat = enum { | 432 | pub const ObjectFormat = enum { |
| ... | @@ -909,15 +914,15 @@ pub const Target = struct { | ... | @@ -909,15 +914,15 @@ pub const Target = struct { |
| 909 | /// TODO add OS version ranges and glibc version | 914 | /// TODO add OS version ranges and glibc version |
| 910 | pub fn zigTriple(self: Target, allocator: *mem.Allocator) ![]u8 { | 915 | pub fn zigTriple(self: Target, allocator: *mem.Allocator) ![]u8 { |
| 911 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ | 916 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ |
| 912 | @tagName(self.getArch()), | 917 | @tagName(self.cpu.arch), |
| 913 | @tagName(self.os), | 918 | @tagName(self.os.tag), |
| 914 | @tagName(self.abi), | 919 | @tagName(self.abi), |
| 915 | }); | 920 | }); |
| 916 | } | 921 | } |
| 917 | 922 | ||
| 918 | /// Returned slice must be freed by the caller. | 923 | /// Returned slice must be freed by the caller. |
| 919 | pub fn vcpkgTriplet(allocator: *mem.Allocator, target: Target, linkage: std.build.VcpkgLinkage) ![]const u8 { | 924 | pub fn vcpkgTriplet(allocator: *mem.Allocator, target: Target, linkage: std.build.VcpkgLinkage) ![]const u8 { |
| 920 | const arch = switch (target.getArch()) { | 925 | const arch = switch (target.cpu.arch) { |
| 921 | .i386 => "x86", | 926 | .i386 => "x86", |
| 922 | .x86_64 => "x64", | 927 | .x86_64 => "x64", |
| 923 | 928 | ||
| ... | @@ -957,16 +962,16 @@ pub const Target = struct { | ... | @@ -957,16 +962,16 @@ pub const Target = struct { |
| 957 | 962 | ||
| 958 | pub fn zigTripleNoSubArch(self: Target, allocator: *mem.Allocator) ![]u8 { | 963 | pub fn zigTripleNoSubArch(self: Target, allocator: *mem.Allocator) ![]u8 { |
| 959 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ | 964 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ |
| 960 | @tagName(self.getArch()), | 965 | @tagName(self.cpu.arch), |
| 961 | @tagName(self.os), | 966 | @tagName(self.os.tag), |
| 962 | @tagName(self.abi), | 967 | @tagName(self.abi), |
| 963 | }); | 968 | }); |
| 964 | } | 969 | } |
| 965 | 970 | ||
| 966 | pub fn linuxTriple(self: Target, allocator: *mem.Allocator) ![]u8 { | 971 | pub fn linuxTriple(self: Target, allocator: *mem.Allocator) ![]u8 { |
| 967 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ | 972 | return std.fmt.allocPrint(allocator, "{}-{}-{}", .{ |
| 968 | @tagName(self.getArch()), | 973 | @tagName(self.cpu.arch), |
| 969 | @tagName(self.os), | 974 | @tagName(self.os.tag), |
| 970 | @tagName(self.abi), | 975 | @tagName(self.abi), |
| 971 | }); | 976 | }); |
| 972 | } | 977 | } |
| ... | @@ -1017,11 +1022,28 @@ pub const Target = struct { | ... | @@ -1017,11 +1022,28 @@ pub const Target = struct { |
| 1017 | diags.arch = arch; | 1022 | diags.arch = arch; |
| 1018 | 1023 | ||
| 1019 | const os_name = it.next() orelse return error.MissingOperatingSystem; | 1024 | const os_name = it.next() orelse return error.MissingOperatingSystem; |
| 1020 | var os = try Os.parse(os_name); // var because Abi.parse can update linux.glibc version | 1025 | var os = try Os.parse(os_name); |
| 1021 | diags.os = os; | 1026 | diags.os = os; |
| 1022 | 1027 | ||
| 1023 | const abi_name = it.next(); | 1028 | const opt_abi_text = it.next(); |
| 1024 | const abi = if (abi_name) |n| try Abi.parse(n, &os) else Abi.default(arch, os); | 1029 | const abi = if (opt_abi_text) |abi_text| blk: { |
| 1030 | var abi_it = mem.separate(abi_text, "."); | ||
| 1031 | const abi = std.meta.stringToEnum(Abi, abi_it.next().?) orelse | ||
| 1032 | return error.UnknownApplicationBinaryInterface; | ||
| 1033 | const abi_ver_text = abi_it.rest(); | ||
| 1034 | if (abi_ver_text.len != 0) { | ||
| 1035 | if (os.tag == .linux and abi.isGnu()) { | ||
| 1036 | os.version_range.linux.glibc = Version.parse(abi_ver_text) catch |err| switch (err) { | ||
| 1037 | error.Overflow => return error.InvalidAbiVersion, | ||
| 1038 | error.InvalidCharacter => return error.InvalidAbiVersion, | ||
| 1039 | error.InvalidVersion => return error.InvalidAbiVersion, | ||
| 1040 | }; | ||
| 1041 | } else { | ||
| 1042 | return error.InvalidAbiVersion; | ||
| 1043 | } | ||
| 1044 | } | ||
| 1045 | break :blk abi; | ||
| 1046 | } else Abi.default(arch, os); | ||
| 1025 | diags.abi = abi; | 1047 | diags.abi = abi; |
| 1026 | 1048 | ||
| 1027 | if (it.next() != null) return error.UnexpectedExtraField; | 1049 | if (it.next() != null) return error.UnexpectedExtraField; |
| ... | @@ -1130,25 +1152,6 @@ pub const Target = struct { | ... | @@ -1130,25 +1152,6 @@ pub const Target = struct { |
| 1130 | } | 1152 | } |
| 1131 | } | 1153 | } |
| 1132 | 1154 | ||
| 1133 | /// Deprecated; access the `os` field directly. | ||
| 1134 | pub fn getOs(self: Target) @TagType(Os) { | ||
| 1135 | return self.os; | ||
| 1136 | } | ||
| 1137 | |||
| 1138 | /// Deprecated; access the `cpu` field directly. | ||
| 1139 | pub fn getCpu(self: Target) Cpu { | ||
| 1140 | return self.cpu; | ||
| 1141 | } | ||
| 1142 | |||
| 1143 | /// Deprecated; access the `abi` field directly. | ||
| 1144 | pub fn getAbi(self: Target) Abi { | ||
| 1145 | return self.abi; | ||
| 1146 | } | ||
| 1147 | |||
| 1148 | pub fn getArch(self: Target) Cpu.Arch { | ||
| 1149 | return self.cpu.arch; | ||
| 1150 | } | ||
| 1151 | |||
| 1152 | pub fn getObjectFormat(self: Target) ObjectFormat { | 1155 | pub fn getObjectFormat(self: Target) ObjectFormat { |
| 1153 | if (self.isWindows() or self.isUefi()) { | 1156 | if (self.isWindows() or self.isUefi()) { |
| 1154 | return .coff; | 1157 | return .coff; |
| ... | @@ -1170,28 +1173,25 @@ pub const Target = struct { | ... | @@ -1170,28 +1173,25 @@ pub const Target = struct { |
| 1170 | } | 1173 | } |
| 1171 | 1174 | ||
| 1172 | pub fn isMusl(self: Target) bool { | 1175 | pub fn isMusl(self: Target) bool { |
| 1173 | return switch (self.abi) { | 1176 | return self.abi.isMusl(); |
| 1174 | .musl, .musleabi, .musleabihf => true, | ||
| 1175 | else => false, | ||
| 1176 | }; | ||
| 1177 | } | 1177 | } |
| 1178 | 1178 | ||
| 1179 | pub fn isDarwin(self: Target) bool { | 1179 | pub fn isDarwin(self: Target) bool { |
| 1180 | return switch (self.os) { | 1180 | return switch (self.os.tag) { |
| 1181 | .ios, .macosx, .watchos, .tvos => true, | 1181 | .ios, .macosx, .watchos, .tvos => true, |
| 1182 | else => false, | 1182 | else => false, |
| 1183 | }; | 1183 | }; |
| 1184 | } | 1184 | } |
| 1185 | 1185 | ||
| 1186 | pub fn isWindows(self: Target) bool { | 1186 | pub fn isWindows(self: Target) bool { |
| 1187 | return switch (self.os) { | 1187 | return switch (self.os.tag) { |
| 1188 | .windows => true, | 1188 | .windows => true, |
| 1189 | else => false, | 1189 | else => false, |
| 1190 | }; | 1190 | }; |
| 1191 | } | 1191 | } |
| 1192 | 1192 | ||
| 1193 | pub fn isLinux(self: Target) bool { | 1193 | pub fn isLinux(self: Target) bool { |
| 1194 | return switch (self.os) { | 1194 | return switch (self.os.tag) { |
| 1195 | .linux => true, | 1195 | .linux => true, |
| 1196 | else => false, | 1196 | else => false, |
| 1197 | }; | 1197 | }; |
| ... | @@ -1205,40 +1205,41 @@ pub const Target = struct { | ... | @@ -1205,40 +1205,41 @@ pub const Target = struct { |
| 1205 | } | 1205 | } |
| 1206 | 1206 | ||
| 1207 | pub fn isDragonFlyBSD(self: Target) bool { | 1207 | pub fn isDragonFlyBSD(self: Target) bool { |
| 1208 | return switch (self.os) { | 1208 | return switch (self.os.tag) { |
| 1209 | .dragonfly => true, | 1209 | .dragonfly => true, |
| 1210 | else => false, | 1210 | else => false, |
| 1211 | }; | 1211 | }; |
| 1212 | } | 1212 | } |
| 1213 | 1213 | ||
| 1214 | pub fn isUefi(self: Target) bool { | 1214 | pub fn isUefi(self: Target) bool { |
| 1215 | return switch (self.os) { | 1215 | return switch (self.os.tag) { |
| 1216 | .uefi => true, | 1216 | .uefi => true, |
| 1217 | else => false, | 1217 | else => false, |
| 1218 | }; | 1218 | }; |
| 1219 | } | 1219 | } |
| 1220 | 1220 | ||
| 1221 | pub fn isWasm(self: Target) bool { | 1221 | pub fn isWasm(self: Target) bool { |
| 1222 | return switch (self.getArch()) { | 1222 | return self.cpu.arch.isWasm(); |
| 1223 | .wasm32, .wasm64 => true, | ||
| 1224 | else => false, | ||
| 1225 | }; | ||
| 1226 | } | 1223 | } |
| 1227 | 1224 | ||
| 1228 | pub fn isFreeBSD(self: Target) bool { | 1225 | pub fn isFreeBSD(self: Target) bool { |
| 1229 | return switch (self.os) { | 1226 | return switch (self.os.tag) { |
| 1230 | .freebsd => true, | 1227 | .freebsd => true, |
| 1231 | else => false, | 1228 | else => false, |
| 1232 | }; | 1229 | }; |
| 1233 | } | 1230 | } |
| 1234 | 1231 | ||
| 1235 | pub fn isNetBSD(self: Target) bool { | 1232 | pub fn isNetBSD(self: Target) bool { |
| 1236 | return switch (self.os) { | 1233 | return switch (self.os.tag) { |
| 1237 | .netbsd => true, | 1234 | .netbsd => true, |
| 1238 | else => false, | 1235 | else => false, |
| 1239 | }; | 1236 | }; |
| 1240 | } | 1237 | } |
| 1241 | 1238 | ||
| 1239 | pub fn isGnuLibC(self: Target) bool { | ||
| 1240 | return self.os.tag == .linux and self.abi.isGnu(); | ||
| 1241 | } | ||
| 1242 | |||
| 1242 | pub fn wantSharedLibSymLinks(self: Target) bool { | 1243 | pub fn wantSharedLibSymLinks(self: Target) bool { |
| 1243 | return !self.isWindows(); | 1244 | return !self.isWindows(); |
| 1244 | } | 1245 | } |
| ... | @@ -1248,7 +1249,7 @@ pub const Target = struct { | ... | @@ -1248,7 +1249,7 @@ pub const Target = struct { |
| 1248 | } | 1249 | } |
| 1249 | 1250 | ||
| 1250 | pub fn getArchPtrBitWidth(self: Target) u32 { | 1251 | pub fn getArchPtrBitWidth(self: Target) u32 { |
| 1251 | switch (self.getArch()) { | 1252 | switch (self.cpu.arch) { |
| 1252 | .avr, | 1253 | .avr, |
| 1253 | .msp430, | 1254 | .msp430, |
| 1254 | => return 16, | 1255 | => return 16, |
| ... | @@ -1323,8 +1324,8 @@ pub const Target = struct { | ... | @@ -1323,8 +1324,8 @@ pub const Target = struct { |
| 1323 | if (@as(@TagType(Target), self) == .Native) return .native; | 1324 | if (@as(@TagType(Target), self) == .Native) return .native; |
| 1324 | 1325 | ||
| 1325 | // If the target OS matches the host OS, we can use QEMU to emulate a foreign architecture. | 1326 | // If the target OS matches the host OS, we can use QEMU to emulate a foreign architecture. |
| 1326 | if (self.os == builtin.os) { | 1327 | if (self.os.tag == builtin.os.tag) { |
| 1327 | return switch (self.getArch()) { | 1328 | return switch (self.cpu.arch) { |
| 1328 | .aarch64 => Executor{ .qemu = "qemu-aarch64" }, | 1329 | .aarch64 => Executor{ .qemu = "qemu-aarch64" }, |
| 1329 | .aarch64_be => Executor{ .qemu = "qemu-aarch64_be" }, | 1330 | .aarch64_be => Executor{ .qemu = "qemu-aarch64_be" }, |
| 1330 | .arm => Executor{ .qemu = "qemu-arm" }, | 1331 | .arm => Executor{ .qemu = "qemu-arm" }, |
| ... | @@ -1381,13 +1382,10 @@ pub const Target = struct { | ... | @@ -1381,13 +1382,10 @@ pub const Target = struct { |
| 1381 | } | 1382 | } |
| 1382 | 1383 | ||
| 1383 | pub fn hasDynamicLinker(self: Target) bool { | 1384 | pub fn hasDynamicLinker(self: Target) bool { |
| 1384 | switch (self.getArch()) { | 1385 | if (self.cpu.arch.isWasm()) { |
| 1385 | .wasm32, | 1386 | return false; |
| 1386 | .wasm64, | ||
| 1387 | => return false, | ||
| 1388 | else => {}, | ||
| 1389 | } | 1387 | } |
| 1390 | switch (self.os) { | 1388 | switch (self.os.tag) { |
| 1391 | .freestanding, | 1389 | .freestanding, |
| 1392 | .ios, | 1390 | .ios, |
| 1393 | .tvos, | 1391 | .tvos, |
| ... | @@ -1424,7 +1422,7 @@ pub const Target = struct { | ... | @@ -1424,7 +1422,7 @@ pub const Target = struct { |
| 1424 | defer result.deinit(); | 1422 | defer result.deinit(); |
| 1425 | 1423 | ||
| 1426 | var is_arm = false; | 1424 | var is_arm = false; |
| 1427 | switch (self.getArch()) { | 1425 | switch (self.cpu.arch) { |
| 1428 | .arm, .thumb => { | 1426 | .arm, .thumb => { |
| 1429 | try result.append("arm"); | 1427 | try result.append("arm"); |
| 1430 | is_arm = true; | 1428 | is_arm = true; |
| ... | @@ -1442,11 +1440,11 @@ pub const Target = struct { | ... | @@ -1442,11 +1440,11 @@ pub const Target = struct { |
| 1442 | return result.toOwnedSlice(); | 1440 | return result.toOwnedSlice(); |
| 1443 | } | 1441 | } |
| 1444 | 1442 | ||
| 1445 | switch (self.os) { | 1443 | switch (self.os.tag) { |
| 1446 | .freebsd => return mem.dupeZ(a, u8, "/libexec/ld-elf.so.1"), | 1444 | .freebsd => return mem.dupeZ(a, u8, "/libexec/ld-elf.so.1"), |
| 1447 | .netbsd => return mem.dupeZ(a, u8, "/libexec/ld.elf_so"), | 1445 | .netbsd => return mem.dupeZ(a, u8, "/libexec/ld.elf_so"), |
| 1448 | .dragonfly => return mem.dupeZ(a, u8, "/libexec/ld-elf.so.2"), | 1446 | .dragonfly => return mem.dupeZ(a, u8, "/libexec/ld-elf.so.2"), |
| 1449 | .linux => switch (self.getArch()) { | 1447 | .linux => switch (self.cpu.arch) { |
| 1450 | .i386, | 1448 | .i386, |
| 1451 | .sparc, | 1449 | .sparc, |
| 1452 | .sparcel, | 1450 | .sparcel, |
| ... | @@ -1539,7 +1537,7 @@ test "Target.parse" { | ... | @@ -1539,7 +1537,7 @@ test "Target.parse" { |
| 1539 | .cpu_features = "x86_64-sse-sse2-avx-cx8", | 1537 | .cpu_features = "x86_64-sse-sse2-avx-cx8", |
| 1540 | }); | 1538 | }); |
| 1541 | 1539 | ||
| 1542 | std.testing.expect(target.os == .linux); | 1540 | std.testing.expect(target.os.tag == .linux); |
| 1543 | std.testing.expect(target.abi == .gnu); | 1541 | std.testing.expect(target.abi == .gnu); |
| 1544 | std.testing.expect(target.cpu.arch == .x86_64); | 1542 | std.testing.expect(target.cpu.arch == .x86_64); |
| 1545 | std.testing.expect(!Target.x86.featureSetHas(target.cpu.features, .sse)); | 1543 | std.testing.expect(!Target.x86.featureSetHas(target.cpu.features, .sse)); |
| ... | @@ -1554,10 +1552,29 @@ test "Target.parse" { | ... | @@ -1554,10 +1552,29 @@ test "Target.parse" { |
| 1554 | .cpu_features = "generic+v8a", | 1552 | .cpu_features = "generic+v8a", |
| 1555 | }); | 1553 | }); |
| 1556 | 1554 | ||
| 1557 | std.testing.expect(target.os == .linux); | 1555 | std.testing.expect(target.os.tag == .linux); |
| 1558 | std.testing.expect(target.abi == .musleabihf); | 1556 | std.testing.expect(target.abi == .musleabihf); |
| 1559 | std.testing.expect(target.cpu.arch == .arm); | 1557 | std.testing.expect(target.cpu.arch == .arm); |
| 1560 | std.testing.expect(target.cpu.model == &Target.arm.cpu.generic); | 1558 | std.testing.expect(target.cpu.model == &Target.arm.cpu.generic); |
| 1561 | std.testing.expect(Target.arm.featureSetHas(target.cpu.features, .v8a)); | 1559 | std.testing.expect(Target.arm.featureSetHas(target.cpu.features, .v8a)); |
| 1562 | } | 1560 | } |
| 1561 | { | ||
| 1562 | const target = try Target.parse(.{ | ||
| 1563 | .arch_os_abi = "aarch64-linux.3.10...4.4.1-gnu.2.27", | ||
| 1564 | .cpu_features = "generic+v8a", | ||
| 1565 | }); | ||
| 1566 | |||
| 1567 | std.testing.expect(target.cpu.arch == .aarch64); | ||
| 1568 | std.testing.expect(target.os.tag == .linux); | ||
| 1569 | std.testing.expect(target.os.version_range.linux.min.major == 3); | ||
| 1570 | std.testing.expect(target.os.version_range.linux.min.minor == 10); | ||
| 1571 | std.testing.expect(target.os.version_range.linux.min.patch == 0); | ||
| 1572 | std.testing.expect(target.os.version_range.linux.max.major == 4); | ||
| 1573 | std.testing.expect(target.os.version_range.linux.max.minor == 4); | ||
| 1574 | std.testing.expect(target.os.version_range.linux.max.patch == 1); | ||
| 1575 | std.testing.expect(target.os.version_range.linux.glibc.major == 2); | ||
| 1576 | std.testing.expect(target.os.version_range.linux.glibc.minor == 27); | ||
| 1577 | std.testing.expect(target.os.version_range.linux.glibc.patch == 0); | ||
| 1578 | std.testing.expect(target.abi == .gnu); | ||
| 1579 | } | ||
| 1563 | } | 1580 | } |
lib/std/thread.zig+10-10| ... | @@ -9,14 +9,14 @@ const assert = std.debug.assert; | ... | @@ -9,14 +9,14 @@ const assert = std.debug.assert; |
| 9 | pub const Thread = struct { | 9 | pub const Thread = struct { |
| 10 | data: Data, | 10 | data: Data, |
| 11 | 11 | ||
| 12 | pub const use_pthreads = builtin.os != .windows and builtin.link_libc; | 12 | pub const use_pthreads = builtin.os.tag != .windows and builtin.link_libc; |
| 13 | 13 | ||
| 14 | /// Represents a kernel thread handle. | 14 | /// Represents a kernel thread handle. |
| 15 | /// May be an integer or a pointer depending on the platform. | 15 | /// May be an integer or a pointer depending on the platform. |
| 16 | /// On Linux and POSIX, this is the same as Id. | 16 | /// On Linux and POSIX, this is the same as Id. |
| 17 | pub const Handle = if (use_pthreads) | 17 | pub const Handle = if (use_pthreads) |
| 18 | c.pthread_t | 18 | c.pthread_t |
| 19 | else switch (builtin.os) { | 19 | else switch (builtin.os.tag) { |
| 20 | .linux => i32, | 20 | .linux => i32, |
| 21 | .windows => windows.HANDLE, | 21 | .windows => windows.HANDLE, |
| 22 | else => void, | 22 | else => void, |
| ... | @@ -25,7 +25,7 @@ pub const Thread = struct { | ... | @@ -25,7 +25,7 @@ pub const Thread = struct { |
| 25 | /// Represents a unique ID per thread. | 25 | /// Represents a unique ID per thread. |
| 26 | /// May be an integer or pointer depending on the platform. | 26 | /// May be an integer or pointer depending on the platform. |
| 27 | /// On Linux and POSIX, this is the same as Handle. | 27 | /// On Linux and POSIX, this is the same as Handle. |
| 28 | pub const Id = switch (builtin.os) { | 28 | pub const Id = switch (builtin.os.tag) { |
| 29 | .windows => windows.DWORD, | 29 | .windows => windows.DWORD, |
| 30 | else => Handle, | 30 | else => Handle, |
| 31 | }; | 31 | }; |
| ... | @@ -35,7 +35,7 @@ pub const Thread = struct { | ... | @@ -35,7 +35,7 @@ pub const Thread = struct { |
| 35 | handle: Thread.Handle, | 35 | handle: Thread.Handle, |
| 36 | memory: []align(mem.page_size) u8, | 36 | memory: []align(mem.page_size) u8, |
| 37 | } | 37 | } |
| 38 | else switch (builtin.os) { | 38 | else switch (builtin.os.tag) { |
| 39 | .linux => struct { | 39 | .linux => struct { |
| 40 | handle: Thread.Handle, | 40 | handle: Thread.Handle, |
| 41 | memory: []align(mem.page_size) u8, | 41 | memory: []align(mem.page_size) u8, |
| ... | @@ -55,7 +55,7 @@ pub const Thread = struct { | ... | @@ -55,7 +55,7 @@ pub const Thread = struct { |
| 55 | if (use_pthreads) { | 55 | if (use_pthreads) { |
| 56 | return c.pthread_self(); | 56 | return c.pthread_self(); |
| 57 | } else | 57 | } else |
| 58 | return switch (builtin.os) { | 58 | return switch (builtin.os.tag) { |
| 59 | .linux => os.linux.gettid(), | 59 | .linux => os.linux.gettid(), |
| 60 | .windows => windows.kernel32.GetCurrentThreadId(), | 60 | .windows => windows.kernel32.GetCurrentThreadId(), |
| 61 | else => @compileError("Unsupported OS"), | 61 | else => @compileError("Unsupported OS"), |
| ... | @@ -83,7 +83,7 @@ pub const Thread = struct { | ... | @@ -83,7 +83,7 @@ pub const Thread = struct { |
| 83 | else => unreachable, | 83 | else => unreachable, |
| 84 | } | 84 | } |
| 85 | os.munmap(self.data.memory); | 85 | os.munmap(self.data.memory); |
| 86 | } else switch (builtin.os) { | 86 | } else switch (builtin.os.tag) { |
| 87 | .linux => { | 87 | .linux => { |
| 88 | while (true) { | 88 | while (true) { |
| 89 | const pid_value = @atomicLoad(i32, &self.data.handle, .SeqCst); | 89 | const pid_value = @atomicLoad(i32, &self.data.handle, .SeqCst); |
| ... | @@ -150,7 +150,7 @@ pub const Thread = struct { | ... | @@ -150,7 +150,7 @@ pub const Thread = struct { |
| 150 | const Context = @TypeOf(context); | 150 | const Context = @TypeOf(context); |
| 151 | comptime assert(@typeInfo(@TypeOf(startFn)).Fn.args[0].arg_type.? == Context); | 151 | comptime assert(@typeInfo(@TypeOf(startFn)).Fn.args[0].arg_type.? == Context); |
| 152 | 152 | ||
| 153 | if (builtin.os == builtin.Os.windows) { | 153 | if (builtin.os.tag == .windows) { |
| 154 | const WinThread = struct { | 154 | const WinThread = struct { |
| 155 | const OuterContext = struct { | 155 | const OuterContext = struct { |
| 156 | thread: Thread, | 156 | thread: Thread, |
| ... | @@ -309,7 +309,7 @@ pub const Thread = struct { | ... | @@ -309,7 +309,7 @@ pub const Thread = struct { |
| 309 | os.EINVAL => unreachable, | 309 | os.EINVAL => unreachable, |
| 310 | else => return os.unexpectedErrno(@intCast(usize, err)), | 310 | else => return os.unexpectedErrno(@intCast(usize, err)), |
| 311 | } | 311 | } |
| 312 | } else if (builtin.os == .linux) { | 312 | } else if (builtin.os.tag == .linux) { |
| 313 | var flags: u32 = os.CLONE_VM | os.CLONE_FS | os.CLONE_FILES | os.CLONE_SIGHAND | | 313 | var flags: u32 = os.CLONE_VM | os.CLONE_FS | os.CLONE_FILES | os.CLONE_SIGHAND | |
| 314 | os.CLONE_THREAD | os.CLONE_SYSVSEM | os.CLONE_PARENT_SETTID | os.CLONE_CHILD_CLEARTID | | 314 | os.CLONE_THREAD | os.CLONE_SYSVSEM | os.CLONE_PARENT_SETTID | os.CLONE_CHILD_CLEARTID | |
| 315 | os.CLONE_DETACHED; | 315 | os.CLONE_DETACHED; |
| ... | @@ -369,11 +369,11 @@ pub const Thread = struct { | ... | @@ -369,11 +369,11 @@ pub const Thread = struct { |
| 369 | }; | 369 | }; |
| 370 | 370 | ||
| 371 | pub fn cpuCount() CpuCountError!usize { | 371 | pub fn cpuCount() CpuCountError!usize { |
| 372 | if (builtin.os == .linux) { | 372 | if (builtin.os.tag == .linux) { |
| 373 | const cpu_set = try os.sched_getaffinity(0); | 373 | const cpu_set = try os.sched_getaffinity(0); |
| 374 | return @as(usize, os.CPU_COUNT(cpu_set)); // TODO should not need this usize cast | 374 | return @as(usize, os.CPU_COUNT(cpu_set)); // TODO should not need this usize cast |
| 375 | } | 375 | } |
| 376 | if (builtin.os == .windows) { | 376 | if (builtin.os.tag == .windows) { |
| 377 | var system_info: windows.SYSTEM_INFO = undefined; | 377 | var system_info: windows.SYSTEM_INFO = undefined; |
| 378 | windows.kernel32.GetSystemInfo(&system_info); | 378 | windows.kernel32.GetSystemInfo(&system_info); |
| 379 | return @intCast(usize, system_info.dwNumberOfProcessors); | 379 | return @intCast(usize, system_info.dwNumberOfProcessors); |
lib/std/time.zig+10-8| ... | @@ -1,5 +1,5 @@ | ... | @@ -1,5 +1,5 @@ |
| 1 | const builtin = @import("builtin"); | ||
| 2 | const std = @import("std.zig"); | 1 | const std = @import("std.zig"); |
| 2 | const builtin = std.builtin; | ||
| 3 | const assert = std.debug.assert; | 3 | const assert = std.debug.assert; |
| 4 | const testing = std.testing; | 4 | const testing = std.testing; |
| 5 | const os = std.os; | 5 | const os = std.os; |
| ... | @@ -7,10 +7,12 @@ const math = std.math; | ... | @@ -7,10 +7,12 @@ const math = std.math; |
| 7 | 7 | ||
| 8 | pub const epoch = @import("time/epoch.zig"); | 8 | pub const epoch = @import("time/epoch.zig"); |
| 9 | 9 | ||
| 10 | const is_windows = std.Target.current.os.tag == .windows; | ||
| 11 | |||
| 10 | /// Spurious wakeups are possible and no precision of timing is guaranteed. | 12 | /// Spurious wakeups are possible and no precision of timing is guaranteed. |
| 11 | /// TODO integrate with evented I/O | 13 | /// TODO integrate with evented I/O |
| 12 | pub fn sleep(nanoseconds: u64) void { | 14 | pub fn sleep(nanoseconds: u64) void { |
| 13 | if (builtin.os == .windows) { | 15 | if (is_windows) { |
| 14 | const ns_per_ms = ns_per_s / ms_per_s; | 16 | const ns_per_ms = ns_per_s / ms_per_s; |
| 15 | const big_ms_from_ns = nanoseconds / ns_per_ms; | 17 | const big_ms_from_ns = nanoseconds / ns_per_ms; |
| 16 | const ms = math.cast(os.windows.DWORD, big_ms_from_ns) catch math.maxInt(os.windows.DWORD); | 18 | const ms = math.cast(os.windows.DWORD, big_ms_from_ns) catch math.maxInt(os.windows.DWORD); |
| ... | @@ -31,7 +33,7 @@ pub fn timestamp() u64 { | ... | @@ -31,7 +33,7 @@ pub fn timestamp() u64 { |
| 31 | /// Get the posix timestamp, UTC, in milliseconds | 33 | /// Get the posix timestamp, UTC, in milliseconds |
| 32 | /// TODO audit this function. is it possible to return an error? | 34 | /// TODO audit this function. is it possible to return an error? |
| 33 | pub fn milliTimestamp() u64 { | 35 | pub fn milliTimestamp() u64 { |
| 34 | if (builtin.os == .windows) { | 36 | if (is_windows) { |
| 35 | //FileTime has a granularity of 100 nanoseconds | 37 | //FileTime has a granularity of 100 nanoseconds |
| 36 | // and uses the NTFS/Windows epoch | 38 | // and uses the NTFS/Windows epoch |
| 37 | var ft: os.windows.FILETIME = undefined; | 39 | var ft: os.windows.FILETIME = undefined; |
| ... | @@ -42,7 +44,7 @@ pub fn milliTimestamp() u64 { | ... | @@ -42,7 +44,7 @@ pub fn milliTimestamp() u64 { |
| 42 | const ft64 = (@as(u64, ft.dwHighDateTime) << 32) | ft.dwLowDateTime; | 44 | const ft64 = (@as(u64, ft.dwHighDateTime) << 32) | ft.dwLowDateTime; |
| 43 | return @divFloor(ft64, hns_per_ms) - -epoch_adj; | 45 | return @divFloor(ft64, hns_per_ms) - -epoch_adj; |
| 44 | } | 46 | } |
| 45 | if (builtin.os == .wasi and !builtin.link_libc) { | 47 | if (builtin.os.tag == .wasi and !builtin.link_libc) { |
| 46 | var ns: os.wasi.timestamp_t = undefined; | 48 | var ns: os.wasi.timestamp_t = undefined; |
| 47 | 49 | ||
| 48 | // TODO: Verify that precision is ignored | 50 | // TODO: Verify that precision is ignored |
| ... | @@ -102,7 +104,7 @@ pub const Timer = struct { | ... | @@ -102,7 +104,7 @@ pub const Timer = struct { |
| 102 | ///if we used resolution's value when performing the | 104 | ///if we used resolution's value when performing the |
| 103 | /// performance counter calc on windows/darwin, it would | 105 | /// performance counter calc on windows/darwin, it would |
| 104 | /// be less precise | 106 | /// be less precise |
| 105 | frequency: switch (builtin.os) { | 107 | frequency: switch (builtin.os.tag) { |
| 106 | .windows => u64, | 108 | .windows => u64, |
| 107 | .macosx, .ios, .tvos, .watchos => os.darwin.mach_timebase_info_data, | 109 | .macosx, .ios, .tvos, .watchos => os.darwin.mach_timebase_info_data, |
| 108 | else => void, | 110 | else => void, |
| ... | @@ -127,7 +129,7 @@ pub const Timer = struct { | ... | @@ -127,7 +129,7 @@ pub const Timer = struct { |
| 127 | pub fn start() Error!Timer { | 129 | pub fn start() Error!Timer { |
| 128 | var self: Timer = undefined; | 130 | var self: Timer = undefined; |
| 129 | 131 | ||
| 130 | if (builtin.os == .windows) { | 132 | if (is_windows) { |
| 131 | self.frequency = os.windows.QueryPerformanceFrequency(); | 133 | self.frequency = os.windows.QueryPerformanceFrequency(); |
| 132 | self.resolution = @divFloor(ns_per_s, self.frequency); | 134 | self.resolution = @divFloor(ns_per_s, self.frequency); |
| 133 | self.start_time = os.windows.QueryPerformanceCounter(); | 135 | self.start_time = os.windows.QueryPerformanceCounter(); |
| ... | @@ -172,7 +174,7 @@ pub const Timer = struct { | ... | @@ -172,7 +174,7 @@ pub const Timer = struct { |
| 172 | } | 174 | } |
| 173 | 175 | ||
| 174 | fn clockNative() u64 { | 176 | fn clockNative() u64 { |
| 175 | if (builtin.os == .windows) { | 177 | if (is_windows) { |
| 176 | return os.windows.QueryPerformanceCounter(); | 178 | return os.windows.QueryPerformanceCounter(); |
| 177 | } | 179 | } |
| 178 | if (comptime std.Target.current.isDarwin()) { | 180 | if (comptime std.Target.current.isDarwin()) { |
| ... | @@ -184,7 +186,7 @@ pub const Timer = struct { | ... | @@ -184,7 +186,7 @@ pub const Timer = struct { |
| 184 | } | 186 | } |
| 185 | 187 | ||
| 186 | fn nativeDurationToNanos(self: Timer, duration: u64) u64 { | 188 | fn nativeDurationToNanos(self: Timer, duration: u64) u64 { |
| 187 | if (builtin.os == .windows) { | 189 | if (is_windows) { |
| 188 | return @divFloor(duration * ns_per_s, self.frequency); | 190 | return @divFloor(duration * ns_per_s, self.frequency); |
| 189 | } | 191 | } |
| 190 | if (comptime std.Target.current.isDarwin()) { | 192 | if (comptime std.Target.current.isDarwin()) { |
lib/std/zig/system.zig+328-2| ... | @@ -1,11 +1,14 @@ | ... | @@ -1,11 +1,14 @@ |
| 1 | const std = @import("../std.zig"); | 1 | const std = @import("../std.zig"); |
| 2 | const elf = std.elf; | ||
| 2 | const mem = std.mem; | 3 | const mem = std.mem; |
| 4 | const fs = std.fs; | ||
| 3 | const Allocator = std.mem.Allocator; | 5 | const Allocator = std.mem.Allocator; |
| 4 | const ArrayList = std.ArrayList; | 6 | const ArrayList = std.ArrayList; |
| 5 | const assert = std.debug.assert; | 7 | const assert = std.debug.assert; |
| 6 | const process = std.process; | 8 | const process = std.process; |
| 9 | const Target = std.Target; | ||
| 7 | 10 | ||
| 8 | const is_windows = std.Target.current.isWindows(); | 11 | const is_windows = Target.current.os.tag == .windows; |
| 9 | 12 | ||
| 10 | pub const NativePaths = struct { | 13 | pub const NativePaths = struct { |
| 11 | include_dirs: ArrayList([:0]u8), | 14 | include_dirs: ArrayList([:0]u8), |
| ... | @@ -77,7 +80,7 @@ pub const NativePaths = struct { | ... | @@ -77,7 +80,7 @@ pub const NativePaths = struct { |
| 77 | } | 80 | } |
| 78 | 81 | ||
| 79 | if (!is_windows) { | 82 | if (!is_windows) { |
| 80 | const triple = try std.Target.current.linuxTriple(allocator); | 83 | const triple = try Target.current.linuxTriple(allocator); |
| 81 | 84 | ||
| 82 | // TODO: $ ld --verbose | grep SEARCH_DIR | 85 | // TODO: $ ld --verbose | grep SEARCH_DIR |
| 83 | // the output contains some paths that end with lib64, maybe include them too? | 86 | // the output contains some paths that end with lib64, maybe include them too? |
| ... | @@ -161,3 +164,326 @@ pub const NativePaths = struct { | ... | @@ -161,3 +164,326 @@ pub const NativePaths = struct { |
| 161 | try array.append(item); | 164 | try array.append(item); |
| 162 | } | 165 | } |
| 163 | }; | 166 | }; |
| 167 | |||
| 168 | pub const NativeTargetInfo = struct { | ||
| 169 | target: Target, | ||
| 170 | dynamic_linker: ?[:0]u8, | ||
| 171 | |||
| 172 | pub const DetectError = error{ | ||
| 173 | OutOfMemory, | ||
| 174 | FileSystem, | ||
| 175 | SystemResources, | ||
| 176 | SymLinkLoop, | ||
| 177 | ProcessFdQuotaExceeded, | ||
| 178 | SystemFdQuotaExceeded, | ||
| 179 | DeviceBusy, | ||
| 180 | }; | ||
| 181 | |||
| 182 | /// Detects the native CPU model & features, operating system & version, and C ABI & dynamic linker. | ||
| 183 | /// On Linux, this is additionally responsible for detecting the native glibc version when applicable. | ||
| 184 | pub fn detect(allocator: *Allocator) DetectError!NativeTargetInfo { | ||
| 185 | const arch = Target.current.cpu.arch; | ||
| 186 | const os_tag = Target.current.os.tag; | ||
| 187 | |||
| 188 | // TODO Detect native CPU model & features. Until that is implemented we hard code baseline. | ||
| 189 | const cpu = Target.Cpu.baseline(arch); | ||
| 190 | |||
| 191 | // TODO Detect native operating system version. Until that is implemented we use the minimum version | ||
| 192 | // of the default range. | ||
| 193 | const os = Target.Os.defaultVersionRange(os_tag); | ||
| 194 | |||
| 195 | return detectAbiAndDynamicLinker(allocator, cpu, os); | ||
| 196 | } | ||
| 197 | |||
| 198 | /// Must be the same `Allocator` passed to `detect`. | ||
| 199 | pub fn deinit(self: *NativeTargetInfo, allocator: *Allocator) void { | ||
| 200 | if (self.dynamic_linker) |dl| allocator.free(dl); | ||
| 201 | self.* = undefined; | ||
| 202 | } | ||
| 203 | |||
| 204 | /// First we attempt to use the executable's own binary. If it is dynamically | ||
| 205 | /// linked, then it should answer both the C ABI question and the dynamic linker question. | ||
| 206 | /// If it is statically linked, then we try /usr/bin/env. If that does not provide the answer, then | ||
| 207 | /// we fall back to the defaults. | ||
| 208 | fn detectAbiAndDynamicLinker( | ||
| 209 | allocator: *Allocator, | ||
| 210 | cpu: Target.Cpu, | ||
| 211 | os: Target.Os, | ||
| 212 | ) DetectError!NativeTargetInfo { | ||
| 213 | if (!comptime Target.current.hasDynamicLinker()) { | ||
| 214 | return defaultAbiAndDynamicLinker(allocator, cpu, os); | ||
| 215 | } | ||
| 216 | // The current target's ABI cannot be relied on for this. For example, we may build the zig | ||
| 217 | // compiler for target riscv64-linux-musl and provide a tarball for users to download. | ||
| 218 | // A user could then run that zig compiler on riscv64-linux-gnu. This use case is well-defined | ||
| 219 | // and supported by Zig. But that means that we must detect the system ABI here rather than | ||
| 220 | // relying on `Target.current`. | ||
| 221 | const LdInfo = struct { | ||
| 222 | ld_path: []u8, | ||
| 223 | abi: Target.Abi, | ||
| 224 | }; | ||
| 225 | var ld_info_list = std.ArrayList(LdInfo).init(allocator); | ||
| 226 | defer { | ||
| 227 | for (ld_info_list.toSlice()) |ld_info| allocator.free(ld_info.ld_path); | ||
| 228 | ld_info_list.deinit(); | ||
| 229 | } | ||
| 230 | |||
| 231 | const all_abis = comptime blk: { | ||
| 232 | assert(@enumToInt(Target.Abi.none) == 0); | ||
| 233 | const fields = std.meta.fields(Target.Abi)[1..]; | ||
| 234 | var array: [fields.len]Target.Abi = undefined; | ||
| 235 | inline for (fields) |field, i| { | ||
| 236 | array[i] = @field(Target.Abi, field.name); | ||
| 237 | } | ||
| 238 | break :blk array; | ||
| 239 | }; | ||
| 240 | for (all_abis) |abi| { | ||
| 241 | // This may be a nonsensical parameter. We detect this with error.UnknownDynamicLinkerPath and | ||
| 242 | // skip adding it to `ld_info_list`. | ||
| 243 | const target: Target = .{ | ||
| 244 | .cpu = cpu, | ||
| 245 | .os = os, | ||
| 246 | .abi = abi, | ||
| 247 | }; | ||
| 248 | const standard_ld_path = target.getStandardDynamicLinkerPath(allocator) catch |err| switch (err) { | ||
| 249 | error.OutOfMemory => return error.OutOfMemory, | ||
| 250 | error.UnknownDynamicLinkerPath, error.TargetHasNoDynamicLinker => continue, | ||
| 251 | }; | ||
| 252 | errdefer allocator.free(standard_ld_path); | ||
| 253 | try ld_info_list.append(.{ | ||
| 254 | .ld_path = standard_ld_path, | ||
| 255 | .abi = abi, | ||
| 256 | }); | ||
| 257 | } | ||
| 258 | |||
| 259 | // Best case scenario: the executable is dynamically linked, and we can iterate | ||
| 260 | // over our own shared objects and find a dynamic linker. | ||
| 261 | self_exe: { | ||
| 262 | const lib_paths = try std.process.getSelfExeSharedLibPaths(allocator); | ||
| 263 | defer allocator.free(lib_paths); | ||
| 264 | |||
| 265 | var found_ld_info: LdInfo = undefined; | ||
| 266 | var found_ld_path: [:0]const u8 = undefined; | ||
| 267 | |||
| 268 | // Look for dynamic linker. | ||
| 269 | // This is O(N^M) but typical case here is N=2 and M=10. | ||
| 270 | find_ld: for (lib_paths) |lib_path| { | ||
| 271 | for (ld_info_list.toSlice()) |ld_info| { | ||
| 272 | const standard_ld_basename = fs.path.basename(ld_info.ld_path); | ||
| 273 | if (std.mem.endsWith(u8, lib_path, standard_ld_basename)) { | ||
| 274 | found_ld_info = ld_info; | ||
| 275 | found_ld_path = lib_path; | ||
| 276 | break :find_ld; | ||
| 277 | } | ||
| 278 | } | ||
| 279 | } else break :self_exe; | ||
| 280 | |||
| 281 | // Look for glibc version. | ||
| 282 | var os_adjusted = os; | ||
| 283 | if (Target.current.os.tag == .linux and found_ld_info.abi.isGnu()) { | ||
| 284 | for (lib_paths) |lib_path| { | ||
| 285 | if (std.mem.endsWith(u8, lib_path, glibc_so_basename)) { | ||
| 286 | os_adjusted.version_range.linux.glibc = glibcVerFromSO(lib_path) catch |err| switch (err) { | ||
| 287 | error.UnrecognizedGnuLibCFileName => continue, | ||
| 288 | error.InvalidGnuLibCVersion => continue, | ||
| 289 | error.GnuLibCVersionUnavailable => continue, | ||
| 290 | else => |e| return e, | ||
| 291 | }; | ||
| 292 | break; | ||
| 293 | } | ||
| 294 | } | ||
| 295 | } | ||
| 296 | |||
| 297 | return NativeTargetInfo{ | ||
| 298 | .target = .{ | ||
| 299 | .cpu = cpu, | ||
| 300 | .os = os_adjusted, | ||
| 301 | .abi = found_ld_info.abi, | ||
| 302 | }, | ||
| 303 | .dynamic_linker = try mem.dupeZ(allocator, u8, found_ld_path), | ||
| 304 | }; | ||
| 305 | } | ||
| 306 | |||
| 307 | // If Zig is statically linked, such as via distributed binary static builds, the above | ||
| 308 | // trick won't work. The next thing we fall back to is the same thing, but for /usr/bin/env. | ||
| 309 | // Since that path is hard-coded into the shebang line of many portable scripts, it's a | ||
| 310 | // reasonably reliable path to check for. | ||
| 311 | return abiAndDynamicLinkerFromUsrBinEnv(allocator, cpu, os) catch |err| switch (err) { | ||
| 312 | error.OutOfMemory => return error.OutOfMemory, | ||
| 313 | error.FileSystem => return error.FileSystem, | ||
| 314 | error.SystemResources => return error.SystemResources, | ||
| 315 | error.SymLinkLoop => return error.SymLinkLoop, | ||
| 316 | error.ProcessFdQuotaExceeded => return error.ProcessFdQuotaExceeded, | ||
| 317 | error.SystemFdQuotaExceeded => return error.SystemFdQuotaExceeded, | ||
| 318 | error.DeviceBusy => return error.DeviceBusy, | ||
| 319 | |||
| 320 | error.UnableToReadElfFile, | ||
| 321 | error.ElfNotADynamicExecutable, | ||
| 322 | error.InvalidElfProgramHeaders, | ||
| 323 | error.InvalidElfClass, | ||
| 324 | error.InvalidElfVersion, | ||
| 325 | error.InvalidElfEndian, | ||
| 326 | error.InvalidElfFile, | ||
| 327 | error.InvalidElfMagic, | ||
| 328 | error.UsrBinEnvNotAvailable, | ||
| 329 | error.Unexpected, | ||
| 330 | // Finally, we fall back on the standard path. | ||
| 331 | => defaultAbiAndDynamicLinker(allocator, cpu, os), | ||
| 332 | }; | ||
| 333 | } | ||
| 334 | |||
| 335 | const glibc_so_basename = "libc.so.6"; | ||
| 336 | |||
| 337 | fn glibcVerFromSO(so_path: [:0]const u8) !std.builtin.Version { | ||
| 338 | var link_buf: [std.os.PATH_MAX]u8 = undefined; | ||
| 339 | const link_name = std.os.readlinkC(so_path.ptr, &link_buf) catch |err| switch (err) { | ||
| 340 | error.AccessDenied => return error.GnuLibCVersionUnavailable, | ||
| 341 | error.FileSystem => return error.FileSystem, | ||
| 342 | error.SymLinkLoop => return error.SymLinkLoop, | ||
| 343 | error.NameTooLong => unreachable, | ||
| 344 | error.FileNotFound => return error.GnuLibCVersionUnavailable, | ||
| 345 | error.SystemResources => return error.SystemResources, | ||
| 346 | error.NotDir => return error.GnuLibCVersionUnavailable, | ||
| 347 | error.Unexpected => return error.GnuLibCVersionUnavailable, | ||
| 348 | }; | ||
| 349 | // example: "libc-2.3.4.so" | ||
| 350 | // example: "libc-2.27.so" | ||
| 351 | const prefix = "libc-"; | ||
| 352 | const suffix = ".so"; | ||
| 353 | if (!mem.startsWith(u8, link_name, prefix) or !mem.endsWith(u8, link_name, suffix)) { | ||
| 354 | return error.UnrecognizedGnuLibCFileName; | ||
| 355 | } | ||
| 356 | // chop off "libc-" and ".so" | ||
| 357 | const link_name_chopped = link_name[prefix.len .. link_name.len - suffix.len]; | ||
| 358 | return std.builtin.Version.parse(link_name_chopped) catch |err| switch (err) { | ||
| 359 | error.Overflow => return error.InvalidGnuLibCVersion, | ||
| 360 | error.InvalidCharacter => return error.InvalidGnuLibCVersion, | ||
| 361 | error.InvalidVersion => return error.InvalidGnuLibCVersion, | ||
| 362 | }; | ||
| 363 | } | ||
| 364 | |||
| 365 | fn abiAndDynamicLinkerFromUsrBinEnv( | ||
| 366 | allocator: *Allocator, | ||
| 367 | cpu: Target.Cpu, | ||
| 368 | os: Target.Os, | ||
| 369 | ) !NativeTargetInfo { | ||
| 370 | const env_file = std.fs.openFileAbsoluteC("/usr/bin/env", .{}) catch |err| switch (err) { | ||
| 371 | error.NoSpaceLeft => unreachable, | ||
| 372 | error.NameTooLong => unreachable, | ||
| 373 | error.PathAlreadyExists => unreachable, | ||
| 374 | error.SharingViolation => unreachable, | ||
| 375 | error.InvalidUtf8 => unreachable, | ||
| 376 | error.BadPathName => unreachable, | ||
| 377 | error.PipeBusy => unreachable, | ||
| 378 | |||
| 379 | error.IsDir => return error.UsrBinEnvNotAvailable, | ||
| 380 | error.NotDir => return error.UsrBinEnvNotAvailable, | ||
| 381 | error.AccessDenied => return error.UsrBinEnvNotAvailable, | ||
| 382 | error.NoDevice => return error.UsrBinEnvNotAvailable, | ||
| 383 | error.FileNotFound => return error.UsrBinEnvNotAvailable, | ||
| 384 | error.FileTooBig => return error.UsrBinEnvNotAvailable, | ||
| 385 | |||
| 386 | else => |e| return e, | ||
| 387 | }; | ||
| 388 | var hdr_buf: [@sizeOf(elf.Elf64_Ehdr)]u8 align(@alignOf(elf.Elf64_Ehdr)) = undefined; | ||
| 389 | const hdr_bytes_len = try wrapRead(env_file.pread(&hdr_buf, 0)); | ||
| 390 | if (hdr_bytes_len < @sizeOf(elf.Elf32_Ehdr)) return error.InvalidElfFile; | ||
| 391 | const hdr32 = @ptrCast(*elf.Elf32_Ehdr, &hdr_buf); | ||
| 392 | const hdr64 = @ptrCast(*elf.Elf64_Ehdr, &hdr_buf); | ||
| 393 | if (!mem.eql(u8, hdr32.e_ident[0..4], "\x7fELF")) return error.InvalidElfMagic; | ||
| 394 | const elf_endian: std.builtin.Endian = switch (hdr32.e_ident[elf.EI_DATA]) { | ||
| 395 | elf.ELFDATA2LSB => .Little, | ||
| 396 | elf.ELFDATA2MSB => .Big, | ||
| 397 | else => return error.InvalidElfEndian, | ||
| 398 | }; | ||
| 399 | const need_bswap = elf_endian != std.builtin.endian; | ||
| 400 | if (hdr32.e_ident[elf.EI_VERSION] != 1) return error.InvalidElfVersion; | ||
| 401 | |||
| 402 | const is_64 = switch (hdr32.e_ident[elf.EI_CLASS]) { | ||
| 403 | elf.ELFCLASS32 => false, | ||
| 404 | elf.ELFCLASS64 => true, | ||
| 405 | else => return error.InvalidElfClass, | ||
| 406 | }; | ||
| 407 | var phoff = elfInt(is_64, need_bswap, hdr32.e_phoff, hdr64.e_phoff); | ||
| 408 | const phentsize = elfInt(is_64, need_bswap, hdr32.e_phentsize, hdr64.e_phentsize); | ||
| 409 | const phnum = elfInt(is_64, need_bswap, hdr32.e_phnum, hdr64.e_phnum); | ||
| 410 | const shstrndx = elfInt(is_64, need_bswap, hdr32.e_shstrndx, hdr64.e_shstrndx); | ||
| 411 | |||
| 412 | const ph_total_size = std.math.mul(u32, phentsize, phnum) catch |err| switch (err) { | ||
| 413 | error.Overflow => return error.InvalidElfProgramHeaders, | ||
| 414 | }; | ||
| 415 | var ph_buf: [16 * @sizeOf(elf.Elf64_Phdr)]u8 align(@alignOf(elf.Elf64_Phdr)) = undefined; | ||
| 416 | var ph_i: u16 = 0; | ||
| 417 | while (ph_i < phnum) { | ||
| 418 | // Reserve some bytes so that we can deref the 64-bit struct fields even when the ELF file is 32-bits. | ||
| 419 | const reserve = @sizeOf(elf.Elf64_Phdr) - @sizeOf(elf.Elf32_Phdr); | ||
| 420 | const read_byte_len = try wrapRead(env_file.pread(ph_buf[0 .. ph_buf.len - reserve], phoff)); | ||
| 421 | if (read_byte_len < phentsize) return error.ElfNotADynamicExecutable; | ||
| 422 | var buf_i: usize = 0; | ||
| 423 | while (buf_i < read_byte_len and ph_i < phnum) : ({ | ||
| 424 | ph_i += 1; | ||
| 425 | phoff += phentsize; | ||
| 426 | buf_i += phentsize; | ||
| 427 | }) { | ||
| 428 | const ph32 = @ptrCast(*elf.Elf32_Phdr, @alignCast(@alignOf(elf.Elf32_Phdr), &ph_buf[buf_i])); | ||
| 429 | const ph64 = @ptrCast(*elf.Elf64_Phdr, @alignCast(@alignOf(elf.Elf64_Phdr), &ph_buf[buf_i])); | ||
| 430 | const p_type = elfInt(is_64, need_bswap, ph32.p_type, ph64.p_type); | ||
| 431 | switch (p_type) { | ||
| 432 | elf.PT_INTERP => { | ||
| 433 | std.debug.warn("found PT_INTERP\n", .{}); | ||
| 434 | }, | ||
| 435 | elf.PT_DYNAMIC => { | ||
| 436 | std.debug.warn("found PT_DYNAMIC\n", .{}); | ||
| 437 | }, | ||
| 438 | else => continue, | ||
| 439 | } | ||
| 440 | } | ||
| 441 | } | ||
| 442 | |||
| 443 | return error.OutOfMemory; // TODO | ||
| 444 | } | ||
| 445 | |||
| 446 | fn wrapRead(res: std.os.ReadError!usize) !usize { | ||
| 447 | return res catch |err| switch (err) { | ||
| 448 | error.OperationAborted => unreachable, // Windows-only | ||
| 449 | error.WouldBlock => unreachable, // Did not request blocking mode | ||
| 450 | error.SystemResources => return error.SystemResources, | ||
| 451 | error.IsDir => return error.UnableToReadElfFile, | ||
| 452 | error.BrokenPipe => return error.UnableToReadElfFile, | ||
| 453 | error.ConnectionResetByPeer => return error.UnableToReadElfFile, | ||
| 454 | error.Unexpected => return error.Unexpected, | ||
| 455 | error.InputOutput => return error.FileSystem, | ||
| 456 | }; | ||
| 457 | } | ||
| 458 | |||
| 459 | fn defaultAbiAndDynamicLinker(allocator: *Allocator, cpu: Target.Cpu, os: Target.Os) !NativeTargetInfo { | ||
| 460 | const target: Target = .{ | ||
| 461 | .cpu = cpu, | ||
| 462 | .os = os, | ||
| 463 | .abi = Target.Abi.default(cpu.arch, os), | ||
| 464 | }; | ||
| 465 | return @as(NativeTargetInfo, .{ | ||
| 466 | .target = target, | ||
| 467 | .dynamic_linker = target.getStandardDynamicLinkerPath(allocator) catch |err| switch (err) { | ||
| 468 | error.OutOfMemory => return error.OutOfMemory, | ||
| 469 | error.UnknownDynamicLinkerPath, error.TargetHasNoDynamicLinker => null, | ||
| 470 | }, | ||
| 471 | }); | ||
| 472 | } | ||
| 473 | }; | ||
| 474 | |||
| 475 | fn elfInt(is_64: bool, need_bswap: bool, int_32: var, int_64: var) @TypeOf(int_64) { | ||
| 476 | if (is_64) { | ||
| 477 | if (need_bswap) { | ||
| 478 | return @byteSwap(@TypeOf(int_64), int_64); | ||
| 479 | } else { | ||
| 480 | return int_64; | ||
| 481 | } | ||
| 482 | } else { | ||
| 483 | if (need_bswap) { | ||
| 484 | return @byteSwap(@TypeOf(int_32), int_32); | ||
| 485 | } else { | ||
| 486 | return int_32; | ||
| 487 | } | ||
| 488 | } | ||
| 489 | } |
src-self-hosted/c_int.zig+1-1| ... | @@ -70,7 +70,7 @@ pub const CInt = struct { | ... | @@ -70,7 +70,7 @@ pub const CInt = struct { |
| 70 | 70 | ||
| 71 | pub fn sizeInBits(cint: CInt, self: Target) u32 { | 71 | pub fn sizeInBits(cint: CInt, self: Target) u32 { |
| 72 | const arch = self.getArch(); | 72 | const arch = self.getArch(); |
| 73 | switch (self.getOs()) { | 73 | switch (self.os.tag) { |
| 74 | .freestanding, .other => switch (self.getArch()) { | 74 | .freestanding, .other => switch (self.getArch()) { |
| 75 | .msp430 => switch (cint.id) { | 75 | .msp430 => switch (cint.id) { |
| 76 | .Short, | 76 | .Short, |
src-self-hosted/clang.zig+1-1| ... | @@ -1050,7 +1050,7 @@ pub const struct_ZigClangExprEvalResult = extern struct { | ... | @@ -1050,7 +1050,7 @@ pub const struct_ZigClangExprEvalResult = extern struct { |
| 1050 | 1050 | ||
| 1051 | pub const struct_ZigClangAPValue = extern struct { | 1051 | pub const struct_ZigClangAPValue = extern struct { |
| 1052 | Kind: ZigClangAPValueKind, | 1052 | Kind: ZigClangAPValueKind, |
| 1053 | Data: if (builtin.os == .windows and builtin.abi == .msvc) [52]u8 else [68]u8, | 1053 | Data: if (builtin.os.tag == .windows and builtin.abi == .msvc) [52]u8 else [68]u8, |
| 1054 | }; | 1054 | }; |
| 1055 | pub extern fn ZigClangVarDecl_getTypeSourceInfo_getType(self: *const struct_ZigClangVarDecl) struct_ZigClangQualType; | 1055 | pub extern fn ZigClangVarDecl_getTypeSourceInfo_getType(self: *const struct_ZigClangVarDecl) struct_ZigClangQualType; |
| 1056 | 1056 |
src-self-hosted/introspect.zig+1-9| ... | @@ -1,4 +1,4 @@ | ... | @@ -1,4 +1,4 @@ |
| 1 | // Introspection and determination of system libraries needed by zig. | 1 | //! Introspection and determination of system libraries needed by zig. |
| 2 | 2 | ||
| 3 | const std = @import("std"); | 3 | const std = @import("std"); |
| 4 | const mem = std.mem; | 4 | const mem = std.mem; |
| ... | @@ -6,14 +6,6 @@ const fs = std.fs; | ... | @@ -6,14 +6,6 @@ const fs = std.fs; |
| 6 | 6 | ||
| 7 | const warn = std.debug.warn; | 7 | const warn = std.debug.warn; |
| 8 | 8 | ||
| 9 | pub fn detectDynamicLinker(allocator: *mem.Allocator, target: std.Target) ![:0]u8 { | ||
| 10 | if (target == .Native) { | ||
| 11 | return @import("libc_installation.zig").detectNativeDynamicLinker(allocator); | ||
| 12 | } else { | ||
| 13 | return target.getStandardDynamicLinkerPath(allocator); | ||
| 14 | } | ||
| 15 | } | ||
| 16 | |||
| 17 | /// Caller must free result | 9 | /// Caller must free result |
| 18 | pub fn testZigInstallPrefix(allocator: *mem.Allocator, test_path: []const u8) ![]u8 { | 10 | pub fn testZigInstallPrefix(allocator: *mem.Allocator, test_path: []const u8) ![]u8 { |
| 19 | const test_zig_dir = try fs.path.join(allocator, &[_][]const u8{ test_path, "lib", "zig" }); | 11 | const test_zig_dir = try fs.path.join(allocator, &[_][]const u8{ test_path, "lib", "zig" }); |
src-self-hosted/libc_installation.zig+7-105| ... | @@ -99,27 +99,27 @@ pub const LibCInstallation = struct { | ... | @@ -99,27 +99,27 @@ pub const LibCInstallation = struct { |
| 99 | return error.ParseError; | 99 | return error.ParseError; |
| 100 | } | 100 | } |
| 101 | if (self.crt_dir == null and !is_darwin) { | 101 | if (self.crt_dir == null and !is_darwin) { |
| 102 | try stderr.print("crt_dir may not be empty for {}\n", .{@tagName(Target.current.getOs())}); | 102 | try stderr.print("crt_dir may not be empty for {}\n", .{@tagName(Target.current.os.tag)}); |
| 103 | return error.ParseError; | 103 | return error.ParseError; |
| 104 | } | 104 | } |
| 105 | if (self.static_crt_dir == null and is_windows and is_gnu) { | 105 | if (self.static_crt_dir == null and is_windows and is_gnu) { |
| 106 | try stderr.print("static_crt_dir may not be empty for {}-{}\n", .{ | 106 | try stderr.print("static_crt_dir may not be empty for {}-{}\n", .{ |
| 107 | @tagName(Target.current.getOs()), | 107 | @tagName(Target.current.os.tag), |
| 108 | @tagName(Target.current.getAbi()), | 108 | @tagName(Target.current.abi), |
| 109 | }); | 109 | }); |
| 110 | return error.ParseError; | 110 | return error.ParseError; |
| 111 | } | 111 | } |
| 112 | if (self.msvc_lib_dir == null and is_windows and !is_gnu) { | 112 | if (self.msvc_lib_dir == null and is_windows and !is_gnu) { |
| 113 | try stderr.print("msvc_lib_dir may not be empty for {}-{}\n", .{ | 113 | try stderr.print("msvc_lib_dir may not be empty for {}-{}\n", .{ |
| 114 | @tagName(Target.current.getOs()), | 114 | @tagName(Target.current.os.tag), |
| 115 | @tagName(Target.current.getAbi()), | 115 | @tagName(Target.current.abi), |
| 116 | }); | 116 | }); |
| 117 | return error.ParseError; | 117 | return error.ParseError; |
| 118 | } | 118 | } |
| 119 | if (self.kernel32_lib_dir == null and is_windows and !is_gnu) { | 119 | if (self.kernel32_lib_dir == null and is_windows and !is_gnu) { |
| 120 | try stderr.print("kernel32_lib_dir may not be empty for {}-{}\n", .{ | 120 | try stderr.print("kernel32_lib_dir may not be empty for {}-{}\n", .{ |
| 121 | @tagName(Target.current.getOs()), | 121 | @tagName(Target.current.os.tag), |
| 122 | @tagName(Target.current.getAbi()), | 122 | @tagName(Target.current.abi), |
| 123 | }); | 123 | }); |
| 124 | return error.ParseError; | 124 | return error.ParseError; |
| 125 | } | 125 | } |
| ... | @@ -616,104 +616,6 @@ fn printVerboseInvocation( | ... | @@ -616,104 +616,6 @@ fn printVerboseInvocation( |
| 616 | } | 616 | } |
| 617 | } | 617 | } |
| 618 | 618 | ||
| 619 | /// Caller owns returned memory. | ||
| 620 | pub fn detectNativeDynamicLinker(allocator: *Allocator) error{ | ||
| 621 | OutOfMemory, | ||
| 622 | TargetHasNoDynamicLinker, | ||
| 623 | UnknownDynamicLinkerPath, | ||
| 624 | }![:0]u8 { | ||
| 625 | if (!comptime Target.current.hasDynamicLinker()) { | ||
| 626 | return error.TargetHasNoDynamicLinker; | ||
| 627 | } | ||
| 628 | |||
| 629 | // The current target's ABI cannot be relied on for this. For example, we may build the zig | ||
| 630 | // compiler for target riscv64-linux-musl and provide a tarball for users to download. | ||
| 631 | // A user could then run that zig compiler on riscv64-linux-gnu. This use case is well-defined | ||
| 632 | // and supported by Zig. But that means that we must detect the system ABI here rather than | ||
| 633 | // relying on `std.Target.current`. | ||
| 634 | |||
| 635 | const LdInfo = struct { | ||
| 636 | ld_path: []u8, | ||
| 637 | abi: Target.Abi, | ||
| 638 | }; | ||
| 639 | var ld_info_list = std.ArrayList(LdInfo).init(allocator); | ||
| 640 | defer { | ||
| 641 | for (ld_info_list.toSlice()) |ld_info| allocator.free(ld_info.ld_path); | ||
| 642 | ld_info_list.deinit(); | ||
| 643 | } | ||
| 644 | |||
| 645 | const all_abis = comptime blk: { | ||
| 646 | const fields = std.meta.fields(Target.Abi); | ||
| 647 | var array: [fields.len]Target.Abi = undefined; | ||
| 648 | inline for (fields) |field, i| { | ||
| 649 | array[i] = @field(Target.Abi, field.name); | ||
| 650 | } | ||
| 651 | break :blk array; | ||
| 652 | }; | ||
| 653 | for (all_abis) |abi| { | ||
| 654 | // This may be a nonsensical parameter. We detect this with error.UnknownDynamicLinkerPath and | ||
| 655 | // skip adding it to `ld_info_list`. | ||
| 656 | const target: Target = .{ | ||
| 657 | .Cross = .{ | ||
| 658 | .cpu = Target.Cpu.baseline(Target.current.getArch()), | ||
| 659 | .os = Target.current.getOs(), | ||
| 660 | .abi = abi, | ||
| 661 | }, | ||
| 662 | }; | ||
| 663 | const standard_ld_path = target.getStandardDynamicLinkerPath(allocator) catch |err| switch (err) { | ||
| 664 | error.OutOfMemory => return error.OutOfMemory, | ||
| 665 | error.UnknownDynamicLinkerPath, error.TargetHasNoDynamicLinker => continue, | ||
| 666 | }; | ||
| 667 | errdefer allocator.free(standard_ld_path); | ||
| 668 | try ld_info_list.append(.{ | ||
| 669 | .ld_path = standard_ld_path, | ||
| 670 | .abi = abi, | ||
| 671 | }); | ||
| 672 | } | ||
| 673 | |||
| 674 | // Best case scenario: the zig compiler is dynamically linked, and we can iterate | ||
| 675 | // over our own shared objects and find a dynamic linker. | ||
| 676 | { | ||
| 677 | const lib_paths = try std.process.getSelfExeSharedLibPaths(allocator); | ||
| 678 | defer allocator.free(lib_paths); | ||
| 679 | |||
| 680 | // This is O(N^M) but typical case here is N=2 and M=10. | ||
| 681 | for (lib_paths) |lib_path| { | ||
| 682 | for (ld_info_list.toSlice()) |ld_info| { | ||
| 683 | const standard_ld_basename = fs.path.basename(ld_info.ld_path); | ||
| 684 | if (std.mem.endsWith(u8, lib_path, standard_ld_basename)) { | ||
| 685 | return std.mem.dupeZ(allocator, u8, lib_path); | ||
| 686 | } | ||
| 687 | } | ||
| 688 | } | ||
| 689 | } | ||
| 690 | |||
| 691 | // If Zig is statically linked, such as via distributed binary static builds, the above | ||
| 692 | // trick won't work. What are we left with? Try to run the system C compiler and get | ||
| 693 | // it to tell us the dynamic linker path. | ||
| 694 | // TODO: instead of this, look at the shared libs of /usr/bin/env. | ||
| 695 | for (ld_info_list.toSlice()) |ld_info| { | ||
| 696 | const standard_ld_basename = fs.path.basename(ld_info.ld_path); | ||
| 697 | |||
| 698 | const full_ld_path = ccPrintFileName(.{ | ||
| 699 | .allocator = allocator, | ||
| 700 | .search_basename = standard_ld_basename, | ||
| 701 | .want_dirname = .full_path, | ||
| 702 | }) catch |err| switch (err) { | ||
| 703 | error.OutOfMemory => return error.OutOfMemory, | ||
| 704 | error.LibCRuntimeNotFound, | ||
| 705 | error.CCompilerExitCode, | ||
| 706 | error.CCompilerCrashed, | ||
| 707 | error.UnableToSpawnCCompiler, | ||
| 708 | => continue, | ||
| 709 | }; | ||
| 710 | return full_ld_path; | ||
| 711 | } | ||
| 712 | |||
| 713 | // Finally, we fall back on the standard path. | ||
| 714 | return Target.current.getStandardDynamicLinkerPath(allocator); | ||
| 715 | } | ||
| 716 | |||
| 717 | const Search = struct { | 619 | const Search = struct { |
| 718 | path: []const u8, | 620 | path: []const u8, |
| 719 | version: []const u8, | 621 | version: []const u8, |
src-self-hosted/link.zig+2-2| ... | @@ -515,7 +515,7 @@ const DarwinPlatform = struct { | ... | @@ -515,7 +515,7 @@ const DarwinPlatform = struct { |
| 515 | break :blk ver; | 515 | break :blk ver; |
| 516 | }, | 516 | }, |
| 517 | .None => blk: { | 517 | .None => blk: { |
| 518 | assert(comp.target.getOs() == .macosx); | 518 | assert(comp.target.os.tag == .macosx); |
| 519 | result.kind = .MacOS; | 519 | result.kind = .MacOS; |
| 520 | break :blk "10.14"; | 520 | break :blk "10.14"; |
| 521 | }, | 521 | }, |
| ... | @@ -534,7 +534,7 @@ const DarwinPlatform = struct { | ... | @@ -534,7 +534,7 @@ const DarwinPlatform = struct { |
| 534 | } | 534 | } |
| 535 | 535 | ||
| 536 | if (result.kind == .IPhoneOS) { | 536 | if (result.kind == .IPhoneOS) { |
| 537 | switch (comp.target.getArch()) { | 537 | switch (comp.target.cpu.arch) { |
| 538 | .i386, | 538 | .i386, |
| 539 | .x86_64, | 539 | .x86_64, |
| 540 | => result.kind = .IPhoneOSSimulator, | 540 | => result.kind = .IPhoneOSSimulator, |
src-self-hosted/main.zig+3-3| ... | @@ -79,9 +79,9 @@ pub fn main() !void { | ... | @@ -79,9 +79,9 @@ pub fn main() !void { |
| 79 | } else if (mem.eql(u8, cmd, "libc")) { | 79 | } else if (mem.eql(u8, cmd, "libc")) { |
| 80 | return cmdLibC(allocator, cmd_args); | 80 | return cmdLibC(allocator, cmd_args); |
| 81 | } else if (mem.eql(u8, cmd, "targets")) { | 81 | } else if (mem.eql(u8, cmd, "targets")) { |
| 82 | // TODO figure out the current target rather than using the target that was specified when | 82 | const info = try std.zig.system.NativeTargetInfo.detect(allocator); |
| 83 | // compiling the compiler | 83 | defer info.deinit(allocator); |
| 84 | return @import("print_targets.zig").cmdTargets(allocator, cmd_args, stdout, Target.current); | 84 | return @import("print_targets.zig").cmdTargets(allocator, cmd_args, stdout, info.target); |
| 85 | } else if (mem.eql(u8, cmd, "version")) { | 85 | } else if (mem.eql(u8, cmd, "version")) { |
| 86 | return cmdVersion(allocator, cmd_args); | 86 | return cmdVersion(allocator, cmd_args); |
| 87 | } else if (mem.eql(u8, cmd, "zen")) { | 87 | } else if (mem.eql(u8, cmd, "zen")) { |
src-self-hosted/print_targets.zig+6-6| ... | @@ -124,7 +124,7 @@ pub fn cmdTargets( | ... | @@ -124,7 +124,7 @@ pub fn cmdTargets( |
| 124 | 124 | ||
| 125 | try jws.objectField("os"); | 125 | try jws.objectField("os"); |
| 126 | try jws.beginArray(); | 126 | try jws.beginArray(); |
| 127 | inline for (@typeInfo(Target.Os).Enum.fields) |field| { | 127 | inline for (@typeInfo(Target.Os.Tag).Enum.fields) |field| { |
| 128 | try jws.arrayElem(); | 128 | try jws.arrayElem(); |
| 129 | try jws.emitString(field.name); | 129 | try jws.emitString(field.name); |
| 130 | } | 130 | } |
| ... | @@ -201,16 +201,16 @@ pub fn cmdTargets( | ... | @@ -201,16 +201,16 @@ pub fn cmdTargets( |
| 201 | try jws.objectField("cpu"); | 201 | try jws.objectField("cpu"); |
| 202 | try jws.beginObject(); | 202 | try jws.beginObject(); |
| 203 | try jws.objectField("arch"); | 203 | try jws.objectField("arch"); |
| 204 | try jws.emitString(@tagName(native_target.getArch())); | 204 | try jws.emitString(@tagName(native_target.cpu.arch)); |
| 205 | 205 | ||
| 206 | try jws.objectField("name"); | 206 | try jws.objectField("name"); |
| 207 | const cpu = native_target.getCpu(); | 207 | const cpu = native_target.cpu; |
| 208 | try jws.emitString(cpu.model.name); | 208 | try jws.emitString(cpu.model.name); |
| 209 | 209 | ||
| 210 | { | 210 | { |
| 211 | try jws.objectField("features"); | 211 | try jws.objectField("features"); |
| 212 | try jws.beginArray(); | 212 | try jws.beginArray(); |
| 213 | for (native_target.getArch().allFeaturesList()) |feature, i_usize| { | 213 | for (native_target.cpu.arch.allFeaturesList()) |feature, i_usize| { |
| 214 | const index = @intCast(Target.Cpu.Feature.Set.Index, i_usize); | 214 | const index = @intCast(Target.Cpu.Feature.Set.Index, i_usize); |
| 215 | if (cpu.features.isEnabled(index)) { | 215 | if (cpu.features.isEnabled(index)) { |
| 216 | try jws.arrayElem(); | 216 | try jws.arrayElem(); |
| ... | @@ -222,9 +222,9 @@ pub fn cmdTargets( | ... | @@ -222,9 +222,9 @@ pub fn cmdTargets( |
| 222 | try jws.endObject(); | 222 | try jws.endObject(); |
| 223 | } | 223 | } |
| 224 | try jws.objectField("os"); | 224 | try jws.objectField("os"); |
| 225 | try jws.emitString(@tagName(native_target.getOs())); | 225 | try jws.emitString(@tagName(native_target.os.tag)); |
| 226 | try jws.objectField("abi"); | 226 | try jws.objectField("abi"); |
| 227 | try jws.emitString(@tagName(native_target.getAbi())); | 227 | try jws.emitString(@tagName(native_target.abi)); |
| 228 | // TODO implement native glibc version detection in self-hosted | 228 | // TODO implement native glibc version detection in self-hosted |
| 229 | try jws.endObject(); | 229 | try jws.endObject(); |
| 230 | 230 |
src-self-hosted/stage2.zig+271-133| ... | @@ -110,6 +110,8 @@ const Error = extern enum { | ... | @@ -110,6 +110,8 @@ const Error = extern enum { |
| 110 | WindowsSdkNotFound, | 110 | WindowsSdkNotFound, |
| 111 | UnknownDynamicLinkerPath, | 111 | UnknownDynamicLinkerPath, |
| 112 | TargetHasNoDynamicLinker, | 112 | TargetHasNoDynamicLinker, |
| 113 | InvalidAbiVersion, | ||
| 114 | InvalidOperatingSystemVersion, | ||
| 113 | }; | 115 | }; |
| 114 | 116 | ||
| 115 | const FILE = std.c.FILE; | 117 | const FILE = std.c.FILE; |
| ... | @@ -633,11 +635,11 @@ export fn stage2_cmd_targets(zig_triple: [*:0]const u8) c_int { | ... | @@ -633,11 +635,11 @@ export fn stage2_cmd_targets(zig_triple: [*:0]const u8) c_int { |
| 633 | 635 | ||
| 634 | fn cmdTargets(zig_triple: [*:0]const u8) !void { | 636 | fn cmdTargets(zig_triple: [*:0]const u8) !void { |
| 635 | var target = try Target.parse(.{ .arch_os_abi = mem.toSliceConst(u8, zig_triple) }); | 637 | var target = try Target.parse(.{ .arch_os_abi = mem.toSliceConst(u8, zig_triple) }); |
| 636 | target.Cross.cpu = blk: { | 638 | target.cpu = blk: { |
| 637 | const llvm = @import("llvm.zig"); | 639 | const llvm = @import("llvm.zig"); |
| 638 | const llvm_cpu_name = llvm.GetHostCPUName(); | 640 | const llvm_cpu_name = llvm.GetHostCPUName(); |
| 639 | const llvm_cpu_features = llvm.GetNativeFeatures(); | 641 | const llvm_cpu_features = llvm.GetNativeFeatures(); |
| 640 | break :blk try detectNativeCpuWithLLVM(target.getArch(), llvm_cpu_name, llvm_cpu_features); | 642 | break :blk try detectNativeCpuWithLLVM(target.cpu.arch, llvm_cpu_name, llvm_cpu_features); |
| 641 | }; | 643 | }; |
| 642 | return @import("print_targets.zig").cmdTargets( | 644 | return @import("print_targets.zig").cmdTargets( |
| 643 | std.heap.c_allocator, | 645 | std.heap.c_allocator, |
| ... | @@ -662,6 +664,14 @@ export fn stage2_target_parse( | ... | @@ -662,6 +664,14 @@ export fn stage2_target_parse( |
| 662 | error.MissingArchitecture => return .MissingArchitecture, | 664 | error.MissingArchitecture => return .MissingArchitecture, |
| 663 | error.InvalidLlvmCpuFeaturesFormat => return .InvalidLlvmCpuFeaturesFormat, | 665 | error.InvalidLlvmCpuFeaturesFormat => return .InvalidLlvmCpuFeaturesFormat, |
| 664 | error.UnexpectedExtraField => return .SemanticAnalyzeFail, | 666 | error.UnexpectedExtraField => return .SemanticAnalyzeFail, |
| 667 | error.InvalidAbiVersion => return .InvalidAbiVersion, | ||
| 668 | error.InvalidOperatingSystemVersion => return .InvalidOperatingSystemVersion, | ||
| 669 | error.FileSystem => return .FileSystem, | ||
| 670 | error.SymLinkLoop => return .SymLinkLoop, | ||
| 671 | error.SystemResources => return .SystemResources, | ||
| 672 | error.ProcessFdQuotaExceeded => return .ProcessFdQuotaExceeded, | ||
| 673 | error.SystemFdQuotaExceeded => return .SystemFdQuotaExceeded, | ||
| 674 | error.DeviceBusy => return .DeviceBusy, | ||
| 665 | }; | 675 | }; |
| 666 | return .None; | 676 | return .None; |
| 667 | } | 677 | } |
| ... | @@ -671,108 +681,48 @@ fn stage2TargetParse( | ... | @@ -671,108 +681,48 @@ fn stage2TargetParse( |
| 671 | zig_triple_oz: ?[*:0]const u8, | 681 | zig_triple_oz: ?[*:0]const u8, |
| 672 | mcpu_oz: ?[*:0]const u8, | 682 | mcpu_oz: ?[*:0]const u8, |
| 673 | ) !void { | 683 | ) !void { |
| 674 | const target: Target = if (zig_triple_oz) |zig_triple_z| blk: { | 684 | const target: std.build.Target = if (zig_triple_oz) |zig_triple_z| blk: { |
| 675 | const zig_triple = mem.toSliceConst(u8, zig_triple_z); | 685 | const zig_triple = mem.toSliceConst(u8, zig_triple_z); |
| 676 | const mcpu = if (mcpu_oz) |mcpu_z| mem.toSliceConst(u8, mcpu_z) else "baseline"; | 686 | const mcpu = if (mcpu_oz) |mcpu_z| mem.toSliceConst(u8, mcpu_z) else "baseline"; |
| 677 | var diags: std.Target.ParseOptions.Diagnostics = .{}; | 687 | var diags: std.Target.ParseOptions.Diagnostics = .{}; |
| 678 | break :blk Target.parse(.{ | 688 | break :blk std.build.Target{ |
| 679 | .arch_os_abi = zig_triple, | 689 | .Cross = Target.parse(.{ |
| 680 | .cpu_features = mcpu, | 690 | .arch_os_abi = zig_triple, |
| 681 | .diagnostics = &diags, | 691 | .cpu_features = mcpu, |
| 682 | }) catch |err| switch (err) { | 692 | .diagnostics = &diags, |
| 683 | error.UnknownCpu => { | 693 | }) catch |err| switch (err) { |
| 684 | std.debug.warn("Unknown CPU: '{}'\nAvailable CPUs for architecture '{}':\n", .{ | 694 | error.UnknownCpu => { |
| 685 | diags.cpu_name.?, | 695 | std.debug.warn("Unknown CPU: '{}'\nAvailable CPUs for architecture '{}':\n", .{ |
| 686 | @tagName(diags.arch.?), | 696 | diags.cpu_name.?, |
| 687 | }); | 697 | @tagName(diags.arch.?), |
| 688 | for (diags.arch.?.allCpuModels()) |cpu| { | 698 | }); |
| 689 | std.debug.warn(" {}\n", .{cpu.name}); | 699 | for (diags.arch.?.allCpuModels()) |cpu| { |
| 690 | } | 700 | std.debug.warn(" {}\n", .{cpu.name}); |
| 691 | process.exit(1); | 701 | } |
| 692 | }, | 702 | process.exit(1); |
| 693 | error.UnknownCpuFeature => { | 703 | }, |
| 694 | std.debug.warn( | 704 | error.UnknownCpuFeature => { |
| 695 | \\Unknown CPU feature: '{}' | 705 | std.debug.warn( |
| 696 | \\Available CPU features for architecture '{}': | 706 | \\Unknown CPU feature: '{}' |
| 697 | \\ | 707 | \\Available CPU features for architecture '{}': |
| 698 | , .{ | 708 | \\ |
| 699 | diags.unknown_feature_name, | 709 | , .{ |
| 700 | @tagName(diags.arch.?), | 710 | diags.unknown_feature_name, |
| 701 | }); | 711 | @tagName(diags.arch.?), |
| 702 | for (diags.arch.?.allFeaturesList()) |feature| { | 712 | }); |
| 703 | std.debug.warn(" {}: {}\n", .{ feature.name, feature.description }); | 713 | for (diags.arch.?.allFeaturesList()) |feature| { |
| 704 | } | 714 | std.debug.warn(" {}: {}\n", .{ feature.name, feature.description }); |
| 705 | process.exit(1); | 715 | } |
| 716 | process.exit(1); | ||
| 717 | }, | ||
| 718 | else => |e| return e, | ||
| 706 | }, | 719 | }, |
| 707 | else => |e| return e, | ||
| 708 | }; | 720 | }; |
| 709 | } else Target.Native; | 721 | } else std.build.Target.Native; |
| 710 | 722 | ||
| 711 | try stage1_target.fromTarget(target); | 723 | try stage1_target.fromTarget(target); |
| 712 | } | 724 | } |
| 713 | 725 | ||
| 714 | fn initStage1TargetCpuFeatures(stage1_target: *Stage2Target, cpu: Target.Cpu) !void { | ||
| 715 | const allocator = std.heap.c_allocator; | ||
| 716 | const cache_hash = try std.fmt.allocPrint0(allocator, "{}\n{}", .{ | ||
| 717 | cpu.model.name, | ||
| 718 | cpu.features.asBytes(), | ||
| 719 | }); | ||
| 720 | errdefer allocator.free(cache_hash); | ||
| 721 | |||
| 722 | const generic_arch_name = cpu.arch.genericName(); | ||
| 723 | var builtin_str_buffer = try std.Buffer.allocPrint(allocator, | ||
| 724 | \\Cpu{{ | ||
| 725 | \\ .arch = .{}, | ||
| 726 | \\ .model = &Target.{}.cpu.{}, | ||
| 727 | \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{ | ||
| 728 | \\ | ||
| 729 | , .{ | ||
| 730 | @tagName(cpu.arch), | ||
| 731 | generic_arch_name, | ||
| 732 | cpu.model.name, | ||
| 733 | generic_arch_name, | ||
| 734 | generic_arch_name, | ||
| 735 | }); | ||
| 736 | defer builtin_str_buffer.deinit(); | ||
| 737 | |||
| 738 | var llvm_features_buffer = try std.Buffer.initSize(allocator, 0); | ||
| 739 | defer llvm_features_buffer.deinit(); | ||
| 740 | |||
| 741 | for (cpu.arch.allFeaturesList()) |feature, index_usize| { | ||
| 742 | const index = @intCast(Target.Cpu.Feature.Set.Index, index_usize); | ||
| 743 | const is_enabled = cpu.features.isEnabled(index); | ||
| 744 | |||
| 745 | if (feature.llvm_name) |llvm_name| { | ||
| 746 | const plus_or_minus = "-+"[@boolToInt(is_enabled)]; | ||
| 747 | try llvm_features_buffer.appendByte(plus_or_minus); | ||
| 748 | try llvm_features_buffer.append(llvm_name); | ||
| 749 | try llvm_features_buffer.append(","); | ||
| 750 | } | ||
| 751 | |||
| 752 | if (is_enabled) { | ||
| 753 | // TODO some kind of "zig identifier escape" function rather than | ||
| 754 | // unconditionally using @"" syntax | ||
| 755 | try builtin_str_buffer.append(" .@\""); | ||
| 756 | try builtin_str_buffer.append(feature.name); | ||
| 757 | try builtin_str_buffer.append("\",\n"); | ||
| 758 | } | ||
| 759 | } | ||
| 760 | |||
| 761 | try builtin_str_buffer.append( | ||
| 762 | \\ }), | ||
| 763 | \\}; | ||
| 764 | \\ | ||
| 765 | ); | ||
| 766 | |||
| 767 | assert(mem.endsWith(u8, llvm_features_buffer.toSliceConst(), ",")); | ||
| 768 | llvm_features_buffer.shrink(llvm_features_buffer.len() - 1); | ||
| 769 | |||
| 770 | stage1_target.llvm_cpu_name = if (cpu.model.llvm_name) |s| s.ptr else null; | ||
| 771 | stage1_target.llvm_cpu_features = llvm_features_buffer.toOwnedSlice().ptr; | ||
| 772 | stage1_target.builtin_str = builtin_str_buffer.toOwnedSlice().ptr; | ||
| 773 | stage1_target.cache_hash = cache_hash.ptr; | ||
| 774 | } | ||
| 775 | |||
| 776 | // ABI warning | 726 | // ABI warning |
| 777 | const Stage2LibCInstallation = extern struct { | 727 | const Stage2LibCInstallation = extern struct { |
| 778 | include_dir: [*:0]const u8, | 728 | include_dir: [*:0]const u8, |
| ... | @@ -952,10 +902,13 @@ const Stage2Target = extern struct { | ... | @@ -952,10 +902,13 @@ const Stage2Target = extern struct { |
| 952 | 902 | ||
| 953 | llvm_cpu_name: ?[*:0]const u8, | 903 | llvm_cpu_name: ?[*:0]const u8, |
| 954 | llvm_cpu_features: ?[*:0]const u8, | 904 | llvm_cpu_features: ?[*:0]const u8, |
| 955 | builtin_str: ?[*:0]const u8, | 905 | cpu_builtin_str: ?[*:0]const u8, |
| 956 | cache_hash: ?[*:0]const u8, | 906 | cache_hash: ?[*:0]const u8, |
| 907 | os_builtin_str: ?[*:0]const u8, | ||
| 908 | |||
| 909 | dynamic_linker: ?[*:0]const u8, | ||
| 957 | 910 | ||
| 958 | fn toTarget(in_target: Stage2Target) Target { | 911 | fn toTarget(in_target: Stage2Target) std.build.Target { |
| 959 | if (in_target.is_native) return .Native; | 912 | if (in_target.is_native) return .Native; |
| 960 | 913 | ||
| 961 | const in_arch = in_target.arch - 1; // skip over ZigLLVM_UnknownArch | 914 | const in_arch = in_target.arch - 1; // skip over ZigLLVM_UnknownArch |
| ... | @@ -965,39 +918,244 @@ const Stage2Target = extern struct { | ... | @@ -965,39 +918,244 @@ const Stage2Target = extern struct { |
| 965 | return .{ | 918 | return .{ |
| 966 | .Cross = .{ | 919 | .Cross = .{ |
| 967 | .cpu = Target.Cpu.baseline(enumInt(Target.Cpu.Arch, in_arch)), | 920 | .cpu = Target.Cpu.baseline(enumInt(Target.Cpu.Arch, in_arch)), |
| 968 | .os = enumInt(Target.Os, in_os), | 921 | .os = Target.Os.defaultVersionRange(enumInt(Target.Os.Tag, in_os)), |
| 969 | .abi = enumInt(Target.Abi, in_abi), | 922 | .abi = enumInt(Target.Abi, in_abi), |
| 970 | }, | 923 | }, |
| 971 | }; | 924 | }; |
| 972 | } | 925 | } |
| 973 | 926 | ||
| 974 | fn fromTarget(self: *Stage2Target, target: Target) !void { | 927 | fn fromTarget(self: *Stage2Target, build_target: std.build.Target) !void { |
| 975 | const cpu = switch (target) { | 928 | const allocator = std.heap.c_allocator; |
| 929 | var dynamic_linker: ?[*:0]u8 = null; | ||
| 930 | const target = switch (build_target) { | ||
| 976 | .Native => blk: { | 931 | .Native => blk: { |
| 977 | // TODO self-host CPU model and feature detection instead of relying on LLVM | 932 | const info = try std.zig.system.NativeTargetInfo.detect(std.heap.c_allocator); |
| 933 | if (info.dynamic_linker) |dl| { | ||
| 934 | dynamic_linker = dl.ptr; | ||
| 935 | } | ||
| 936 | |||
| 937 | // TODO we want to just use info.target but implementing CPU model & feature detection is todo | ||
| 938 | // so here we rely on LLVM | ||
| 978 | const llvm = @import("llvm.zig"); | 939 | const llvm = @import("llvm.zig"); |
| 979 | const llvm_cpu_name = llvm.GetHostCPUName(); | 940 | const llvm_cpu_name = llvm.GetHostCPUName(); |
| 980 | const llvm_cpu_features = llvm.GetNativeFeatures(); | 941 | const llvm_cpu_features = llvm.GetNativeFeatures(); |
| 981 | break :blk try detectNativeCpuWithLLVM(target.getArch(), llvm_cpu_name, llvm_cpu_features); | 942 | const arch = std.Target.current.cpu.arch; |
| 943 | var t = info.target; | ||
| 944 | t.cpu = try detectNativeCpuWithLLVM(arch, llvm_cpu_name, llvm_cpu_features); | ||
| 945 | break :blk t; | ||
| 982 | }, | 946 | }, |
| 983 | .Cross => target.getCpu(), | 947 | .Cross => |t| t, |
| 984 | }; | 948 | }; |
| 949 | |||
| 950 | var cache_hash = try std.Buffer.allocPrint(allocator, "{}\n{}\n", .{ | ||
| 951 | target.cpu.model.name, | ||
| 952 | target.cpu.features.asBytes(), | ||
| 953 | }); | ||
| 954 | defer cache_hash.deinit(); | ||
| 955 | |||
| 956 | const generic_arch_name = target.cpu.arch.genericName(); | ||
| 957 | var cpu_builtin_str_buffer = try std.Buffer.allocPrint(allocator, | ||
| 958 | \\Cpu{{ | ||
| 959 | \\ .arch = .{}, | ||
| 960 | \\ .model = &Target.{}.cpu.{}, | ||
| 961 | \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{ | ||
| 962 | \\ | ||
| 963 | , .{ | ||
| 964 | @tagName(target.cpu.arch), | ||
| 965 | generic_arch_name, | ||
| 966 | target.cpu.model.name, | ||
| 967 | generic_arch_name, | ||
| 968 | generic_arch_name, | ||
| 969 | }); | ||
| 970 | defer cpu_builtin_str_buffer.deinit(); | ||
| 971 | |||
| 972 | var llvm_features_buffer = try std.Buffer.initSize(allocator, 0); | ||
| 973 | defer llvm_features_buffer.deinit(); | ||
| 974 | |||
| 975 | for (target.cpu.arch.allFeaturesList()) |feature, index_usize| { | ||
| 976 | const index = @intCast(Target.Cpu.Feature.Set.Index, index_usize); | ||
| 977 | const is_enabled = target.cpu.features.isEnabled(index); | ||
| 978 | |||
| 979 | if (feature.llvm_name) |llvm_name| { | ||
| 980 | const plus_or_minus = "-+"[@boolToInt(is_enabled)]; | ||
| 981 | try llvm_features_buffer.appendByte(plus_or_minus); | ||
| 982 | try llvm_features_buffer.append(llvm_name); | ||
| 983 | try llvm_features_buffer.append(","); | ||
| 984 | } | ||
| 985 | |||
| 986 | if (is_enabled) { | ||
| 987 | // TODO some kind of "zig identifier escape" function rather than | ||
| 988 | // unconditionally using @"" syntax | ||
| 989 | try cpu_builtin_str_buffer.append(" .@\""); | ||
| 990 | try cpu_builtin_str_buffer.append(feature.name); | ||
| 991 | try cpu_builtin_str_buffer.append("\",\n"); | ||
| 992 | } | ||
| 993 | } | ||
| 994 | |||
| 995 | try cpu_builtin_str_buffer.append( | ||
| 996 | \\ }), | ||
| 997 | \\}; | ||
| 998 | \\ | ||
| 999 | ); | ||
| 1000 | |||
| 1001 | assert(mem.endsWith(u8, llvm_features_buffer.toSliceConst(), ",")); | ||
| 1002 | llvm_features_buffer.shrink(llvm_features_buffer.len() - 1); | ||
| 1003 | |||
| 1004 | var os_builtin_str_buffer = try std.Buffer.allocPrint(allocator, | ||
| 1005 | \\Os{{ | ||
| 1006 | \\ .tag = .{}, | ||
| 1007 | \\ .version_range = .{{ | ||
| 1008 | , .{@tagName(target.os.tag)}); | ||
| 1009 | defer os_builtin_str_buffer.deinit(); | ||
| 1010 | |||
| 1011 | // We'll re-use the OS version range builtin string for the cache hash. | ||
| 1012 | const os_builtin_str_ver_start_index = os_builtin_str_buffer.len(); | ||
| 1013 | |||
| 1014 | @setEvalBranchQuota(2000); | ||
| 1015 | switch (target.os.tag) { | ||
| 1016 | .freestanding, | ||
| 1017 | .ananas, | ||
| 1018 | .cloudabi, | ||
| 1019 | .dragonfly, | ||
| 1020 | .fuchsia, | ||
| 1021 | .ios, | ||
| 1022 | .kfreebsd, | ||
| 1023 | .lv2, | ||
| 1024 | .solaris, | ||
| 1025 | .haiku, | ||
| 1026 | .minix, | ||
| 1027 | .rtems, | ||
| 1028 | .nacl, | ||
| 1029 | .cnk, | ||
| 1030 | .aix, | ||
| 1031 | .cuda, | ||
| 1032 | .nvcl, | ||
| 1033 | .amdhsa, | ||
| 1034 | .ps4, | ||
| 1035 | .elfiamcu, | ||
| 1036 | .tvos, | ||
| 1037 | .watchos, | ||
| 1038 | .mesa3d, | ||
| 1039 | .contiki, | ||
| 1040 | .amdpal, | ||
| 1041 | .hermit, | ||
| 1042 | .hurd, | ||
| 1043 | .wasi, | ||
| 1044 | .emscripten, | ||
| 1045 | .uefi, | ||
| 1046 | .other, | ||
| 1047 | => try os_builtin_str_buffer.append(" .none = {} }\n"), | ||
| 1048 | |||
| 1049 | .freebsd, | ||
| 1050 | .macosx, | ||
| 1051 | .netbsd, | ||
| 1052 | .openbsd, | ||
| 1053 | => try os_builtin_str_buffer.print( | ||
| 1054 | \\.semver = .{{ | ||
| 1055 | \\ .min = .{{ | ||
| 1056 | \\ .major = {}, | ||
| 1057 | \\ .minor = {}, | ||
| 1058 | \\ .patch = {}, | ||
| 1059 | \\ }}, | ||
| 1060 | \\ .max = .{{ | ||
| 1061 | \\ .major = {}, | ||
| 1062 | \\ .minor = {}, | ||
| 1063 | \\ .patch = {}, | ||
| 1064 | \\ }}, | ||
| 1065 | \\ }}}}, | ||
| 1066 | , .{ | ||
| 1067 | target.os.version_range.semver.min.major, | ||
| 1068 | target.os.version_range.semver.min.minor, | ||
| 1069 | target.os.version_range.semver.min.patch, | ||
| 1070 | |||
| 1071 | target.os.version_range.semver.max.major, | ||
| 1072 | target.os.version_range.semver.max.minor, | ||
| 1073 | target.os.version_range.semver.max.patch, | ||
| 1074 | }), | ||
| 1075 | |||
| 1076 | .linux => try os_builtin_str_buffer.print( | ||
| 1077 | \\.linux = .{{ | ||
| 1078 | \\ .range = .{{ | ||
| 1079 | \\ .min = .{{ | ||
| 1080 | \\ .major = {}, | ||
| 1081 | \\ .minor = {}, | ||
| 1082 | \\ .patch = {}, | ||
| 1083 | \\ }}, | ||
| 1084 | \\ .max = .{{ | ||
| 1085 | \\ .major = {}, | ||
| 1086 | \\ .minor = {}, | ||
| 1087 | \\ .patch = {}, | ||
| 1088 | \\ }}, | ||
| 1089 | \\ }}, | ||
| 1090 | \\ .glibc = .{{ | ||
| 1091 | \\ .major = {}, | ||
| 1092 | \\ .minor = {}, | ||
| 1093 | \\ .patch = {}, | ||
| 1094 | \\ }}, | ||
| 1095 | \\ }}}}, | ||
| 1096 | \\ | ||
| 1097 | , .{ | ||
| 1098 | target.os.version_range.linux.range.min.major, | ||
| 1099 | target.os.version_range.linux.range.min.minor, | ||
| 1100 | target.os.version_range.linux.range.min.patch, | ||
| 1101 | |||
| 1102 | target.os.version_range.linux.range.max.major, | ||
| 1103 | target.os.version_range.linux.range.max.minor, | ||
| 1104 | target.os.version_range.linux.range.max.patch, | ||
| 1105 | |||
| 1106 | target.os.version_range.linux.glibc.major, | ||
| 1107 | target.os.version_range.linux.glibc.minor, | ||
| 1108 | target.os.version_range.linux.glibc.patch, | ||
| 1109 | }), | ||
| 1110 | |||
| 1111 | .windows => try os_builtin_str_buffer.print( | ||
| 1112 | \\.semver = .{{ | ||
| 1113 | \\ .min = .{}, | ||
| 1114 | \\ .max = .{}, | ||
| 1115 | \\ }}}}, | ||
| 1116 | , .{ | ||
| 1117 | @tagName(target.os.version_range.windows.min), | ||
| 1118 | @tagName(target.os.version_range.windows.max), | ||
| 1119 | }), | ||
| 1120 | } | ||
| 1121 | try os_builtin_str_buffer.append("};\n"); | ||
| 1122 | |||
| 1123 | try cache_hash.append( | ||
| 1124 | os_builtin_str_buffer.toSlice()[os_builtin_str_ver_start_index..os_builtin_str_buffer.len()], | ||
| 1125 | ); | ||
| 1126 | |||
| 1127 | const glibc_version = if (target.isGnuLibC()) blk: { | ||
| 1128 | const stage1_glibc = try std.heap.c_allocator.create(Stage2GLibCVersion); | ||
| 1129 | const stage2_glibc = target.os.version_range.linux.glibc; | ||
| 1130 | stage1_glibc.* = .{ | ||
| 1131 | .major = stage2_glibc.major, | ||
| 1132 | .minor = stage2_glibc.minor, | ||
| 1133 | .patch = stage2_glibc.patch, | ||
| 1134 | }; | ||
| 1135 | break :blk stage1_glibc; | ||
| 1136 | } else null; | ||
| 1137 | |||
| 985 | self.* = .{ | 1138 | self.* = .{ |
| 986 | .arch = @enumToInt(target.getArch()) + 1, // skip over ZigLLVM_UnknownArch | 1139 | .arch = @enumToInt(target.cpu.arch) + 1, // skip over ZigLLVM_UnknownArch |
| 987 | .vendor = 0, | 1140 | .vendor = 0, |
| 988 | .os = @enumToInt(target.getOs()), | 1141 | .os = @enumToInt(target.os.tag), |
| 989 | .abi = @enumToInt(target.getAbi()), | 1142 | .abi = @enumToInt(target.abi), |
| 990 | .llvm_cpu_name = null, | 1143 | .llvm_cpu_name = if (target.cpu.model.llvm_name) |s| s.ptr else null, |
| 991 | .llvm_cpu_features = null, | 1144 | .llvm_cpu_features = llvm_features_buffer.toOwnedSlice().ptr, |
| 992 | .builtin_str = null, | 1145 | .cpu_builtin_str = cpu_builtin_str_buffer.toOwnedSlice().ptr, |
| 993 | .cache_hash = null, | 1146 | .os_builtin_str = os_builtin_str_buffer.toOwnedSlice().ptr, |
| 994 | .is_native = target == .Native, | 1147 | .cache_hash = cache_hash.toOwnedSlice().ptr, |
| 995 | .glibc_version = null, | 1148 | .is_native = build_target == .Native, |
| 1149 | .glibc_version = glibc_version, | ||
| 1150 | .dynamic_linker = dynamic_linker, | ||
| 996 | }; | 1151 | }; |
| 997 | try initStage1TargetCpuFeatures(self, cpu); | ||
| 998 | } | 1152 | } |
| 999 | }; | 1153 | }; |
| 1000 | 1154 | ||
| 1155 | fn enumInt(comptime Enum: type, int: c_int) Enum { | ||
| 1156 | return @intToEnum(Enum, @intCast(@TagType(Enum), int)); | ||
| 1157 | } | ||
| 1158 | |||
| 1001 | // ABI warning | 1159 | // ABI warning |
| 1002 | const Stage2GLibCVersion = extern struct { | 1160 | const Stage2GLibCVersion = extern struct { |
| 1003 | major: u32, | 1161 | major: u32, |
| ... | @@ -1005,26 +1163,6 @@ const Stage2GLibCVersion = extern struct { | ... | @@ -1005,26 +1163,6 @@ const Stage2GLibCVersion = extern struct { |
| 1005 | patch: u32, | 1163 | patch: u32, |
| 1006 | }; | 1164 | }; |
| 1007 | 1165 | ||
| 1008 | // ABI warning | ||
| 1009 | export fn stage2_detect_dynamic_linker(in_target: *const Stage2Target, out_ptr: *[*:0]u8, out_len: *usize) Error { | ||
| 1010 | const target = in_target.toTarget(); | ||
| 1011 | const result = @import("introspect.zig").detectDynamicLinker( | ||
| 1012 | std.heap.c_allocator, | ||
| 1013 | target, | ||
| 1014 | ) catch |err| switch (err) { | ||
| 1015 | error.OutOfMemory => return .OutOfMemory, | ||
| 1016 | error.UnknownDynamicLinkerPath => return .UnknownDynamicLinkerPath, | ||
| 1017 | error.TargetHasNoDynamicLinker => return .TargetHasNoDynamicLinker, | ||
| 1018 | }; | ||
| 1019 | out_ptr.* = result.ptr; | ||
| 1020 | out_len.* = result.len; | ||
| 1021 | return .None; | ||
| 1022 | } | ||
| 1023 | |||
| 1024 | fn enumInt(comptime Enum: type, int: c_int) Enum { | ||
| 1025 | return @intToEnum(Enum, @intCast(@TagType(Enum), int)); | ||
| 1026 | } | ||
| 1027 | |||
| 1028 | // ABI warning | 1166 | // ABI warning |
| 1029 | const Stage2NativePaths = extern struct { | 1167 | const Stage2NativePaths = extern struct { |
| 1030 | include_dirs_ptr: [*][*:0]u8, | 1168 | include_dirs_ptr: [*][*:0]u8, |
src-self-hosted/util.zig-22| ... | @@ -34,25 +34,3 @@ pub fn initializeAllTargets() void { | ... | @@ -34,25 +34,3 @@ pub fn initializeAllTargets() void { |
| 34 | llvm.InitializeAllAsmPrinters(); | 34 | llvm.InitializeAllAsmPrinters(); |
| 35 | llvm.InitializeAllAsmParsers(); | 35 | llvm.InitializeAllAsmParsers(); |
| 36 | } | 36 | } |
| 37 | |||
| 38 | pub fn getTriple(allocator: *std.mem.Allocator, self: std.Target) !std.Buffer { | ||
| 39 | var result = try std.Buffer.initSize(allocator, 0); | ||
| 40 | errdefer result.deinit(); | ||
| 41 | |||
| 42 | // LLVM WebAssembly output support requires the target to be activated at | ||
| 43 | // build type with -DCMAKE_LLVM_EXPIERMENTAL_TARGETS_TO_BUILD=WebAssembly. | ||
| 44 | // | ||
| 45 | // LLVM determines the output format based on the abi suffix, | ||
| 46 | // defaulting to an object based on the architecture. The default format in | ||
| 47 | // LLVM 6 sets the wasm arch output incorrectly to ELF. We need to | ||
| 48 | // explicitly set this ourself in order for it to work. | ||
| 49 | // | ||
| 50 | // This is fixed in LLVM 7 and you will be able to get wasm output by | ||
| 51 | // using the target triple `wasm32-unknown-unknown-unknown`. | ||
| 52 | const env_name = if (self.isWasm()) "wasm" else @tagName(self.getAbi()); | ||
| 53 | |||
| 54 | var out = &std.io.BufferOutStream.init(&result).stream; | ||
| 55 | try out.print("{}-unknown-{}-{}", .{ @tagName(self.getArch()), @tagName(self.getOs()), env_name }); | ||
| 56 | |||
| 57 | return result; | ||
| 58 | } |
src/codegen.cpp+14-24| ... | @@ -4483,7 +4483,7 @@ static LLVMValueRef ir_render_union_field_ptr(CodeGen *g, IrExecutableGen *execu | ... | @@ -4483,7 +4483,7 @@ static LLVMValueRef ir_render_union_field_ptr(CodeGen *g, IrExecutableGen *execu |
| 4483 | 4483 | ||
| 4484 | if (!type_has_bits(field->type_entry)) { | 4484 | if (!type_has_bits(field->type_entry)) { |
| 4485 | ZigType *tag_type = union_type->data.unionation.tag_type; | 4485 | ZigType *tag_type = union_type->data.unionation.tag_type; |
| 4486 | if (!instruction->initializing || !type_has_bits(tag_type)) | 4486 | if (!instruction->initializing || tag_type == nullptr || !type_has_bits(tag_type)) |
| 4487 | return nullptr; | 4487 | return nullptr; |
| 4488 | 4488 | ||
| 4489 | // The field has no bits but we still have to change the discriminant | 4489 | // The field has no bits but we still have to change the discriminant |
| ... | @@ -8543,25 +8543,24 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { | ... | @@ -8543,25 +8543,24 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { |
| 8543 | buf_appendf(contents, "pub const link_mode = LinkMode.%s;\n", link_type); | 8543 | buf_appendf(contents, "pub const link_mode = LinkMode.%s;\n", link_type); |
| 8544 | buf_appendf(contents, "pub const is_test = %s;\n", bool_to_str(g->is_test_build)); | 8544 | buf_appendf(contents, "pub const is_test = %s;\n", bool_to_str(g->is_test_build)); |
| 8545 | buf_appendf(contents, "pub const single_threaded = %s;\n", bool_to_str(g->is_single_threaded)); | 8545 | buf_appendf(contents, "pub const single_threaded = %s;\n", bool_to_str(g->is_single_threaded)); |
| 8546 | buf_appendf(contents, "pub const os = Os.%s;\n", cur_os); | 8546 | buf_append_str(contents, "/// Deprecated: use `std.Target.cpu.arch`\n"); |
| 8547 | buf_appendf(contents, "pub const arch = Arch.%s;\n", cur_arch); | 8547 | buf_appendf(contents, "pub const arch = Arch.%s;\n", cur_arch); |
| 8548 | buf_appendf(contents, "pub const abi = Abi.%s;\n", cur_abi); | 8548 | buf_appendf(contents, "pub const abi = Abi.%s;\n", cur_abi); |
| 8549 | { | 8549 | { |
| 8550 | buf_append_str(contents, "pub const cpu: Cpu = "); | 8550 | buf_append_str(contents, "pub const cpu: Cpu = "); |
| 8551 | if (g->zig_target->builtin_str != nullptr) { | 8551 | if (g->zig_target->cpu_builtin_str != nullptr) { |
| 8552 | buf_append_str(contents, g->zig_target->builtin_str); | 8552 | buf_append_str(contents, g->zig_target->cpu_builtin_str); |
| 8553 | } else { | 8553 | } else { |
| 8554 | buf_append_str(contents, "Target.Cpu.baseline(arch);\n"); | 8554 | buf_appendf(contents, "Target.Cpu.baseline(.%s);\n", cur_arch); |
| 8555 | } | 8555 | } |
| 8556 | } | 8556 | } |
| 8557 | if (g->libc_link_lib != nullptr && g->zig_target->glibc_version != nullptr) { | 8557 | { |
| 8558 | buf_appendf(contents, | 8558 | buf_append_str(contents, "pub const os = "); |
| 8559 | "pub const glibc_version: ?Version = Version{.major = %d, .minor = %d, .patch = %d};\n", | 8559 | if (g->zig_target->os_builtin_str != nullptr) { |
| 8560 | g->zig_target->glibc_version->major, | 8560 | buf_append_str(contents, g->zig_target->os_builtin_str); |
| 8561 | g->zig_target->glibc_version->minor, | 8561 | } else { |
| 8562 | g->zig_target->glibc_version->patch); | 8562 | buf_appendf(contents, "Target.Os.defaultVersionRange(.%s);\n", cur_os); |
| 8563 | } else { | 8563 | } |
| 8564 | buf_appendf(contents, "pub const glibc_version: ?Version = null;\n"); | ||
| 8565 | } | 8564 | } |
| 8566 | buf_appendf(contents, "pub const object_format = ObjectFormat.%s;\n", cur_obj_fmt); | 8565 | buf_appendf(contents, "pub const object_format = ObjectFormat.%s;\n", cur_obj_fmt); |
| 8567 | buf_appendf(contents, "pub const mode = %s;\n", build_mode_to_str(g->build_mode)); | 8566 | buf_appendf(contents, "pub const mode = %s;\n", build_mode_to_str(g->build_mode)); |
| ... | @@ -8867,8 +8866,6 @@ static void init(CodeGen *g) { | ... | @@ -8867,8 +8866,6 @@ static void init(CodeGen *g) { |
| 8867 | } | 8866 | } |
| 8868 | 8867 | ||
| 8869 | static void detect_dynamic_linker(CodeGen *g) { | 8868 | static void detect_dynamic_linker(CodeGen *g) { |
| 8870 | Error err; | ||
| 8871 | |||
| 8872 | if (g->dynamic_linker_path != nullptr) | 8869 | if (g->dynamic_linker_path != nullptr) |
| 8873 | return; | 8870 | return; |
| 8874 | if (!g->have_dynamic_link) | 8871 | if (!g->have_dynamic_link) |
| ... | @@ -8876,16 +8873,9 @@ static void detect_dynamic_linker(CodeGen *g) { | ... | @@ -8876,16 +8873,9 @@ static void detect_dynamic_linker(CodeGen *g) { |
| 8876 | if (g->out_type == OutTypeObj || (g->out_type == OutTypeLib && !g->is_dynamic)) | 8873 | if (g->out_type == OutTypeObj || (g->out_type == OutTypeLib && !g->is_dynamic)) |
| 8877 | return; | 8874 | return; |
| 8878 | 8875 | ||
| 8879 | char *dynamic_linker_ptr; | 8876 | if (g->zig_target->dynamic_linker != nullptr) { |
| 8880 | size_t dynamic_linker_len; | 8877 | g->dynamic_linker_path = buf_create_from_str(g->zig_target->dynamic_linker); |
| 8881 | if ((err = stage2_detect_dynamic_linker(g->zig_target, &dynamic_linker_ptr, &dynamic_linker_len))) { | ||
| 8882 | if (err == ErrorTargetHasNoDynamicLinker) return; | ||
| 8883 | fprintf(stderr, "Unable to detect dynamic linker: %s\n", err_str(err)); | ||
| 8884 | exit(1); | ||
| 8885 | } | 8878 | } |
| 8886 | g->dynamic_linker_path = buf_create_from_mem(dynamic_linker_ptr, dynamic_linker_len); | ||
| 8887 | // Skips heap::c_allocator because the memory is allocated by stage2 library. | ||
| 8888 | free(dynamic_linker_ptr); | ||
| 8889 | } | 8879 | } |
| 8890 | 8880 | ||
| 8891 | static void detect_libc(CodeGen *g) { | 8881 | static void detect_libc(CodeGen *g) { |
src/error.cpp+2| ... | @@ -81,6 +81,8 @@ const char *err_str(Error err) { | ... | @@ -81,6 +81,8 @@ const char *err_str(Error err) { |
| 81 | case ErrorWindowsSdkNotFound: return "Windows SDK not found"; | 81 | case ErrorWindowsSdkNotFound: return "Windows SDK not found"; |
| 82 | case ErrorUnknownDynamicLinkerPath: return "unknown dynamic linker path"; | 82 | case ErrorUnknownDynamicLinkerPath: return "unknown dynamic linker path"; |
| 83 | case ErrorTargetHasNoDynamicLinker: return "target has no dynamic linker"; | 83 | case ErrorTargetHasNoDynamicLinker: return "target has no dynamic linker"; |
| 84 | case ErrorInvalidAbiVersion: return "invalid C ABI version"; | ||
| 85 | case ErrorInvalidOperatingSystemVersion: return "invalid operating system version"; | ||
| 84 | } | 86 | } |
| 85 | return "(invalid error)"; | 87 | return "(invalid error)"; |
| 86 | } | 88 | } |
src/main.cpp+1-28| ... | @@ -89,8 +89,7 @@ static int print_full_usage(const char *arg0, FILE *file, int return_code) { | ... | @@ -89,8 +89,7 @@ static int print_full_usage(const char *arg0, FILE *file, int return_code) { |
| 89 | " --single-threaded source may assume it is only used single-threaded\n" | 89 | " --single-threaded source may assume it is only used single-threaded\n" |
| 90 | " -dynamic create a shared library (.so; .dll; .dylib)\n" | 90 | " -dynamic create a shared library (.so; .dll; .dylib)\n" |
| 91 | " --strip exclude debug symbols\n" | 91 | " --strip exclude debug symbols\n" |
| 92 | " -target [name] <arch><sub>-<os>-<abi> see the targets command\n" | 92 | " -target [name] <arch>-<os>-<abi> see the targets command\n" |
| 93 | " -target-glibc [version] target a specific glibc version (default: 2.17)\n" | ||
| 94 | " --verbose-tokenize enable compiler debug output for tokenization\n" | 93 | " --verbose-tokenize enable compiler debug output for tokenization\n" |
| 95 | " --verbose-ast enable compiler debug output for AST parsing\n" | 94 | " --verbose-ast enable compiler debug output for AST parsing\n" |
| 96 | " --verbose-link enable compiler debug output for linking\n" | 95 | " --verbose-link enable compiler debug output for linking\n" |
| ... | @@ -419,7 +418,6 @@ static int main0(int argc, char **argv) { | ... | @@ -419,7 +418,6 @@ static int main0(int argc, char **argv) { |
| 419 | const char *mios_version_min = nullptr; | 418 | const char *mios_version_min = nullptr; |
| 420 | const char *linker_script = nullptr; | 419 | const char *linker_script = nullptr; |
| 421 | Buf *version_script = nullptr; | 420 | Buf *version_script = nullptr; |
| 422 | const char *target_glibc = nullptr; | ||
| 423 | ZigList<const char *> rpath_list = {0}; | 421 | ZigList<const char *> rpath_list = {0}; |
| 424 | bool each_lib_rpath = false; | 422 | bool each_lib_rpath = false; |
| 425 | ZigList<const char *> objects = {0}; | 423 | ZigList<const char *> objects = {0}; |
| ... | @@ -853,8 +851,6 @@ static int main0(int argc, char **argv) { | ... | @@ -853,8 +851,6 @@ static int main0(int argc, char **argv) { |
| 853 | linker_script = argv[i]; | 851 | linker_script = argv[i]; |
| 854 | } else if (strcmp(arg, "--version-script") == 0) { | 852 | } else if (strcmp(arg, "--version-script") == 0) { |
| 855 | version_script = buf_create_from_str(argv[i]); | 853 | version_script = buf_create_from_str(argv[i]); |
| 856 | } else if (strcmp(arg, "-target-glibc") == 0) { | ||
| 857 | target_glibc = argv[i]; | ||
| 858 | } else if (strcmp(arg, "-rpath") == 0) { | 854 | } else if (strcmp(arg, "-rpath") == 0) { |
| 859 | rpath_list.append(argv[i]); | 855 | rpath_list.append(argv[i]); |
| 860 | } else if (strcmp(arg, "--test-filter") == 0) { | 856 | } else if (strcmp(arg, "--test-filter") == 0) { |
| ... | @@ -982,29 +978,6 @@ static int main0(int argc, char **argv) { | ... | @@ -982,29 +978,6 @@ static int main0(int argc, char **argv) { |
| 982 | "See `%s targets` to display valid targets.\n", err_str(err), arg0); | 978 | "See `%s targets` to display valid targets.\n", err_str(err), arg0); |
| 983 | return print_error_usage(arg0); | 979 | return print_error_usage(arg0); |
| 984 | } | 980 | } |
| 985 | if (target_is_glibc(&target)) { | ||
| 986 | target.glibc_version = heap::c_allocator.create<ZigGLibCVersion>(); | ||
| 987 | |||
| 988 | if (target_glibc != nullptr) { | ||
| 989 | if ((err = target_parse_glibc_version(target.glibc_version, target_glibc))) { | ||
| 990 | fprintf(stderr, "invalid glibc version '%s': %s\n", target_glibc, err_str(err)); | ||
| 991 | return print_error_usage(arg0); | ||
| 992 | } | ||
| 993 | } else { | ||
| 994 | target_init_default_glibc_version(&target); | ||
| 995 | #if defined(ZIG_OS_LINUX) | ||
| 996 | if (target.is_native) { | ||
| 997 | // TODO self-host glibc version detection, and then this logic can go away | ||
| 998 | if ((err = glibc_detect_native_version(target.glibc_version))) { | ||
| 999 | // Fall back to the default version. | ||
| 1000 | } | ||
| 1001 | } | ||
| 1002 | #endif | ||
| 1003 | } | ||
| 1004 | } else if (target_glibc != nullptr) { | ||
| 1005 | fprintf(stderr, "'%s' is not a glibc-compatible target", target_string); | ||
| 1006 | return print_error_usage(arg0); | ||
| 1007 | } | ||
| 1008 | 981 | ||
| 1009 | Buf zig_triple_buf = BUF_INIT; | 982 | Buf zig_triple_buf = BUF_INIT; |
| 1010 | target_triple_zig(&zig_triple_buf, &target); | 983 | target_triple_zig(&zig_triple_buf, &target); |
src/stage2.cpp-8| ... | @@ -100,13 +100,11 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons | ... | @@ -100,13 +100,11 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons |
| 100 | if (mcpu == nullptr) { | 100 | if (mcpu == nullptr) { |
| 101 | target->llvm_cpu_name = ZigLLVMGetHostCPUName(); | 101 | target->llvm_cpu_name = ZigLLVMGetHostCPUName(); |
| 102 | target->llvm_cpu_features = ZigLLVMGetNativeFeatures(); | 102 | target->llvm_cpu_features = ZigLLVMGetNativeFeatures(); |
| 103 | target->builtin_str = "Target.Cpu.baseline(arch);\n"; | ||
| 104 | target->cache_hash = "native\n\n"; | 103 | target->cache_hash = "native\n\n"; |
| 105 | } else if (strcmp(mcpu, "baseline") == 0) { | 104 | } else if (strcmp(mcpu, "baseline") == 0) { |
| 106 | target->is_native = false; | 105 | target->is_native = false; |
| 107 | target->llvm_cpu_name = ""; | 106 | target->llvm_cpu_name = ""; |
| 108 | target->llvm_cpu_features = ""; | 107 | target->llvm_cpu_features = ""; |
| 109 | target->builtin_str = "Target.Cpu.baseline(arch);\n"; | ||
| 110 | target->cache_hash = "baseline\n\n"; | 108 | target->cache_hash = "baseline\n\n"; |
| 111 | } else { | 109 | } else { |
| 112 | const char *msg = "stage0 can't handle CPU/features in the target"; | 110 | const char *msg = "stage0 can't handle CPU/features in the target"; |
| ... | @@ -148,7 +146,6 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons | ... | @@ -148,7 +146,6 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons |
| 148 | const char *msg = "stage0 can't handle CPU/features in the target"; | 146 | const char *msg = "stage0 can't handle CPU/features in the target"; |
| 149 | stage2_panic(msg, strlen(msg)); | 147 | stage2_panic(msg, strlen(msg)); |
| 150 | } | 148 | } |
| 151 | target->builtin_str = "Target.Cpu.baseline(arch);\n"; | ||
| 152 | target->cache_hash = "\n\n"; | 149 | target->cache_hash = "\n\n"; |
| 153 | } | 150 | } |
| 154 | 151 | ||
| ... | @@ -186,11 +183,6 @@ enum Error stage2_libc_find_native(struct Stage2LibCInstallation *libc) { | ... | @@ -186,11 +183,6 @@ enum Error stage2_libc_find_native(struct Stage2LibCInstallation *libc) { |
| 186 | stage2_panic(msg, strlen(msg)); | 183 | stage2_panic(msg, strlen(msg)); |
| 187 | } | 184 | } |
| 188 | 185 | ||
| 189 | enum Error stage2_detect_dynamic_linker(const struct ZigTarget *target, char **out_ptr, size_t *out_len) { | ||
| 190 | const char *msg = "stage0 called stage2_detect_dynamic_linker"; | ||
| 191 | stage2_panic(msg, strlen(msg)); | ||
| 192 | } | ||
| 193 | |||
| 194 | enum Error stage2_detect_native_paths(struct Stage2NativePaths *native_paths) { | 186 | enum Error stage2_detect_native_paths(struct Stage2NativePaths *native_paths) { |
| 195 | native_paths->include_dirs_ptr = nullptr; | 187 | native_paths->include_dirs_ptr = nullptr; |
| 196 | native_paths->include_dirs_len = 0; | 188 | native_paths->include_dirs_len = 0; |
src/stage2.h+5-5| ... | @@ -103,6 +103,8 @@ enum Error { | ... | @@ -103,6 +103,8 @@ enum Error { |
| 103 | ErrorWindowsSdkNotFound, | 103 | ErrorWindowsSdkNotFound, |
| 104 | ErrorUnknownDynamicLinkerPath, | 104 | ErrorUnknownDynamicLinkerPath, |
| 105 | ErrorTargetHasNoDynamicLinker, | 105 | ErrorTargetHasNoDynamicLinker, |
| 106 | ErrorInvalidAbiVersion, | ||
| 107 | ErrorInvalidOperatingSystemVersion, | ||
| 106 | }; | 108 | }; |
| 107 | 109 | ||
| 108 | // ABI warning | 110 | // ABI warning |
| ... | @@ -290,14 +292,12 @@ struct ZigTarget { | ... | @@ -290,14 +292,12 @@ struct ZigTarget { |
| 290 | 292 | ||
| 291 | const char *llvm_cpu_name; | 293 | const char *llvm_cpu_name; |
| 292 | const char *llvm_cpu_features; | 294 | const char *llvm_cpu_features; |
| 293 | const char *builtin_str; | 295 | const char *cpu_builtin_str; |
| 294 | const char *cache_hash; | 296 | const char *cache_hash; |
| 297 | const char *os_builtin_str; | ||
| 298 | const char *dynamic_linker; | ||
| 295 | }; | 299 | }; |
| 296 | 300 | ||
| 297 | // ABI warning | ||
| 298 | ZIG_EXTERN_C enum Error stage2_detect_dynamic_linker(const struct ZigTarget *target, | ||
| 299 | char **out_ptr, size_t *out_len); | ||
| 300 | |||
| 301 | // ABI warning | 301 | // ABI warning |
| 302 | ZIG_EXTERN_C enum Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, const char *mcpu); | 302 | ZIG_EXTERN_C enum Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, const char *mcpu); |
| 303 | 303 |
test/stage1/behavior/asm.zig+4-3| ... | @@ -1,9 +1,10 @@ | ... | @@ -1,9 +1,10 @@ |
| 1 | const std = @import("std"); | 1 | const std = @import("std"); |
| 2 | const config = @import("builtin"); | ||
| 3 | const expect = std.testing.expect; | 2 | const expect = std.testing.expect; |
| 4 | 3 | ||
| 4 | const is_x86_64_linux = std.Target.current.cpu.arch == .x86_64 and std.Target.current.os.tag == .linux; | ||
| 5 | |||
| 5 | comptime { | 6 | comptime { |
| 6 | if (config.arch == config.Arch.x86_64 and config.os == config.Os.linux) { | 7 | if (is_x86_64_linux) { |
| 7 | asm ( | 8 | asm ( |
| 8 | \\.globl this_is_my_alias; | 9 | \\.globl this_is_my_alias; |
| 9 | \\.type this_is_my_alias, @function; | 10 | \\.type this_is_my_alias, @function; |
| ... | @@ -13,7 +14,7 @@ comptime { | ... | @@ -13,7 +14,7 @@ comptime { |
| 13 | } | 14 | } |
| 14 | 15 | ||
| 15 | test "module level assembly" { | 16 | test "module level assembly" { |
| 16 | if (config.arch == config.Arch.x86_64 and config.os == config.Os.linux) { | 17 | if (is_x86_64_linux) { |
| 17 | expect(this_is_my_alias() == 1234); | 18 | expect(this_is_my_alias() == 1234); |
| 18 | } | 19 | } |
| 19 | } | 20 | } |
test/stage1/behavior/byteswap.zig+2-3| ... | @@ -1,6 +1,5 @@ | ... | @@ -1,6 +1,5 @@ |
| 1 | const std = @import("std"); | 1 | const std = @import("std"); |
| 2 | const expect = std.testing.expect; | 2 | const expect = std.testing.expect; |
| 3 | const builtin = @import("builtin"); | ||
| 4 | 3 | ||
| 5 | test "@byteSwap integers" { | 4 | test "@byteSwap integers" { |
| 6 | const ByteSwapIntTest = struct { | 5 | const ByteSwapIntTest = struct { |
| ... | @@ -41,10 +40,10 @@ test "@byteSwap integers" { | ... | @@ -41,10 +40,10 @@ test "@byteSwap integers" { |
| 41 | 40 | ||
| 42 | test "@byteSwap vectors" { | 41 | test "@byteSwap vectors" { |
| 43 | // https://github.com/ziglang/zig/issues/3563 | 42 | // https://github.com/ziglang/zig/issues/3563 |
| 44 | if (builtin.os == .dragonfly) return error.SkipZigTest; | 43 | if (std.Target.current.os.tag == .dragonfly) return error.SkipZigTest; |
| 45 | 44 | ||
| 46 | // https://github.com/ziglang/zig/issues/3317 | 45 | // https://github.com/ziglang/zig/issues/3317 |
| 47 | if (builtin.arch == .mipsel) return error.SkipZigTest; | 46 | if (std.Target.current.cpu.arch == .mipsel) return error.SkipZigTest; |
| 48 | 47 | ||
| 49 | const ByteSwapVectorTest = struct { | 48 | const ByteSwapVectorTest = struct { |
| 50 | fn run() void { | 49 | fn run() void { |
test/stage1/behavior/namespace_depends_on_compile_var.zig+4-4| ... | @@ -1,5 +1,5 @@ | ... | @@ -1,5 +1,5 @@ |
| 1 | const builtin = @import("builtin"); | 1 | const std = @import("std"); |
| 2 | const expect = @import("std").testing.expect; | 2 | const expect = std.testing.expect; |
| 3 | 3 | ||
| 4 | test "namespace depends on compile var" { | 4 | test "namespace depends on compile var" { |
| 5 | if (some_namespace.a_bool) { | 5 | if (some_namespace.a_bool) { |
| ... | @@ -8,7 +8,7 @@ test "namespace depends on compile var" { | ... | @@ -8,7 +8,7 @@ test "namespace depends on compile var" { |
| 8 | expect(!some_namespace.a_bool); | 8 | expect(!some_namespace.a_bool); |
| 9 | } | 9 | } |
| 10 | } | 10 | } |
| 11 | const some_namespace = switch (builtin.os) { | 11 | const some_namespace = switch (std.builtin.os.tag) { |
| 12 | builtin.Os.linux => @import("namespace_depends_on_compile_var/a.zig"), | 12 | .linux => @import("namespace_depends_on_compile_var/a.zig"), |
| 13 | else => @import("namespace_depends_on_compile_var/b.zig"), | 13 | else => @import("namespace_depends_on_compile_var/b.zig"), |
| 14 | }; | 14 | }; |
test/stage1/behavior/vector.zig+1-2| ... | @@ -2,7 +2,6 @@ const std = @import("std"); | ... | @@ -2,7 +2,6 @@ const std = @import("std"); |
| 2 | const mem = std.mem; | 2 | const mem = std.mem; |
| 3 | const expect = std.testing.expect; | 3 | const expect = std.testing.expect; |
| 4 | const expectEqual = std.testing.expectEqual; | 4 | const expectEqual = std.testing.expectEqual; |
| 5 | const builtin = @import("builtin"); | ||
| 6 | 5 | ||
| 7 | test "implicit cast vector to array - bool" { | 6 | test "implicit cast vector to array - bool" { |
| 8 | const S = struct { | 7 | const S = struct { |
| ... | @@ -114,7 +113,7 @@ test "array to vector" { | ... | @@ -114,7 +113,7 @@ test "array to vector" { |
| 114 | 113 | ||
| 115 | test "vector casts of sizes not divisable by 8" { | 114 | test "vector casts of sizes not divisable by 8" { |
| 116 | // https://github.com/ziglang/zig/issues/3563 | 115 | // https://github.com/ziglang/zig/issues/3563 |
| 117 | if (builtin.os == .dragonfly) return error.SkipZigTest; | 116 | if (std.Target.current.os.tag == .dragonfly) return error.SkipZigTest; |
| 118 | 117 | ||
| 119 | const S = struct { | 118 | const S = struct { |
| 120 | fn doTheTest() void { | 119 | fn doTheTest() void { |
test/tests.zig+1-1| ... | @@ -31,7 +31,7 @@ pub const RunTranslatedCContext = @import("src/run_translated_c.zig").RunTransla | ... | @@ -31,7 +31,7 @@ pub const RunTranslatedCContext = @import("src/run_translated_c.zig").RunTransla |
| 31 | pub const CompareOutputContext = @import("src/compare_output.zig").CompareOutputContext; | 31 | pub const CompareOutputContext = @import("src/compare_output.zig").CompareOutputContext; |
| 32 | 32 | ||
| 33 | const TestTarget = struct { | 33 | const TestTarget = struct { |
| 34 | target: Target = .Native, | 34 | target: build.Target = .Native, |
| 35 | mode: builtin.Mode = .Debug, | 35 | mode: builtin.Mode = .Debug, |
| 36 | link_libc: bool = false, | 36 | link_libc: bool = false, |
| 37 | single_threaded: bool = false, | 37 | single_threaded: bool = false, |