| ... | @@ -99,55 +99,46 @@ pub const GetRandomError = OpenError; | ... | @@ -99,55 +99,46 @@ pub const GetRandomError = OpenError; |
| 99 | /// When linking against libc, this calls the | 99 | /// When linking against libc, this calls the |
| 100 | /// appropriate OS-specific library call. Otherwise it uses the zig standard | 100 | /// appropriate OS-specific library call. Otherwise it uses the zig standard |
| 101 | /// library implementation. | 101 | /// library implementation. |
| 102 | pub fn getrandom(buf: []u8) GetRandomError!void { | 102 | pub fn getrandom(buffer: []u8) GetRandomError!void { |
| 103 | if (windows.is_the_target) { | 103 | if (windows.is_the_target) { |
| 104 | return windows.RtlGenRandom(buf); | 104 | return windows.RtlGenRandom(buffer); |
| 105 | } | 105 | } |
| 106 | if (linux.is_the_target or freebsd.is_the_target) { | 106 | if (linux.is_the_target or freebsd.is_the_target) { |
| 107 | var buf_slice: []u8 = buf[0..]; | 107 | var buf = buffer; |
| 108 | var total_read: usize = 0; | 108 | const use_c = !linux.is_the_target or |
| 109 | const use_c = (!linux.is_the_target) or std.c.versionCheck(builtin.Version{ .major = 2, .minor = 25, .patch = 0 }).ok; | 109 | std.c.versionCheck(builtin.Version{ .major = 2, .minor = 25, .patch = 0 }).ok; |
| 110 | | 110 | |
| 111 | while (total_read < buf.len) { | 111 | while (buf.len != 0) { |
| 112 | var err: u16 = 0; | 112 | var err: u16 = undefined; |
| 113 | | | |
| 114 | const num_read: usize = if (use_c) blk: { | | |
| 115 | const res: c_int = std.c.getrandom(buf_slice.ptr, buf_slice.len, 0); | | |
| 116 | | | |
| 117 | if (res == -1) { | | |
| 118 | err = @intCast(u16, std.c._errno().*); | | |
| 119 | break :blk 0; | | |
| 120 | } else { | | |
| 121 | break :blk @intCast(usize, res); | | |
| 122 | } | | |
| 123 | } else blk: { | | |
| 124 | const res: usize = linux.getrandom(buf_slice.ptr, buf_slice.len, 0); | | |
| 125 | | 113 | |
| 126 | err = @intCast(u16, linux.getErrno(res)); | 114 | const num_read = if (use_c) blk: { |
| 127 | break :blk res; | 115 | const rc = std.c.getrandom(buf.ptr, buf.len, 0); |
| | 116 | err = std.c.getErrno(rc); |
| | 117 | break :blk @bitCast(usize, rc); |
| | 118 | } else blk: { |
| | 119 | const rc = linux.getrandom(buf.ptr, buf.len, 0); |
| | 120 | err = linux.getErrno(rc); |
| | 121 | break :blk rc; |
| 128 | }; | 122 | }; |
| 129 | | 123 | |
| 130 | if (err != 0) { | 124 | switch (err) { |
| 131 | switch (err) { | 125 | 0 => buf = buf[num_read..], |
| 132 | EINVAL => unreachable, | 126 | EINVAL => unreachable, |
| 133 | EFAULT => unreachable, | 127 | EFAULT => unreachable, |
| 134 | EINTR => continue, | 128 | EINTR => continue, |
| 135 | ENOSYS => return getRandomBytesDevURandom(buf), | 129 | ENOSYS => return getRandomBytesDevURandom(buf), |
| 136 | else => return unexpectedErrno(err), | 130 | else => return unexpectedErrno(err), |
| 137 | } | | |
| 138 | } else { | | |
| 139 | total_read += num_read; | | |
| 140 | buf_slice = buf_slice[num_read..]; | | |
| 141 | } | 131 | } |
| 142 | } | 132 | } |
| | 133 | return; |
| 143 | } | 134 | } |
| 144 | if (wasi.is_the_target) { | 135 | if (wasi.is_the_target) { |
| 145 | switch (wasi.random_get(buf.ptr, buf.len)) { | 136 | switch (wasi.random_get(buffer.ptr, buffer.len)) { |
| 146 | 0 => return, | 137 | 0 => return, |
| 147 | else => |err| return unexpectedErrno(err), | 138 | else => |err| return unexpectedErrno(err), |
| 148 | } | 139 | } |
| 149 | } | 140 | } |
| 150 | return getRandomBytesDevURandom(buf); | 141 | return getRandomBytesDevURandom(buffer); |
| 151 | } | 142 | } |
| 152 | | 143 | |
| 153 | fn getRandomBytesDevURandom(buf: []u8) !void { | 144 | fn getRandomBytesDevURandom(buf: []u8) !void { |