| author | |
| committer | |
| log | f83834993e2628e347da71a11ffb07c804fc46c5 |
| tree | 21fd10b3ba19c4236326549872a202a4ffe29b3f |
| parent | fe2bd9dda8467b775da4fe3bd535aece9e07ee1b |
17 files changed, 164 insertions(+), 97 deletions(-)
lib/std/crypto/tlcsprng.zig+8-13| ... | ... | @@ -5,7 +5,6 @@ |
| 5 | 5 | |
| 6 | 6 | const std = @import("std"); |
| 7 | 7 | const builtin = @import("builtin"); |
| 8 | const root = @import("root"); | |
| 9 | 8 | const mem = std.mem; |
| 10 | 9 | const os = std.os; |
| 11 | 10 | |
| ... | ... | @@ -67,8 +66,8 @@ fn tlsCsprngFill(_: *anyopaque, buffer: []u8) void { |
| 67 | 66 | // Allow applications to decide they would prefer to have every call to |
| 68 | 67 | // std.crypto.random always make an OS syscall, rather than rely on an |
| 69 | 68 | // application implementation of a CSPRNG. |
| 70 | if (comptime std.meta.globalOption("crypto_always_getrandom", bool) orelse false) { | |
| 71 | return fillWithOsEntropy(buffer); | |
| 69 | if (std.options.crypto_always_getrandom) { | |
| 70 | return defaultRandomSeed(buffer); | |
| 72 | 71 | } |
| 73 | 72 | |
| 74 | 73 | if (wipe_mem.len == 0) { |
| ... | ... | @@ -86,7 +85,7 @@ fn tlsCsprngFill(_: *anyopaque, buffer: []u8) void { |
| 86 | 85 | ) catch { |
| 87 | 86 | // Could not allocate memory for the local state, fall back to |
| 88 | 87 | // the OS syscall. |
| 89 | return fillWithOsEntropy(buffer); | |
| 88 | return std.options.cryptoRandomSeed(buffer); | |
| 90 | 89 | }; |
| 91 | 90 | // The memory is already zero-initialized. |
| 92 | 91 | } else { |
| ... | ... | @@ -128,14 +127,14 @@ fn tlsCsprngFill(_: *anyopaque, buffer: []u8) void { |
| 128 | 127 | // Since we failed to set up fork safety, we fall back to always |
| 129 | 128 | // calling getrandom every time. |
| 130 | 129 | ctx.init_state = .failed; |
| 131 | return fillWithOsEntropy(buffer); | |
| 130 | return std.options.cryptoRandomSeed(buffer); | |
| 132 | 131 | }, |
| 133 | 132 | .initialized => { |
| 134 | 133 | return fillWithCsprng(buffer); |
| 135 | 134 | }, |
| 136 | 135 | .failed => { |
| 137 | 136 | if (want_fork_safety) { |
| 138 | return fillWithOsEntropy(buffer); | |
| 137 | return std.options.cryptoRandomSeed(buffer); | |
| 139 | 138 | } else { |
| 140 | 139 | unreachable; |
| 141 | 140 | } |
| ... | ... | @@ -165,7 +164,7 @@ fn fillWithCsprng(buffer: []u8) void { |
| 165 | 164 | mem.set(u8, ctx.gimli.toSlice()[0..std.crypto.core.Gimli.RATE], 0); |
| 166 | 165 | } |
| 167 | 166 | |
| 168 | fn fillWithOsEntropy(buffer: []u8) void { | |
| 167 | pub fn defaultRandomSeed(buffer: []u8) void { | |
| 169 | 168 | os.getrandom(buffer) catch @panic("getrandom() failed to provide entropy"); |
| 170 | 169 | } |
| 171 | 170 | |
| ... | ... | @@ -174,12 +173,8 @@ fn initAndFill(buffer: []u8) void { |
| 174 | 173 | // Because we panic on getrandom() failing, we provide the opportunity |
| 175 | 174 | // to override the default seed function. This also makes |
| 176 | 175 | // `std.crypto.random` available on freestanding targets, provided that |
| 177 | // the `cryptoRandomSeed` function is provided. | |
| 178 | if (@hasDecl(root, "cryptoRandomSeed")) { | |
| 179 | root.cryptoRandomSeed(&seed); | |
| 180 | } else { | |
| 181 | fillWithOsEntropy(&seed); | |
| 182 | } | |
| 176 | // the `std.options.cryptoRandomSeed` function is provided. | |
| 177 | std.options.cryptoRandomSeed(&seed); | |
| 183 | 178 | |
| 184 | 179 | const ctx = @ptrCast(*Context, wipe_mem.ptr); |
| 185 | 180 | ctx.gimli = std.crypto.core.Gimli.init(seed); |
lib/std/debug.zig+3-4| ... | ... | @@ -1861,10 +1861,9 @@ pub const have_segfault_handling_support = switch (native_os) { |
| 1861 | 1861 | .freebsd, .openbsd => @hasDecl(os.system, "ucontext_t"), |
| 1862 | 1862 | else => false, |
| 1863 | 1863 | }; |
| 1864 | pub const enable_segfault_handler: bool = if (@hasDecl(root, "enable_segfault_handler")) | |
| 1865 | root.enable_segfault_handler | |
| 1866 | else | |
| 1867 | runtime_safety and have_segfault_handling_support; | |
| 1864 | ||
| 1865 | const enable_segfault_handler = std.options.enable_segfault_handler; | |
| 1866 | pub const default_enable_segfault_handler = runtime_safety and have_segfault_handling_support; | |
| 1868 | 1867 | |
| 1869 | 1868 | pub fn maybeEnableSegfaultHandler() void { |
| 1870 | 1869 | if (enable_segfault_handler) { |
lib/std/event/batch.zig+1-1| ... | ... | @@ -17,7 +17,7 @@ pub fn Batch( |
| 17 | 17 | comptime async_behavior: enum { |
| 18 | 18 | /// Observe the value of `std.io.is_async` to decide whether `add` |
| 19 | 19 | /// and `wait` will be async functions. Asserts that the jobs do not suspend when |
| 20 | /// `std.io.mode == .blocking`. This is a generally safe assumption, and the | |
| 20 | /// `std.options.io_mode == .blocking`. This is a generally safe assumption, and the | |
| 21 | 21 | /// usual recommended option for this parameter. |
| 22 | 22 | auto_async, |
| 23 | 23 |
lib/std/event/loop.zig+13-10| ... | ... | @@ -1,6 +1,5 @@ |
| 1 | 1 | const std = @import("../std.zig"); |
| 2 | 2 | const builtin = @import("builtin"); |
| 3 | const root = @import("root"); | |
| 4 | 3 | const assert = std.debug.assert; |
| 5 | 4 | const testing = std.testing; |
| 6 | 5 | const mem = std.mem; |
| ... | ... | @@ -104,25 +103,29 @@ pub const Loop = struct { |
| 104 | 103 | }; |
| 105 | 104 | }; |
| 106 | 105 | |
| 107 | const LoopOrVoid = switch (std.io.mode) { | |
| 108 | .blocking => void, | |
| 109 | .evented => Loop, | |
| 106 | pub const Instance = switch (std.options.io_mode) { | |
| 107 | .blocking => @TypeOf(null), | |
| 108 | .evented => ?*Loop, | |
| 110 | 109 | }; |
| 110 | pub const instance = std.options.event_loop; | |
| 111 | 111 | |
| 112 | var global_instance_state: LoopOrVoid = undefined; | |
| 113 | const default_instance: ?*LoopOrVoid = switch (std.io.mode) { | |
| 112 | var global_instance_state: Loop = undefined; | |
| 113 | pub const default_instance = switch (std.options.io_mode) { | |
| 114 | 114 | .blocking => null, |
| 115 | 115 | .evented => &global_instance_state, |
| 116 | 116 | }; |
| 117 | pub const instance: ?*LoopOrVoid = if (@hasDecl(root, "event_loop")) root.event_loop else default_instance; | |
| 117 | ||
| 118 | pub const Mode = enum { | |
| 119 | single_threaded, | |
| 120 | multi_threaded, | |
| 121 | }; | |
| 122 | pub const default_mode = .multi_threaded; | |
| 118 | 123 | |
| 119 | 124 | /// TODO copy elision / named return values so that the threads referencing *Loop |
| 120 | 125 | /// have the correct pointer value. |
| 121 | 126 | /// https://github.com/ziglang/zig/issues/2761 and https://github.com/ziglang/zig/issues/2765 |
| 122 | 127 | pub fn init(self: *Loop) !void { |
| 123 | if (builtin.single_threaded or | |
| 124 | (@hasDecl(root, "event_loop_mode") and root.event_loop_mode == .single_threaded)) | |
| 125 | { | |
| 128 | if (builtin.single_threaded or std.options.event_loop_mode == .single_threaded) { | |
| 126 | 129 | return self.initSingleThreaded(); |
| 127 | 130 | } else { |
| 128 | 131 | return self.initMultiThreaded(); |
lib/std/fs.zig+6-6| ... | ... | @@ -2661,17 +2661,17 @@ pub fn cwd() Dir { |
| 2661 | 2661 | if (builtin.os.tag == .windows) { |
| 2662 | 2662 | return Dir{ .fd = os.windows.peb().ProcessParameters.CurrentDirectory.Handle }; |
| 2663 | 2663 | } else if (builtin.os.tag == .wasi) { |
| 2664 | if (@hasDecl(root, "wasi_cwd")) { | |
| 2665 | return root.wasi_cwd(); | |
| 2666 | } else { | |
| 2667 | // Expect the first preopen to be current working directory. | |
| 2668 | return .{ .fd = 3 }; | |
| 2669 | } | |
| 2664 | return std.options.wasiCwd(); | |
| 2670 | 2665 | } else { |
| 2671 | 2666 | return Dir{ .fd = os.AT.FDCWD }; |
| 2672 | 2667 | } |
| 2673 | 2668 | } |
| 2674 | 2669 | |
| 2670 | pub fn defaultWasiCwd() Dir { | |
| 2671 | // Expect the first preopen to be current working directory. | |
| 2672 | return .{ .fd = 3 }; | |
| 2673 | } | |
| 2674 | ||
| 2675 | 2675 | /// Opens a directory at the given path. The directory is a system resource that remains |
| 2676 | 2676 | /// open until `close` is called on the result. |
| 2677 | 2677 | /// See `openDirAbsoluteZ` for a function that accepts a null-terminated path. |
lib/std/fs/file.zig+1-1| ... | ... | @@ -21,7 +21,7 @@ pub const File = struct { |
| 21 | 21 | /// blocking. |
| 22 | 22 | capable_io_mode: io.ModeOverride = io.default_mode, |
| 23 | 23 | |
| 24 | /// Furthermore, even when `std.io.mode` is async, it is still sometimes desirable | |
| 24 | /// Furthermore, even when `std.options.io_mode` is async, it is still sometimes desirable | |
| 25 | 25 | /// to perform blocking I/O, although not by default. For example, when printing a |
| 26 | 26 | /// stack trace to stderr. This field tracks both by acting as an overriding I/O mode. |
| 27 | 27 | /// When not building in async I/O mode, the type only has the `.blocking` tag, making |
lib/std/io.zig+1-8| ... | ... | @@ -19,14 +19,7 @@ pub const Mode = enum { |
| 19 | 19 | evented, |
| 20 | 20 | }; |
| 21 | 21 | |
| 22 | /// The application's chosen I/O mode. This defaults to `Mode.blocking` but can be overridden | |
| 23 | /// by `root.event_loop`. | |
| 24 | pub const mode: Mode = if (@hasDecl(root, "io_mode")) | |
| 25 | root.io_mode | |
| 26 | else if (@hasDecl(root, "event_loop")) | |
| 27 | Mode.evented | |
| 28 | else | |
| 29 | Mode.blocking; | |
| 22 | const mode = std.options.io_mode; | |
| 30 | 23 | pub const is_async = mode != .blocking; |
| 31 | 24 | |
| 32 | 25 | /// This is an enum value to use for I/O mode at runtime, since it takes up zero bytes at runtime, |
lib/std/log.zig+15-26| ... | ... | @@ -1,6 +1,6 @@ |
| 1 | 1 | //! std.log is a standardized interface for logging which allows for the logging |
| 2 | 2 | //! of programs and libraries using this interface to be formatted and filtered |
| 3 | //! by the implementer of the root.log function. | |
| 3 | //! by the implementer of the `std.options.logFn` function. | |
| 4 | 4 | //! |
| 5 | 5 | //! Each log message has an associated scope enum, which can be used to give |
| 6 | 6 | //! context to the logging. The logging functions in std.log implicitly use a |
| ... | ... | @@ -13,16 +13,20 @@ |
| 13 | 13 | //! `const log = std.log.scoped(.libfoo);` to use .libfoo as the scope of its |
| 14 | 14 | //! log messages. |
| 15 | 15 | //! |
| 16 | //! An example root.log might look something like this: | |
| 16 | //! An example `logFn` might look something like this: | |
| 17 | 17 | //! |
| 18 | 18 | //! ``` |
| 19 | 19 | //! const std = @import("std"); |
| 20 | 20 | //! |
| 21 | //! // Set the log level to info | |
| 22 | //! pub const log_level: std.log.Level = .info; | |
| 21 | //! pub const std_options = struct { | |
| 22 | //! // Set the log level to info | |
| 23 | //! pub const log_level = .info; | |
| 23 | 24 | //! |
| 24 | //! // Define root.log to override the std implementation | |
| 25 | //! pub fn log( | |
| 25 | //! // Define logFn to override the std implementation | |
| 26 | //! pub const logFn = myLogFn; | |
| 27 | //! }; | |
| 28 | //! | |
| 29 | //! pub fn myLogFn( | |
| 26 | 30 | //! comptime level: std.log.Level, |
| 27 | 31 | //! comptime scope: @TypeOf(.EnumLiteral), |
| 28 | 32 | //! comptime format: []const u8, |
| ... | ... | @@ -70,7 +74,6 @@ |
| 70 | 74 | |
| 71 | 75 | const std = @import("std.zig"); |
| 72 | 76 | const builtin = @import("builtin"); |
| 73 | const root = @import("root"); | |
| 74 | 77 | |
| 75 | 78 | pub const Level = enum { |
| 76 | 79 | /// Error: something has gone wrong. This might be recoverable or might |
| ... | ... | @@ -102,22 +105,14 @@ pub const default_level: Level = switch (builtin.mode) { |
| 102 | 105 | .ReleaseFast, .ReleaseSmall => .err, |
| 103 | 106 | }; |
| 104 | 107 | |
| 105 | /// The current log level. This is set to root.log_level if present, otherwise | |
| 106 | /// log.default_level. | |
| 107 | pub const level: Level = if (@hasDecl(root, "log_level")) | |
| 108 | root.log_level | |
| 109 | else | |
| 110 | default_level; | |
| 108 | const level = std.options.log_level; | |
| 111 | 109 | |
| 112 | 110 | pub const ScopeLevel = struct { |
| 113 | 111 | scope: @Type(.EnumLiteral), |
| 114 | 112 | level: Level, |
| 115 | 113 | }; |
| 116 | 114 | |
| 117 | const scope_levels = if (@hasDecl(root, "scope_levels")) | |
| 118 | root.scope_levels | |
| 119 | else | |
| 120 | [0]ScopeLevel{}; | |
| 115 | const scope_levels = std.options.log_scope_levels; | |
| 121 | 116 | |
| 122 | 117 | fn log( |
| 123 | 118 | comptime message_level: Level, |
| ... | ... | @@ -127,13 +122,7 @@ fn log( |
| 127 | 122 | ) void { |
| 128 | 123 | if (comptime !logEnabled(message_level, scope)) return; |
| 129 | 124 | |
| 130 | if (@hasDecl(root, "log")) { | |
| 131 | if (@typeInfo(@TypeOf(root.log)) != .Fn) | |
| 132 | @compileError("Expected root.log to be a function"); | |
| 133 | root.log(message_level, scope, format, args); | |
| 134 | } else { | |
| 135 | defaultLog(message_level, scope, format, args); | |
| 136 | } | |
| 125 | std.options.logFn(message_level, scope, format, args); | |
| 137 | 126 | } |
| 138 | 127 | |
| 139 | 128 | /// Determine if a specific log message level and scope combination are enabled for logging. |
| ... | ... | @@ -149,8 +138,8 @@ pub fn defaultLogEnabled(comptime message_level: Level) bool { |
| 149 | 138 | return comptime logEnabled(message_level, default_log_scope); |
| 150 | 139 | } |
| 151 | 140 | |
| 152 | /// The default implementation for root.log. root.log may forward log messages | |
| 153 | /// to this function. | |
| 141 | /// The default implementation for the log function, custom log functions may | |
| 142 | /// forward log messages to this function. | |
| 154 | 143 | pub fn defaultLog( |
| 155 | 144 | comptime message_level: Level, |
| 156 | 145 | comptime scope: @Type(.EnumLiteral), |
lib/std/start.zig+2-2| ... | ... | @@ -527,7 +527,7 @@ const bad_main_ret = "expected return type of main to be 'void', '!void', 'noret |
| 527 | 527 | // and we want fewer call frames in stack traces. |
| 528 | 528 | inline fn initEventLoopAndCallMain() u8 { |
| 529 | 529 | if (std.event.Loop.instance) |loop| { |
| 530 | if (!@hasDecl(root, "event_loop")) { | |
| 530 | if (loop == std.event.Loop.default_instance) { | |
| 531 | 531 | loop.init() catch |err| { |
| 532 | 532 | std.log.err("{s}", .{@errorName(err)}); |
| 533 | 533 | if (@errorReturnTrace()) |trace| { |
| ... | ... | @@ -556,7 +556,7 @@ inline fn initEventLoopAndCallMain() u8 { |
| 556 | 556 | // because it is working around stage1 compiler bugs. |
| 557 | 557 | inline fn initEventLoopAndCallWinMain() std.os.windows.INT { |
| 558 | 558 | if (std.event.Loop.instance) |loop| { |
| 559 | if (!@hasDecl(root, "event_loop")) { | |
| 559 | if (loop == std.event.Loop.default_instance) { | |
| 560 | 560 | loop.init() catch |err| { |
| 561 | 561 | std.log.err("{s}", .{@errorName(err)}); |
| 562 | 562 | if (@errorReturnTrace()) |trace| { |
lib/std/std.zig+69| ... | ... | @@ -94,10 +94,79 @@ pub const wasm = @import("wasm.zig"); |
| 94 | 94 | pub const zig = @import("zig.zig"); |
| 95 | 95 | pub const start = @import("start.zig"); |
| 96 | 96 | |
| 97 | const root = @import("root"); | |
| 98 | const options_override = if (@hasDecl(root, "std_options")) root.std_options else struct {}; | |
| 99 | ||
| 100 | pub const options = struct { | |
| 101 | pub const enable_segfault_handler: bool = if (@hasDecl(options_override, "enable_segfault_handler")) | |
| 102 | options_override.enable_segfault_handler | |
| 103 | else | |
| 104 | debug.default_enable_segfault_handler; | |
| 105 | ||
| 106 | /// Function used to implement std.fs.cwd for wasi. | |
| 107 | pub const wasiCwd: fn () fs.Dir = if (@hasDecl(options_override, "wasiCwd")) | |
| 108 | options_override.wasiCwd | |
| 109 | else | |
| 110 | fs.defaultWasiCwd; | |
| 111 | ||
| 112 | /// The application's chosen I/O mode. | |
| 113 | pub const io_mode: io.Mode = if (@hasDecl(options_override, "io_mode")) | |
| 114 | options_override.io_mode | |
| 115 | else if (@hasDecl(options_override, "event_loop")) | |
| 116 | .evented | |
| 117 | else | |
| 118 | .blocking; | |
| 119 | ||
| 120 | pub const event_loop: event.Loop.Instance = if (@hasDecl(options_override, "event_loop")) | |
| 121 | options_override.event_loop | |
| 122 | else | |
| 123 | event.Loop.default_instance; | |
| 124 | ||
| 125 | pub const event_loop_mode: event.Loop.Mode = if (@hasDecl(options_override, "event_loop_mode")) | |
| 126 | options_override.event_loop_mode | |
| 127 | else | |
| 128 | event.Loop.default_mode; | |
| 129 | ||
| 130 | /// The current log level. | |
| 131 | pub const log_level: log.Level = if (@hasDecl(options_override, "log_level")) | |
| 132 | options_override.log_level | |
| 133 | else | |
| 134 | log.default_level; | |
| 135 | ||
| 136 | pub const log_scope_levels: []const log.ScopeLevel = if (@hasDecl(options_override, "log_scope_levels")) | |
| 137 | options_override.log_scope_levels | |
| 138 | else | |
| 139 | &.{}; | |
| 140 | ||
| 141 | pub const logFn: fn ( | |
| 142 | comptime message_level: log.Level, | |
| 143 | comptime scope: @TypeOf(.enum_literal), | |
| 144 | comptime format: []const u8, | |
| 145 | args: anytype, | |
| 146 | ) void = if (@hasDecl(options_override, "logFn")) | |
| 147 | options_override.logFn | |
| 148 | else | |
| 149 | log.defaultLog; | |
| 150 | ||
| 151 | pub const cryptoRandomSeed: fn (buffer: []u8) void = if (@hasDecl(options_override, "cryptoRandomSeed")) | |
| 152 | options_override.cryptoRandomSeed | |
| 153 | else | |
| 154 | @import("crypto/tlcsprng.zig").defaultRandomSeed; | |
| 155 | ||
| 156 | pub const crypto_always_getrandom: bool = if (@hasDecl(options_override, "crypto_always_getrandom")) | |
| 157 | options_override.crypto_always_getrandom | |
| 158 | else | |
| 159 | false; | |
| 160 | }; | |
| 161 | ||
| 97 | 162 | // This forces the start.zig file to be imported, and the comptime logic inside that |
| 98 | 163 | // file decides whether to export any appropriate start symbols, and call main. |
| 99 | 164 | comptime { |
| 100 | 165 | _ = start; |
| 166 | ||
| 167 | for (@typeInfo(options_override).Struct.decls) |decl| { | |
| 168 | if (!@hasDecl(options, decl.name)) @compileError("no option named " ++ decl.name); | |
| 169 | } | |
| 101 | 170 | } |
| 102 | 171 | |
| 103 | 172 | test { |
lib/test_runner.zig+5-2| ... | ... | @@ -2,7 +2,10 @@ const std = @import("std"); |
| 2 | 2 | const io = std.io; |
| 3 | 3 | const builtin = @import("builtin"); |
| 4 | 4 | |
| 5 | pub const io_mode: io.Mode = builtin.test_io_mode; | |
| 5 | pub const std_options = struct { | |
| 6 | pub const io_mode: io.Mode = builtin.test_io_mode; | |
| 7 | pub const logFn = log; | |
| 8 | }; | |
| 6 | 9 | |
| 7 | 10 | var log_err_count: usize = 0; |
| 8 | 11 | |
| ... | ... | @@ -45,7 +48,7 @@ pub fn main() void { |
| 45 | 48 | if (!have_tty) { |
| 46 | 49 | std.debug.print("{d}/{d} {s}... ", .{ i + 1, test_fn_list.len, test_fn.name }); |
| 47 | 50 | } |
| 48 | const result = if (test_fn.async_frame_size) |size| switch (io_mode) { | |
| 51 | const result = if (test_fn.async_frame_size) |size| switch (std.options.io_mode) { | |
| 49 | 52 | .evented => blk: { |
| 50 | 53 | if (async_frame_buffer.len < size) { |
| 51 | 54 | std.heap.page_allocator.free(async_frame_buffer); |
src/crash_report.zig+3-5| ... | ... | @@ -13,12 +13,10 @@ const Decl = Module.Decl; |
| 13 | 13 | |
| 14 | 14 | pub const is_enabled = builtin.mode == .Debug; |
| 15 | 15 | |
| 16 | /// To use these crash report diagnostics, publish these symbols in your main file. | |
| 16 | /// To use these crash report diagnostics, publish this panic in your main file | |
| 17 | /// and add `pub const enable_segfault_handler = false;` to your `std_options`. | |
| 17 | 18 | /// You will also need to call initialize() on startup, preferably as the very first operation in your program. |
| 18 | pub const root_decls = struct { | |
| 19 | pub const panic = if (is_enabled) compilerPanic else std.builtin.default_panic; | |
| 20 | pub const enable_segfault_handler = false; | |
| 21 | }; | |
| 19 | pub const panic = if (is_enabled) compilerPanic else std.builtin.default_panic; | |
| 22 | 20 | |
| 23 | 21 | /// Install signal handlers to identify crashes and report diagnostics. |
| 24 | 22 | pub fn initialize() void { |
src/main.zig+16-10| ... | ... | @@ -25,11 +25,23 @@ const target_util = @import("target.zig"); |
| 25 | 25 | const ThreadPool = @import("ThreadPool.zig"); |
| 26 | 26 | const crash_report = @import("crash_report.zig"); |
| 27 | 27 | |
| 28 | // Crash report needs to override the panic handler and other root decls | |
| 29 | pub usingnamespace crash_report.root_decls; | |
| 28 | pub const std_options = struct { | |
| 29 | pub const wasiCwd = wasi_cwd; | |
| 30 | pub const logFn = log; | |
| 31 | pub const enable_segfault_handler = false; | |
| 32 | ||
| 33 | pub const log_level: std.log.Level = switch (builtin.mode) { | |
| 34 | .Debug => .debug, | |
| 35 | .ReleaseSafe, .ReleaseFast => .info, | |
| 36 | .ReleaseSmall => .err, | |
| 37 | }; | |
| 38 | }; | |
| 39 | ||
| 40 | // Crash report needs to override the panic handler | |
| 41 | pub const panic = crash_report.panic; | |
| 30 | 42 | |
| 31 | 43 | var wasi_preopens: fs.wasi.Preopens = undefined; |
| 32 | pub inline fn wasi_cwd() fs.Dir { | |
| 44 | pub fn wasi_cwd() fs.Dir { | |
| 33 | 45 | // Expect the first preopen to be current working directory. |
| 34 | 46 | const cwd_fd: std.os.fd_t = 3; |
| 35 | 47 | assert(mem.eql(u8, wasi_preopens.names[cwd_fd], ".")); |
| ... | ... | @@ -111,12 +123,6 @@ const debug_usage = normal_usage ++ |
| 111 | 123 | |
| 112 | 124 | const usage = if (debug_extensions_enabled) debug_usage else normal_usage; |
| 113 | 125 | |
| 114 | pub const log_level: std.log.Level = switch (builtin.mode) { | |
| 115 | .Debug => .debug, | |
| 116 | .ReleaseSafe, .ReleaseFast => .info, | |
| 117 | .ReleaseSmall => .err, | |
| 118 | }; | |
| 119 | ||
| 120 | 126 | var log_scopes: std.ArrayListUnmanaged([]const u8) = .{}; |
| 121 | 127 | |
| 122 | 128 | pub fn log( |
| ... | ... | @@ -128,7 +134,7 @@ pub fn log( |
| 128 | 134 | // Hide debug messages unless: |
| 129 | 135 | // * logging enabled with `-Dlog`. |
| 130 | 136 | // * the --debug-log arg for the scope has been provided |
| 131 | if (@enumToInt(level) > @enumToInt(std.log.level) or | |
| 137 | if (@enumToInt(level) > @enumToInt(std.options.log_level) or | |
| 132 | 138 | @enumToInt(level) > @enumToInt(std.log.Level.info)) |
| 133 | 139 | { |
| 134 | 140 | if (!build_options.enable_logging) return; |
test/behavior/pointers.zig+2-2| ... | ... | @@ -509,8 +509,8 @@ test "ptrCast comptime known slice to C pointer" { |
| 509 | 509 | test "ptrToInt on a generic function" { |
| 510 | 510 | if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO |
| 511 | 511 | if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO |
| 512 | if (builtin.zig_backend == .stage2_aarch64 and builtin.os.tag != .linux) return error.SkipZigTest; // TODO | |
| 513 | if (builtin.zig_backend == .stage2_x86_64 and builtin.os.tag != .linux) return error.SkipZigTest; // TODO | |
| 512 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO | |
| 513 | if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO | |
| 514 | 514 | |
| 515 | 515 | const S = struct { |
| 516 | 516 | fn generic(i: anytype) @TypeOf(i) { |
test/compare_output.zig+12-6| ... | ... | @@ -440,11 +440,14 @@ pub fn addCases(cases: *tests.CompareOutputContext) void { |
| 440 | 440 | cases.add("std.log per scope log level override", |
| 441 | 441 | \\const std = @import("std"); |
| 442 | 442 | \\ |
| 443 | \\pub const log_level: std.log.Level = .debug; | |
| 444 | \\ | |
| 445 | \\pub const scope_levels = [_]std.log.ScopeLevel{ | |
| 446 | \\ .{ .scope = .a, .level = .warn }, | |
| 447 | \\ .{ .scope = .c, .level = .err }, | |
| 443 | \\pub const std_options = struct { | |
| 444 | \\ pub const log_level: std.log.Level = .debug; | |
| 445 | \\ | |
| 446 | \\ pub const log_scope_levels = &[_]std.log.ScopeLevel{ | |
| 447 | \\ .{ .scope = .a, .level = .warn }, | |
| 448 | \\ .{ .scope = .c, .level = .err }, | |
| 449 | \\ }; | |
| 450 | \\ pub const logFn = log; | |
| 448 | 451 | \\}; |
| 449 | 452 | \\ |
| 450 | 453 | \\const loga = std.log.scoped(.a); |
| ... | ... | @@ -494,7 +497,10 @@ pub fn addCases(cases: *tests.CompareOutputContext) void { |
| 494 | 497 | cases.add("std.heap.LoggingAllocator logs to std.log", |
| 495 | 498 | \\const std = @import("std"); |
| 496 | 499 | \\ |
| 497 | \\pub const log_level: std.log.Level = .debug; | |
| 500 | \\pub const std_options = struct { | |
| 501 | \\ pub const log_level: std.log.Level = .debug; | |
| 502 | \\ pub const logFn = log; | |
| 503 | \\}; | |
| 498 | 504 | \\ |
| 499 | 505 | \\pub fn main() !void { |
| 500 | 506 | \\ var allocator_buf: [10]u8 = undefined; |
test/standalone/issue_7030/main.zig+4| ... | ... | @@ -1,5 +1,9 @@ |
| 1 | 1 | const std = @import("std"); |
| 2 | 2 | |
| 3 | pub const std_options = struct { | |
| 4 | pub const logFn = log; | |
| 5 | }; | |
| 6 | ||
| 3 | 7 | pub fn log( |
| 4 | 8 | comptime message_level: std.log.Level, |
| 5 | 9 | comptime scope: @Type(.EnumLiteral), |
test/standalone/issue_9693/main.zig+3-1| ... | ... | @@ -1,2 +1,4 @@ |
| 1 | pub const io_mode = .evented; | |
| 1 | pub const std_options = struct { | |
| 2 | pub const io_mode = .evented; | |
| 3 | }; | |
| 2 | 4 | pub fn main() void {} |