| author | |
| committer | |
| log | 241180216f92c86f833910d73e1c86f54ae940e4 |
| tree | dbbf933551c394f573be87bf814dc68906bab765 |
| parent | c9f929a18b705451e9c2c81f01019575de8bf5fd |
Rather than finding the original object file, we seekTo to the
object file's position within the archive file, and from there open
a new file handle. This file handle is passed to the `Object` parser
which will create the object.2 files changed, 12 insertions(+), 10 deletions(-)
src/link/Wasm/Archive.zig+8-7| ... | @@ -181,6 +181,8 @@ pub fn parseObject(self: Archive, allocator: Allocator, file_offset: u32) !Objec | ... | @@ -181,6 +181,8 @@ pub fn parseObject(self: Archive, allocator: Allocator, file_offset: u32) !Objec |
| 181 | try self.file.seekTo(file_offset); | 181 | try self.file.seekTo(file_offset); |
| 182 | const reader = self.file.reader(); | 182 | const reader = self.file.reader(); |
| 183 | const header = try reader.readStruct(ar_hdr); | 183 | const header = try reader.readStruct(ar_hdr); |
| 184 | const current_offset = try self.file.getPos(); | ||
| 185 | try self.file.seekTo(0); | ||
| 184 | 186 | ||
| 185 | if (!mem.eql(u8, &header.ar_fmag, ARFMAG)) { | 187 | if (!mem.eql(u8, &header.ar_fmag, ARFMAG)) { |
| 186 | log.err("invalid header delimiter: expected '{s}', found '{s}'", .{ ARFMAG, header.ar_fmag }); | 188 | log.err("invalid header delimiter: expected '{s}', found '{s}'", .{ ARFMAG, header.ar_fmag }); |
| ... | @@ -191,16 +193,15 @@ pub fn parseObject(self: Archive, allocator: Allocator, file_offset: u32) !Objec | ... | @@ -191,16 +193,15 @@ pub fn parseObject(self: Archive, allocator: Allocator, file_offset: u32) !Objec |
| 191 | defer allocator.free(object_name); | 193 | defer allocator.free(object_name); |
| 192 | 194 | ||
| 193 | const name = name: { | 195 | const name = name: { |
| 194 | if (object_name.len == 0) { | 196 | var buffer: [std.fs.MAX_PATH_BYTES]u8 = undefined; |
| 195 | break :name try std.fmt.allocPrint(allocator, "{s}.o", .{self.name}); | 197 | const path = try std.os.realpath(self.name, &buffer); |
| 196 | } | 198 | break :name try std.fmt.allocPrint(allocator, "{s}({s})", .{ path, object_name }); |
| 197 | const base_path = std.fs.path.dirname(self.name); | ||
| 198 | break :name try std.fmt.allocPrint(allocator, "{s}/{s}.o", .{ base_path, object_name }); | ||
| 199 | }; | 199 | }; |
| 200 | defer allocator.free(name); | ||
| 200 | 201 | ||
| 201 | log.debug(" parsing object file '{s}' from archive\n", .{name}); | 202 | const object_file = try std.fs.cwd().openFile(self.name, .{}); |
| 202 | const object_file = try std.fs.cwd().openFile(name, .{}); | ||
| 203 | errdefer object_file.close(); | 203 | errdefer object_file.close(); |
| 204 | 204 | ||
| 205 | try object_file.seekTo(current_offset); | ||
| 205 | return Object.create(allocator, object_file, name); | 206 | return Object.create(allocator, object_file, name); |
| 206 | } | 207 | } |
src/link/Wasm/Object.zig+4-3| ... | @@ -68,7 +68,7 @@ string_table: Wasm.StringTable = .{}, | ... | @@ -68,7 +68,7 @@ string_table: Wasm.StringTable = .{}, |
| 68 | const RelocatableData = struct { | 68 | const RelocatableData = struct { |
| 69 | /// The type of the relocatable data | 69 | /// The type of the relocatable data |
| 70 | type: enum { data, code, custom }, | 70 | type: enum { data, code, custom }, |
| 71 | /// Pointer to the data of the segment, where it's length is written to `size` | 71 | /// Pointer to the data of the segment, where its length is written to `size` |
| 72 | data: [*]u8, | 72 | data: [*]u8, |
| 73 | /// The size in bytes of the data representing the segment within the section | 73 | /// The size in bytes of the data representing the segment within the section |
| 74 | size: u32, | 74 | size: u32, |
| ... | @@ -105,10 +105,10 @@ pub const InitError = error{NotObjectFile} || ParseError || std.fs.File.ReadErro | ... | @@ -105,10 +105,10 @@ pub const InitError = error{NotObjectFile} || ParseError || std.fs.File.ReadErro |
| 105 | 105 | ||
| 106 | /// Initializes a new `Object` from a wasm object file. | 106 | /// Initializes a new `Object` from a wasm object file. |
| 107 | /// This also parses and verifies the object file. | 107 | /// This also parses and verifies the object file. |
| 108 | pub fn create(gpa: Allocator, file: std.fs.File, path: []const u8) InitError!Object { | 108 | pub fn create(gpa: Allocator, file: std.fs.File, name: []const u8) InitError!Object { |
| 109 | var object: Object = .{ | 109 | var object: Object = .{ |
| 110 | .file = file, | 110 | .file = file, |
| 111 | .name = path, | 111 | .name = try gpa.dupe(u8, name), |
| 112 | }; | 112 | }; |
| 113 | 113 | ||
| 114 | var is_object_file: bool = false; | 114 | var is_object_file: bool = false; |
| ... | @@ -154,6 +154,7 @@ pub fn deinit(self: *Object, gpa: Allocator) void { | ... | @@ -154,6 +154,7 @@ pub fn deinit(self: *Object, gpa: Allocator) void { |
| 154 | } | 154 | } |
| 155 | gpa.free(self.relocatable_data); | 155 | gpa.free(self.relocatable_data); |
| 156 | self.string_table.deinit(gpa); | 156 | self.string_table.deinit(gpa); |
| 157 | gpa.free(self.name); | ||
| 157 | self.* = undefined; | 158 | self.* = undefined; |
| 158 | } | 159 | } |
| 159 | 160 |