| author | |
| committer | |
| log | b64cee2ec2cdfd4c49208b3b32bb925233a73e08 |
| tree | 4a4387479ba8084d7e0f3009a2b54a363f1ba814 |
| parent | 08d41da916787ab0c19130dc4dc4e7b0e75c9fa8 |
| parent | c4d1597f503f812fdf514cdeca50a3f61781b76d |
| signature |
Mmap debug info on linux3 files changed, 106 insertions(+), 28 deletions(-)
std/debug.zig+26-16| ... | ... | @@ -1004,21 +1004,33 @@ pub fn openElfDebugInfo( |
| 1004 | 1004 | fn openSelfDebugInfoLinux(allocator: *mem.Allocator) !DwarfInfo { |
| 1005 | 1005 | const S = struct { |
| 1006 | 1006 | var self_exe_file: os.File = undefined; |
| 1007 | var self_exe_seekable_stream: os.File.SeekableStream = undefined; | |
| 1008 | var self_exe_in_stream: os.File.InStream = undefined; | |
| 1007 | var self_exe_mmap_seekable: io.SliceSeekableInStream = undefined; | |
| 1009 | 1008 | }; |
| 1009 | ||
| 1010 | 1010 | S.self_exe_file = try os.openSelfExe(); |
| 1011 | 1011 | errdefer S.self_exe_file.close(); |
| 1012 | 1012 | |
| 1013 | S.self_exe_seekable_stream = S.self_exe_file.seekableStream(); | |
| 1014 | S.self_exe_in_stream = S.self_exe_file.inStream(); | |
| 1013 | const self_exe_mmap_len = try S.self_exe_file.getEndPos(); | |
| 1014 | const self_exe_mmap = os.posix.mmap( | |
| 1015 | null, | |
| 1016 | self_exe_mmap_len, | |
| 1017 | os.posix.PROT_READ, | |
| 1018 | os.posix.MAP_SHARED, | |
| 1019 | S.self_exe_file.handle, | |
| 1020 | 0, | |
| 1021 | ); | |
| 1022 | if (self_exe_mmap == os.posix.MAP_FAILED) return error.OutOfMemory; | |
| 1023 | errdefer assert(os.posix.munmap(self_exe_mmap, self_exe_mmap_len) == 0); | |
| 1024 | ||
| 1025 | const file_mmap_slice = @intToPtr([*]const u8, self_exe_mmap)[0..self_exe_mmap_len]; | |
| 1026 | S.self_exe_mmap_seekable = io.SliceSeekableInStream.init(file_mmap_slice); | |
| 1015 | 1027 | |
| 1016 | 1028 | return openElfDebugInfo( |
| 1017 | 1029 | allocator, |
| 1018 | 1030 | // TODO https://github.com/ziglang/zig/issues/764 |
| 1019 | @ptrCast(*DwarfSeekableStream, &S.self_exe_seekable_stream.stream), | |
| 1031 | @ptrCast(*DwarfSeekableStream, &S.self_exe_mmap_seekable.seekable_stream), | |
| 1020 | 1032 | // TODO https://github.com/ziglang/zig/issues/764 |
| 1021 | @ptrCast(*DwarfInStream, &S.self_exe_in_stream.stream), | |
| 1033 | @ptrCast(*DwarfInStream, &S.self_exe_mmap_seekable.stream), | |
| 1022 | 1034 | ); |
| 1023 | 1035 | } |
| 1024 | 1036 | |
| ... | ... | @@ -1478,16 +1490,14 @@ fn parseFormValueTargetAddrSize(in_stream: var) !u64 { |
| 1478 | 1490 | } |
| 1479 | 1491 | |
| 1480 | 1492 | fn parseFormValueRef(allocator: *mem.Allocator, in_stream: var, size: i32) !FormValue { |
| 1481 | return FormValue{ | |
| 1482 | .Ref = switch (size) { | |
| 1483 | 1 => try in_stream.readIntLittle(u8), | |
| 1484 | 2 => try in_stream.readIntLittle(u16), | |
| 1485 | 4 => try in_stream.readIntLittle(u32), | |
| 1486 | 8 => try in_stream.readIntLittle(u64), | |
| 1487 | -1 => try leb.readULEB128(u64, in_stream), | |
| 1488 | else => unreachable, | |
| 1489 | }, | |
| 1490 | }; | |
| 1493 | return FormValue{ .Ref = switch (size) { | |
| 1494 | 1 => try in_stream.readIntLittle(u8), | |
| 1495 | 2 => try in_stream.readIntLittle(u16), | |
| 1496 | 4 => try in_stream.readIntLittle(u32), | |
| 1497 | 8 => try in_stream.readIntLittle(u64), | |
| 1498 | -1 => try leb.readULEB128(u64, in_stream), | |
| 1499 | else => unreachable, | |
| 1500 | } }; | |
| 1491 | 1501 | } |
| 1492 | 1502 | |
| 1493 | 1503 | fn parseFormValue(allocator: *mem.Allocator, in_stream: var, form_id: u64, is_64: bool) anyerror!FormValue { |
std/io.zig+9-12| ... | ... | @@ -36,6 +36,7 @@ pub fn getStdIn() GetStdIoErrs!File { |
| 36 | 36 | } |
| 37 | 37 | |
| 38 | 38 | pub const SeekableStream = @import("io/seekable_stream.zig").SeekableStream; |
| 39 | pub const SliceSeekableInStream = @import("io/seekable_stream.zig").SliceSeekableInStream; | |
| 39 | 40 | pub const COutStream = @import("io/c_out_stream.zig").COutStream; |
| 40 | 41 | |
| 41 | 42 | pub fn InStream(comptime ReadError: type) type { |
| ... | ... | @@ -1115,12 +1116,10 @@ pub fn Deserializer(comptime endian: builtin.Endian, comptime packing: Packing, |
| 1115 | 1116 | pub const Stream = InStream(Error); |
| 1116 | 1117 | |
| 1117 | 1118 | pub fn init(in_stream: *Stream) Self { |
| 1118 | return Self{ | |
| 1119 | .in_stream = switch (packing) { | |
| 1120 | .Bit => BitInStream(endian, Stream.Error).init(in_stream), | |
| 1121 | .Byte => in_stream, | |
| 1122 | }, | |
| 1123 | }; | |
| 1119 | return Self{ .in_stream = switch (packing) { | |
| 1120 | .Bit => BitInStream(endian, Stream.Error).init(in_stream), | |
| 1121 | .Byte => in_stream, | |
| 1122 | } }; | |
| 1124 | 1123 | } |
| 1125 | 1124 | |
| 1126 | 1125 | pub fn alignToByte(self: *Self) void { |
| ... | ... | @@ -1326,12 +1325,10 @@ pub fn Serializer(comptime endian: builtin.Endian, comptime packing: Packing, co |
| 1326 | 1325 | pub const Stream = OutStream(Error); |
| 1327 | 1326 | |
| 1328 | 1327 | pub fn init(out_stream: *Stream) Self { |
| 1329 | return Self{ | |
| 1330 | .out_stream = switch (packing) { | |
| 1331 | .Bit => BitOutStream(endian, Stream.Error).init(out_stream), | |
| 1332 | .Byte => out_stream, | |
| 1333 | }, | |
| 1334 | }; | |
| 1328 | return Self{ .out_stream = switch (packing) { | |
| 1329 | .Bit => BitOutStream(endian, Stream.Error).init(out_stream), | |
| 1330 | .Byte => out_stream, | |
| 1331 | } }; | |
| 1335 | 1332 | } |
| 1336 | 1333 | |
| 1337 | 1334 | /// Flushes any unwritten bits to the stream |
std/io/seekable_stream.zig+71| ... | ... | @@ -30,3 +30,74 @@ pub fn SeekableStream(comptime SeekErrorType: type, comptime GetSeekPosErrorType |
| 30 | 30 | } |
| 31 | 31 | }; |
| 32 | 32 | } |
| 33 | ||
| 34 | pub const SliceSeekableInStream = struct { | |
| 35 | const Self = @This(); | |
| 36 | pub const Error = error{}; | |
| 37 | pub const SeekError = error{EndOfStream}; | |
| 38 | pub const GetSeekPosError = error{}; | |
| 39 | pub const Stream = InStream(Error); | |
| 40 | pub const SeekableInStream = SeekableStream(SeekError, GetSeekPosError); | |
| 41 | ||
| 42 | pub stream: Stream, | |
| 43 | pub seekable_stream: SeekableInStream, | |
| 44 | ||
| 45 | pos: usize, | |
| 46 | slice: []const u8, | |
| 47 | ||
| 48 | pub fn init(slice: []const u8) Self { | |
| 49 | return Self{ | |
| 50 | .slice = slice, | |
| 51 | .pos = 0, | |
| 52 | .stream = Stream{ .readFn = readFn }, | |
| 53 | .seekable_stream = SeekableInStream{ | |
| 54 | .seekToFn = seekToFn, | |
| 55 | .seekForwardFn = seekForwardFn, | |
| 56 | .getEndPosFn = getEndPosFn, | |
| 57 | .getPosFn = getPosFn, | |
| 58 | }, | |
| 59 | }; | |
| 60 | } | |
| 61 | ||
| 62 | fn readFn(in_stream: *Stream, dest: []u8) Error!usize { | |
| 63 | const self = @fieldParentPtr(Self, "stream", in_stream); | |
| 64 | const size = std.math.min(dest.len, self.slice.len - self.pos); | |
| 65 | const end = self.pos + size; | |
| 66 | ||
| 67 | std.mem.copy(u8, dest[0..size], self.slice[self.pos..end]); | |
| 68 | self.pos = end; | |
| 69 | ||
| 70 | return size; | |
| 71 | } | |
| 72 | ||
| 73 | fn seekToFn(in_stream: *SeekableInStream, pos: u64) SeekError!void { | |
| 74 | const self = @fieldParentPtr(Self, "seekable_stream", in_stream); | |
| 75 | const usize_pos = @intCast(usize, pos); | |
| 76 | if (usize_pos >= self.slice.len) return error.EndOfStream; | |
| 77 | self.pos = usize_pos; | |
| 78 | } | |
| 79 | ||
| 80 | fn seekForwardFn(in_stream: *SeekableInStream, amt: i64) SeekError!void { | |
| 81 | const self = @fieldParentPtr(Self, "seekable_stream", in_stream); | |
| 82 | ||
| 83 | if (amt < 0) { | |
| 84 | const abs_amt = @intCast(usize, -amt); | |
| 85 | if (abs_amt > self.pos) return error.EndOfStream; | |
| 86 | self.pos -= abs_amt; | |
| 87 | } else { | |
| 88 | const usize_amt = @intCast(usize, amt); | |
| 89 | if (self.pos + usize_amt >= self.slice.len) return error.EndOfStream; | |
| 90 | self.pos += usize_amt; | |
| 91 | } | |
| 92 | } | |
| 93 | ||
| 94 | fn getEndPosFn(in_stream: *SeekableInStream) GetSeekPosError!u64 { | |
| 95 | const self = @fieldParentPtr(Self, "seekable_stream", in_stream); | |
| 96 | return @intCast(u64, self.slice.len); | |
| 97 | } | |
| 98 | ||
| 99 | fn getPosFn(in_stream: *SeekableInStream) GetSeekPosError!u64 { | |
| 100 | const self = @fieldParentPtr(Self, "seekable_stream", in_stream); | |
| 101 | return @intCast(u64, self.pos); | |
| 102 | } | |
| 103 | }; |