52
std/coff.zig
52
std/coff.zig
@@ -8,9 +8,9 @@ const ArrayList = std.ArrayList;
|
||||
|
||||
// CoffHeader.machine values
|
||||
// see https://msdn.microsoft.com/en-us/library/windows/desktop/ms680313(v=vs.85).aspx
|
||||
const IMAGE_FILE_MACHINE_I386 = 0x014c;
|
||||
const IMAGE_FILE_MACHINE_IA64 = 0x0200;
|
||||
const IMAGE_FILE_MACHINE_AMD64 = 0x8664;
|
||||
const IMAGE_FILE_MACHINE_I386 = 0x014c;
|
||||
const IMAGE_FILE_MACHINE_IA64 = 0x0200;
|
||||
const IMAGE_FILE_MACHINE_AMD64 = 0x8664;
|
||||
|
||||
// OptionalHeader.magic values
|
||||
// see https://msdn.microsoft.com/en-us/library/windows/desktop/ms680339(v=vs.85).aspx
|
||||
@@ -20,7 +20,7 @@ const IMAGE_NT_OPTIONAL_HDR64_MAGIC = 0x20b;
|
||||
const IMAGE_NUMBEROF_DIRECTORY_ENTRIES = 16;
|
||||
const DEBUG_DIRECTORY = 6;
|
||||
|
||||
pub const CoffError = error {
|
||||
pub const CoffError = error{
|
||||
InvalidPEMagic,
|
||||
InvalidPEHeader,
|
||||
InvalidMachine,
|
||||
@@ -56,24 +56,21 @@ pub const Coff = struct {
|
||||
|
||||
var pe_header_magic: [4]u8 = undefined;
|
||||
try in.readNoEof(pe_header_magic[0..]);
|
||||
if (!mem.eql(u8, pe_header_magic, []u8{'P', 'E', 0, 0}))
|
||||
if (!mem.eql(u8, pe_header_magic, []u8{ 'P', 'E', 0, 0 }))
|
||||
return error.InvalidPEHeader;
|
||||
|
||||
self.coff_header = CoffHeader {
|
||||
self.coff_header = CoffHeader{
|
||||
.machine = try in.readIntLe(u16),
|
||||
.number_of_sections = try in.readIntLe(u16),
|
||||
.timedate_stamp = try in.readIntLe(u32),
|
||||
.pointer_to_symbol_table = try in.readIntLe(u32),
|
||||
.number_of_symbols = try in.readIntLe(u32),
|
||||
.size_of_optional_header = try in.readIntLe(u16),
|
||||
.characteristics = try in.readIntLe(u16),
|
||||
.number_of_sections = try in.readIntLe(u16),
|
||||
.timedate_stamp = try in.readIntLe(u32),
|
||||
.pointer_to_symbol_table = try in.readIntLe(u32),
|
||||
.number_of_symbols = try in.readIntLe(u32),
|
||||
.size_of_optional_header = try in.readIntLe(u16),
|
||||
.characteristics = try in.readIntLe(u16),
|
||||
};
|
||||
|
||||
switch (self.coff_header.machine) {
|
||||
IMAGE_FILE_MACHINE_I386,
|
||||
IMAGE_FILE_MACHINE_AMD64,
|
||||
IMAGE_FILE_MACHINE_IA64
|
||||
=> {},
|
||||
IMAGE_FILE_MACHINE_I386, IMAGE_FILE_MACHINE_AMD64, IMAGE_FILE_MACHINE_IA64 => {},
|
||||
else => return error.InvalidMachine,
|
||||
}
|
||||
|
||||
@@ -89,11 +86,9 @@ pub const Coff = struct {
|
||||
var skip_size: u16 = undefined;
|
||||
if (self.pe_header.magic == IMAGE_NT_OPTIONAL_HDR32_MAGIC) {
|
||||
skip_size = 2 * @sizeOf(u8) + 8 * @sizeOf(u16) + 18 * @sizeOf(u32);
|
||||
}
|
||||
else if (self.pe_header.magic == IMAGE_NT_OPTIONAL_HDR64_MAGIC) {
|
||||
} else if (self.pe_header.magic == IMAGE_NT_OPTIONAL_HDR64_MAGIC) {
|
||||
skip_size = 2 * @sizeOf(u8) + 8 * @sizeOf(u16) + 12 * @sizeOf(u32) + 5 * @sizeOf(u64);
|
||||
}
|
||||
else
|
||||
} else
|
||||
return error.InvalidPEMagic;
|
||||
|
||||
try self.in_file.seekForward(skip_size);
|
||||
@@ -103,7 +98,7 @@ pub const Coff = struct {
|
||||
return error.InvalidPEHeader;
|
||||
|
||||
for (self.pe_header.data_directory) |*data_dir| {
|
||||
data_dir.* = OptionalHeader.DataDirectory {
|
||||
data_dir.* = OptionalHeader.DataDirectory{
|
||||
.virtual_address = try in.readIntLe(u32),
|
||||
.size = try in.readIntLe(u32),
|
||||
};
|
||||
@@ -114,7 +109,7 @@ pub const Coff = struct {
|
||||
try self.loadSections();
|
||||
const header = (self.getSection(".rdata") orelse return error.MissingCoffSection).header;
|
||||
|
||||
// The linker puts a chunk that contains the .pdb path right after the
|
||||
// The linker puts a chunk that contains the .pdb path right after the
|
||||
// debug_directory.
|
||||
const debug_dir = &self.pe_header.data_directory[DEBUG_DIRECTORY];
|
||||
const file_offset = debug_dir.virtual_address - header.virtual_address + header.pointer_to_raw_data;
|
||||
@@ -159,10 +154,10 @@ pub const Coff = struct {
|
||||
var i: u16 = 0;
|
||||
while (i < self.coff_header.number_of_sections) : (i += 1) {
|
||||
try in.readNoEof(name[0..]);
|
||||
try self.sections.append(Section {
|
||||
.header = SectionHeader {
|
||||
try self.sections.append(Section{
|
||||
.header = SectionHeader{
|
||||
.name = name,
|
||||
.misc = SectionHeader.Misc { .physical_address = try in.readIntLe(u32) },
|
||||
.misc = SectionHeader.Misc{ .physical_address = try in.readIntLe(u32) },
|
||||
.virtual_address = try in.readIntLe(u32),
|
||||
.size_of_raw_data = try in.readIntLe(u32),
|
||||
.pointer_to_raw_data = try in.readIntLe(u32),
|
||||
@@ -184,7 +179,6 @@ pub const Coff = struct {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
const CoffHeader = struct {
|
||||
@@ -194,13 +188,13 @@ const CoffHeader = struct {
|
||||
pointer_to_symbol_table: u32,
|
||||
number_of_symbols: u32,
|
||||
size_of_optional_header: u16,
|
||||
characteristics: u16
|
||||
characteristics: u16,
|
||||
};
|
||||
|
||||
const OptionalHeader = struct {
|
||||
const DataDirectory = struct {
|
||||
virtual_address: u32,
|
||||
size: u32
|
||||
size: u32,
|
||||
};
|
||||
|
||||
magic: u16,
|
||||
@@ -214,7 +208,7 @@ pub const Section = struct {
|
||||
const SectionHeader = struct {
|
||||
const Misc = union {
|
||||
physical_address: u32,
|
||||
virtual_size: u32
|
||||
virtual_size: u32,
|
||||
};
|
||||
|
||||
name: [8]u8,
|
||||
|
||||
@@ -115,7 +115,7 @@ pub const X25519 = struct {
|
||||
return !zerocmp(u8, out);
|
||||
}
|
||||
|
||||
pub fn createPublicKey(public_key: [] u8, private_key: []const u8) bool {
|
||||
pub fn createPublicKey(public_key: []u8, private_key: []const u8) bool {
|
||||
var base_point = []u8{9} ++ []u8{0} ** 31;
|
||||
return create(public_key, private_key, base_point);
|
||||
}
|
||||
|
||||
@@ -242,9 +242,12 @@ pub fn writeCurrentStackTrace(out_stream: var, debug_info: *DebugInfo, tty_color
|
||||
}
|
||||
}
|
||||
|
||||
pub fn writeCurrentStackTraceWindows(out_stream: var, debug_info: *DebugInfo,
|
||||
tty_color: bool, start_addr: ?usize) !void
|
||||
{
|
||||
pub fn writeCurrentStackTraceWindows(
|
||||
out_stream: var,
|
||||
debug_info: *DebugInfo,
|
||||
tty_color: bool,
|
||||
start_addr: ?usize,
|
||||
) !void {
|
||||
var addr_buf: [1024]usize = undefined;
|
||||
const casted_len = @intCast(u32, addr_buf.len); // TODO shouldn't need this cast
|
||||
const n = windows.RtlCaptureStackBackTrace(0, casted_len, @ptrCast(**c_void, &addr_buf), null);
|
||||
@@ -391,7 +394,7 @@ fn printSourceAtAddressWindows(di: *DebugInfo, out_stream: var, relocated_addres
|
||||
break :subsections null;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
if (tty_color) {
|
||||
setTtyColor(TtyColor.White);
|
||||
if (opt_line_info) |li| {
|
||||
@@ -438,7 +441,7 @@ fn printSourceAtAddressWindows(di: *DebugInfo, out_stream: var, relocated_addres
|
||||
}
|
||||
}
|
||||
|
||||
const TtyColor = enum{
|
||||
const TtyColor = enum {
|
||||
Red,
|
||||
Green,
|
||||
Cyan,
|
||||
@@ -465,18 +468,16 @@ fn setTtyColor(tty_color: TtyColor) void {
|
||||
// TODO handle errors
|
||||
switch (tty_color) {
|
||||
TtyColor.Red => {
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_RED|windows.FOREGROUND_INTENSITY);
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_RED | windows.FOREGROUND_INTENSITY);
|
||||
},
|
||||
TtyColor.Green => {
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_GREEN|windows.FOREGROUND_INTENSITY);
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_GREEN | windows.FOREGROUND_INTENSITY);
|
||||
},
|
||||
TtyColor.Cyan => {
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle,
|
||||
windows.FOREGROUND_GREEN|windows.FOREGROUND_BLUE|windows.FOREGROUND_INTENSITY);
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_GREEN | windows.FOREGROUND_BLUE | windows.FOREGROUND_INTENSITY);
|
||||
},
|
||||
TtyColor.White, TtyColor.Bold => {
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle,
|
||||
windows.FOREGROUND_RED|windows.FOREGROUND_GREEN|windows.FOREGROUND_BLUE|windows.FOREGROUND_INTENSITY);
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_RED | windows.FOREGROUND_GREEN | windows.FOREGROUND_BLUE | windows.FOREGROUND_INTENSITY);
|
||||
},
|
||||
TtyColor.Dim => {
|
||||
_ = windows.SetConsoleTextAttribute(stderr_file.handle, windows.FOREGROUND_INTENSITY);
|
||||
|
||||
@@ -119,7 +119,7 @@ pub async fn pwriteWindows(loop: *Loop, fd: os.FileHandle, data: []const u8, off
|
||||
},
|
||||
};
|
||||
// TODO only call create io completion port once per fd
|
||||
_ = try os.windowsCreateIoCompletionPort(fd, loop.os_data.io_port, undefined, undefined);
|
||||
_ = windows.CreateIoCompletionPort(fd, loop.os_data.io_port, undefined, undefined);
|
||||
loop.beginOneEvent();
|
||||
errdefer loop.finishOneEvent();
|
||||
|
||||
@@ -251,7 +251,7 @@ pub async fn preadWindows(loop: *Loop, fd: os.FileHandle, data: []u8, offset: u6
|
||||
},
|
||||
};
|
||||
// TODO only call create io completion port once per fd
|
||||
_ = try os.windowsCreateIoCompletionPort(fd, loop.os_data.io_port, undefined, undefined);
|
||||
_ = windows.CreateIoCompletionPort(fd, loop.os_data.io_port, undefined, undefined);
|
||||
loop.beginOneEvent();
|
||||
errdefer loop.finishOneEvent();
|
||||
|
||||
@@ -264,12 +264,13 @@ pub async fn preadWindows(loop: *Loop, fd: os.FileHandle, data: []u8, offset: u6
|
||||
var bytes_transferred: windows.DWORD = undefined;
|
||||
if (windows.GetOverlappedResult(fd, &resume_node.base.overlapped, &bytes_transferred, windows.FALSE) == 0) {
|
||||
const err = windows.GetLastError();
|
||||
return switch (err) {
|
||||
switch (err) {
|
||||
windows.ERROR.IO_PENDING => unreachable,
|
||||
windows.ERROR.OPERATION_ABORTED => error.OperationAborted,
|
||||
windows.ERROR.BROKEN_PIPE => error.BrokenPipe,
|
||||
else => os.unexpectedErrorWindows(err),
|
||||
};
|
||||
windows.ERROR.OPERATION_ABORTED => return error.OperationAborted,
|
||||
windows.ERROR.BROKEN_PIPE => return error.BrokenPipe,
|
||||
windows.ERROR.HANDLE_EOF => return usize(bytes_transferred),
|
||||
else => return os.unexpectedErrorWindows(err),
|
||||
}
|
||||
}
|
||||
return usize(bytes_transferred);
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ pub const Loop = struct {
|
||||
handle: promise,
|
||||
overlapped: Overlapped,
|
||||
|
||||
const overlapped_init = switch (builtin.os) {
|
||||
pub const overlapped_init = switch (builtin.os) {
|
||||
builtin.Os.windows => windows.OVERLAPPED{
|
||||
.Internal = 0,
|
||||
.InternalHigh = 0,
|
||||
@@ -39,7 +39,7 @@ pub const Loop = struct {
|
||||
},
|
||||
else => {},
|
||||
};
|
||||
const Overlapped = @typeOf(overlapped_init);
|
||||
pub const Overlapped = @typeOf(overlapped_init);
|
||||
|
||||
pub const Id = enum {
|
||||
Basic,
|
||||
@@ -415,6 +415,7 @@ pub const Loop = struct {
|
||||
.base = ResumeNode{
|
||||
.id = ResumeNode.Id.Basic,
|
||||
.handle = @handle(),
|
||||
.overlapped = ResumeNode.overlapped_init,
|
||||
},
|
||||
};
|
||||
try self.linuxAddFd(fd, &resume_node.base, flags);
|
||||
@@ -697,11 +698,10 @@ pub const Loop = struct {
|
||||
const overlapped = while (true) {
|
||||
var nbytes: windows.DWORD = undefined;
|
||||
var overlapped: ?*windows.OVERLAPPED = undefined;
|
||||
switch (os.windowsGetQueuedCompletionStatus(self.os_data.io_port, &nbytes, &completion_key,
|
||||
&overlapped, windows.INFINITE))
|
||||
{
|
||||
switch (os.windowsGetQueuedCompletionStatus(self.os_data.io_port, &nbytes, &completion_key, &overlapped, windows.INFINITE)) {
|
||||
os.WindowsWaitResult.Aborted => return,
|
||||
os.WindowsWaitResult.Normal => {},
|
||||
os.WindowsWaitResult.EOF => {},
|
||||
os.WindowsWaitResult.Cancelled => continue,
|
||||
}
|
||||
if (overlapped) |o| break o;
|
||||
|
||||
@@ -32,6 +32,7 @@ pub const Server = struct {
|
||||
.listen_resume_node = event.Loop.ResumeNode{
|
||||
.id = event.Loop.ResumeNode.Id.Basic,
|
||||
.handle = undefined,
|
||||
.overlapped = event.Loop.ResumeNode.overlapped_init,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
@@ -658,8 +658,16 @@ fn windowsCreateProcess(app_name: [*]u16, cmd_line: [*]u16, envp_ptr: ?[*]u16, c
|
||||
// environment variables to programs that were not, which seems unlikely.
|
||||
// More investigation is needed.
|
||||
if (windows.CreateProcessW(
|
||||
app_name, cmd_line, null, null, windows.TRUE, windows.CREATE_UNICODE_ENVIRONMENT,
|
||||
@ptrCast(?*c_void, envp_ptr), cwd_ptr, lpStartupInfo, lpProcessInformation,
|
||||
app_name,
|
||||
cmd_line,
|
||||
null,
|
||||
null,
|
||||
windows.TRUE,
|
||||
windows.CREATE_UNICODE_ENVIRONMENT,
|
||||
@ptrCast(?*c_void, envp_ptr),
|
||||
cwd_ptr,
|
||||
lpStartupInfo,
|
||||
lpProcessInformation,
|
||||
) == 0) {
|
||||
const err = windows.GetLastError();
|
||||
switch (err) {
|
||||
|
||||
@@ -206,7 +206,6 @@ pub const FILE_NOTIFY_CHANGE_DIR_NAME = 2;
|
||||
pub const FILE_NOTIFY_CHANGE_FILE_NAME = 1;
|
||||
pub const FILE_NOTIFY_CHANGE_ATTRIBUTES = 4;
|
||||
|
||||
|
||||
pub const CONSOLE_SCREEN_BUFFER_INFO = extern struct {
|
||||
dwSize: COORD,
|
||||
dwCursorPosition: COORD,
|
||||
|
||||
@@ -223,7 +223,7 @@ pub fn windowsFindFirstFile(
|
||||
dir_path: []const u8,
|
||||
find_file_data: *windows.WIN32_FIND_DATAW,
|
||||
) !windows.HANDLE {
|
||||
const dir_path_w = try sliceToPrefixedSuffixedFileW(dir_path, []u16{'\\', '*', 0});
|
||||
const dir_path_w = try sliceToPrefixedSuffixedFileW(dir_path, []u16{ '\\', '*', 0 });
|
||||
const handle = windows.FindFirstFileW(&dir_path_w, find_file_data);
|
||||
|
||||
if (handle == windows.INVALID_HANDLE_VALUE) {
|
||||
@@ -278,6 +278,7 @@ pub const WindowsWaitResult = enum {
|
||||
Normal,
|
||||
Aborted,
|
||||
Cancelled,
|
||||
EOF,
|
||||
};
|
||||
|
||||
pub fn windowsGetQueuedCompletionStatus(completion_port: windows.HANDLE, bytes_transferred_count: *windows.DWORD, lpCompletionKey: *usize, lpOverlapped: *?*windows.OVERLAPPED, dwMilliseconds: windows.DWORD) WindowsWaitResult {
|
||||
@@ -286,6 +287,7 @@ pub fn windowsGetQueuedCompletionStatus(completion_port: windows.HANDLE, bytes_t
|
||||
switch (err) {
|
||||
windows.ERROR.ABANDONED_WAIT_0 => return WindowsWaitResult.Aborted,
|
||||
windows.ERROR.OPERATION_ABORTED => return WindowsWaitResult.Cancelled,
|
||||
windows.ERROR.HANDLE_EOF => return WindowsWaitResult.EOF,
|
||||
else => {
|
||||
if (std.debug.runtime_safety) {
|
||||
std.debug.panic("unexpected error: {}\n", err);
|
||||
|
||||
157
std/pdb.zig
157
std/pdb.zig
@@ -64,19 +64,35 @@ pub const ModInfo = packed struct {
|
||||
};
|
||||
|
||||
pub const SectionMapHeader = packed struct {
|
||||
Count: u16, /// Number of segment descriptors
|
||||
LogCount: u16, /// Number of logical segment descriptors
|
||||
/// Number of segment descriptors
|
||||
Count: u16,
|
||||
|
||||
/// Number of logical segment descriptors
|
||||
LogCount: u16,
|
||||
};
|
||||
|
||||
pub const SectionMapEntry = packed struct {
|
||||
Flags: u16 , /// See the SectionMapEntryFlags enum below.
|
||||
Ovl: u16 , /// Logical overlay number
|
||||
Group: u16 , /// Group index into descriptor array.
|
||||
Frame: u16 ,
|
||||
SectionName: u16 , /// Byte index of segment / group name in string table, or 0xFFFF.
|
||||
ClassName: u16 , /// Byte index of class in string table, or 0xFFFF.
|
||||
Offset: u32 , /// Byte offset of the logical segment within physical segment. If group is set in flags, this is the offset of the group.
|
||||
SectionLength: u32 , /// Byte count of the segment or group.
|
||||
/// See the SectionMapEntryFlags enum below.
|
||||
Flags: u16,
|
||||
|
||||
/// Logical overlay number
|
||||
Ovl: u16,
|
||||
|
||||
/// Group index into descriptor array.
|
||||
Group: u16,
|
||||
Frame: u16,
|
||||
|
||||
/// Byte index of segment / group name in string table, or 0xFFFF.
|
||||
SectionName: u16,
|
||||
|
||||
/// Byte index of class in string table, or 0xFFFF.
|
||||
ClassName: u16,
|
||||
|
||||
/// Byte offset of the logical segment within physical segment. If group is set in flags, this is the offset of the group.
|
||||
Offset: u32,
|
||||
|
||||
/// Byte count of the segment or group.
|
||||
SectionLength: u32,
|
||||
};
|
||||
|
||||
pub const StreamType = enum(u16) {
|
||||
@@ -290,13 +306,13 @@ pub const SymbolKind = packed enum(u16) {
|
||||
pub const TypeIndex = u32;
|
||||
|
||||
pub const ProcSym = packed struct {
|
||||
Parent: u32 ,
|
||||
End: u32 ,
|
||||
Next: u32 ,
|
||||
CodeSize: u32 ,
|
||||
DbgStart: u32 ,
|
||||
DbgEnd: u32 ,
|
||||
FunctionType: TypeIndex ,
|
||||
Parent: u32,
|
||||
End: u32,
|
||||
Next: u32,
|
||||
CodeSize: u32,
|
||||
DbgStart: u32,
|
||||
DbgEnd: u32,
|
||||
FunctionType: TypeIndex,
|
||||
CodeOffset: u32,
|
||||
Segment: u16,
|
||||
Flags: ProcSymFlags,
|
||||
@@ -315,25 +331,34 @@ pub const ProcSymFlags = packed struct {
|
||||
HasOptimizedDebugInfo: bool,
|
||||
};
|
||||
|
||||
pub const SectionContrSubstreamVersion = enum(u32) {
|
||||
Ver60 = 0xeffe0000 + 19970605,
|
||||
V2 = 0xeffe0000 + 20140516
|
||||
pub const SectionContrSubstreamVersion = enum(u32) {
|
||||
Ver60 = 0xeffe0000 + 19970605,
|
||||
V2 = 0xeffe0000 + 20140516,
|
||||
};
|
||||
|
||||
pub const RecordPrefix = packed struct {
|
||||
RecordLen: u16, /// Record length, starting from &RecordKind.
|
||||
RecordKind: SymbolKind, /// Record kind enum (SymRecordKind or TypeRecordKind)
|
||||
/// Record length, starting from &RecordKind.
|
||||
RecordLen: u16,
|
||||
|
||||
/// Record kind enum (SymRecordKind or TypeRecordKind)
|
||||
RecordKind: SymbolKind,
|
||||
};
|
||||
|
||||
pub const LineFragmentHeader = packed struct {
|
||||
RelocOffset: u32, /// Code offset of line contribution.
|
||||
RelocSegment: u16, /// Code segment of line contribution.
|
||||
/// Code offset of line contribution.
|
||||
RelocOffset: u32,
|
||||
|
||||
/// Code segment of line contribution.
|
||||
RelocSegment: u16,
|
||||
Flags: LineFlags,
|
||||
CodeSize: u32, /// Code size of this line contribution.
|
||||
|
||||
/// Code size of this line contribution.
|
||||
CodeSize: u32,
|
||||
};
|
||||
|
||||
pub const LineFlags = packed struct {
|
||||
LF_HaveColumns: bool, /// CV_LINES_HAVE_COLUMNS
|
||||
/// CV_LINES_HAVE_COLUMNS
|
||||
LF_HaveColumns: bool,
|
||||
unused: u15,
|
||||
};
|
||||
|
||||
@@ -348,12 +373,14 @@ pub const LineBlockFragmentHeader = packed struct {
|
||||
/// table of the actual name.
|
||||
NameIndex: u32,
|
||||
NumLines: u32,
|
||||
BlockSize: u32, /// code size of block, in bytes
|
||||
|
||||
/// code size of block, in bytes
|
||||
BlockSize: u32,
|
||||
};
|
||||
|
||||
|
||||
pub const LineNumberEntry = packed struct {
|
||||
Offset: u32, /// Offset to start of code bytes for line number
|
||||
/// Offset to start of code bytes for line number
|
||||
Offset: u32,
|
||||
Flags: u32,
|
||||
|
||||
/// TODO runtime crash when I make the actual type of Flags this
|
||||
@@ -371,42 +398,53 @@ pub const ColumnNumberEntry = packed struct {
|
||||
|
||||
/// Checksum bytes follow.
|
||||
pub const FileChecksumEntryHeader = packed struct {
|
||||
FileNameOffset: u32, /// Byte offset of filename in global string table.
|
||||
ChecksumSize: u8, /// Number of bytes of checksum.
|
||||
ChecksumKind: u8, /// FileChecksumKind
|
||||
/// Byte offset of filename in global string table.
|
||||
FileNameOffset: u32,
|
||||
|
||||
/// Number of bytes of checksum.
|
||||
ChecksumSize: u8,
|
||||
|
||||
/// FileChecksumKind
|
||||
ChecksumKind: u8,
|
||||
};
|
||||
|
||||
pub const DebugSubsectionKind = packed enum(u32) {
|
||||
None = 0,
|
||||
Symbols = 0xf1,
|
||||
Lines = 0xf2,
|
||||
StringTable = 0xf3,
|
||||
FileChecksums = 0xf4,
|
||||
FrameData = 0xf5,
|
||||
InlineeLines = 0xf6,
|
||||
CrossScopeImports = 0xf7,
|
||||
CrossScopeExports = 0xf8,
|
||||
None = 0,
|
||||
Symbols = 0xf1,
|
||||
Lines = 0xf2,
|
||||
StringTable = 0xf3,
|
||||
FileChecksums = 0xf4,
|
||||
FrameData = 0xf5,
|
||||
InlineeLines = 0xf6,
|
||||
CrossScopeImports = 0xf7,
|
||||
CrossScopeExports = 0xf8,
|
||||
|
||||
// These appear to relate to .Net assembly info.
|
||||
ILLines = 0xf9,
|
||||
FuncMDTokenMap = 0xfa,
|
||||
TypeMDTokenMap = 0xfb,
|
||||
MergedAssemblyInput = 0xfc,
|
||||
// These appear to relate to .Net assembly info.
|
||||
ILLines = 0xf9,
|
||||
FuncMDTokenMap = 0xfa,
|
||||
TypeMDTokenMap = 0xfb,
|
||||
MergedAssemblyInput = 0xfc,
|
||||
|
||||
CoffSymbolRVA = 0xfd,
|
||||
CoffSymbolRVA = 0xfd,
|
||||
};
|
||||
|
||||
|
||||
pub const DebugSubsectionHeader = packed struct {
|
||||
Kind: DebugSubsectionKind, /// codeview::DebugSubsectionKind enum
|
||||
Length: u32, /// number of bytes occupied by this record.
|
||||
/// codeview::DebugSubsectionKind enum
|
||||
Kind: DebugSubsectionKind,
|
||||
|
||||
/// number of bytes occupied by this record.
|
||||
Length: u32,
|
||||
};
|
||||
|
||||
|
||||
pub const PDBStringTableHeader = packed struct {
|
||||
Signature: u32, /// PDBStringTableSignature
|
||||
HashVersion: u32, /// 1 or 2
|
||||
ByteSize: u32, /// Number of bytes of names buffer.
|
||||
/// PDBStringTableSignature
|
||||
Signature: u32,
|
||||
|
||||
/// 1 or 2
|
||||
HashVersion: u32,
|
||||
|
||||
/// Number of bytes of names buffer.
|
||||
ByteSize: u32,
|
||||
};
|
||||
|
||||
pub const Pdb = struct {
|
||||
@@ -456,7 +494,7 @@ const Msf = struct {
|
||||
switch (superblock.BlockSize) {
|
||||
// llvm only supports 4096 but we can handle any of these values
|
||||
512, 1024, 2048, 4096 => {},
|
||||
else => return error.InvalidDebugInfo
|
||||
else => return error.InvalidDebugInfo,
|
||||
}
|
||||
|
||||
if (superblock.NumBlocks * superblock.BlockSize != try file.getEndPos())
|
||||
@@ -536,7 +574,6 @@ const SuperBlock = packed struct {
|
||||
/// The number of ulittle32_t’s in this array is given by
|
||||
/// ceil(NumDirectoryBytes / BlockSize).
|
||||
BlockMapAddr: u32,
|
||||
|
||||
};
|
||||
|
||||
const MsfStream = struct {
|
||||
@@ -552,14 +589,12 @@ const MsfStream = struct {
|
||||
pub const Stream = io.InStream(Error);
|
||||
|
||||
fn init(block_size: u32, block_count: u32, pos: usize, file: os.File, allocator: *mem.Allocator) !MsfStream {
|
||||
var stream = MsfStream {
|
||||
var stream = MsfStream{
|
||||
.in_file = file,
|
||||
.pos = 0,
|
||||
.blocks = try allocator.alloc(u32, block_count),
|
||||
.block_size = block_size,
|
||||
.stream = Stream {
|
||||
.readFn = readFn,
|
||||
},
|
||||
.stream = Stream{ .readFn = readFn },
|
||||
};
|
||||
|
||||
var file_stream = io.FileInStream.init(file);
|
||||
@@ -597,7 +632,7 @@ const MsfStream = struct {
|
||||
|
||||
var size: usize = 0;
|
||||
for (buffer) |*byte| {
|
||||
byte.* = try in.readByte();
|
||||
byte.* = try in.readByte();
|
||||
|
||||
offset += 1;
|
||||
size += 1;
|
||||
|
||||
Reference in New Issue
Block a user