| ... | @@ -75,6 +75,7 @@ bss_section_index: ?u16 = null, | ... | @@ -75,6 +75,7 @@ bss_section_index: ?u16 = null, |
| 75 | | 75 | |
| 76 | globals: std.StringArrayHashMapUnmanaged(Symbol) = .{}, | 76 | globals: std.StringArrayHashMapUnmanaged(Symbol) = .{}, |
| 77 | undefs: std.StringArrayHashMapUnmanaged(Symbol) = .{}, | 77 | undefs: std.StringArrayHashMapUnmanaged(Symbol) = .{}, |
| | 78 | externs: std.StringArrayHashMapUnmanaged(Symbol) = .{}, |
| 78 | strtab: std.ArrayListUnmanaged(u8) = .{}, | 79 | strtab: std.ArrayListUnmanaged(u8) = .{}, |
| 79 | | 80 | |
| 80 | // locals: std.StringArrayHashMapUnmanaged(std.ArrayListUnmanaged(Symbol)) = .{}, | 81 | // locals: std.StringArrayHashMapUnmanaged(std.ArrayListUnmanaged(Symbol)) = .{}, |
| ... | @@ -223,6 +224,11 @@ pub fn deinit(self: *Zld) void { | ... | @@ -223,6 +224,11 @@ pub fn deinit(self: *Zld) void { |
| 223 | self.allocator.free(entry.key); | 224 | self.allocator.free(entry.key); |
| 224 | } | 225 | } |
| 225 | self.undefs.deinit(self.allocator); | 226 | self.undefs.deinit(self.allocator); |
| | 227 | |
| | 228 | for (self.externs.items()) |*entry| { |
| | 229 | self.allocator.free(entry.key); |
| | 230 | } |
| | 231 | self.externs.deinit(self.allocator); |
| 226 | } | 232 | } |
| 227 | | 233 | |
| 228 | pub fn closeFiles(self: Zld) void { | 234 | pub fn closeFiles(self: Zld) void { |
| ... | @@ -1215,7 +1221,11 @@ fn resolveSymbolsInObject(self: *Zld, object_id: u16) !void { | ... | @@ -1215,7 +1221,11 @@ fn resolveSymbolsInObject(self: *Zld, object_id: u16) !void { |
| 1215 | .file = object_id, | 1221 | .file = object_id, |
| 1216 | .index = @intCast(u32, sym_id), | 1222 | .index = @intCast(u32, sym_id), |
| 1217 | }); | 1223 | }); |
| 1218 | _ = self.undefs.swapRemove(sym_name); | 1224 | |
| | 1225 | if (self.undefs.swapRemove(sym_name)) |undef| { |
| | 1226 | self.allocator.free(undef.key); |
| | 1227 | } |
| | 1228 | |
| 1219 | continue; | 1229 | continue; |
| 1220 | }; | 1230 | }; |
| 1221 | | 1231 | |
| ... | @@ -1252,6 +1262,7 @@ fn resolveSymbols(self: *Zld) !void { | ... | @@ -1252,6 +1262,7 @@ fn resolveSymbols(self: *Zld) !void { |
| 1252 | try self.resolveSymbolsInObject(@intCast(u16, object_id)); | 1262 | try self.resolveSymbolsInObject(@intCast(u16, object_id)); |
| 1253 | } | 1263 | } |
| 1254 | | 1264 | |
| | 1265 | // Second pass, resolve symbols in static libraries. |
| 1255 | var next: usize = 0; | 1266 | var next: usize = 0; |
| 1256 | while (true) { | 1267 | while (true) { |
| 1257 | var archive = &self.archives.items[next]; | 1268 | var archive = &self.archives.items[next]; |
| ... | @@ -1285,6 +1296,26 @@ fn resolveSymbols(self: *Zld) !void { | ... | @@ -1285,6 +1296,26 @@ fn resolveSymbols(self: *Zld) !void { |
| 1285 | archive = &self.archives.items[next]; | 1296 | archive = &self.archives.items[next]; |
| 1286 | } | 1297 | } |
| 1287 | } | 1298 | } |
| | 1299 | |
| | 1300 | // Third pass, resolve symbols in dynamic libraries. |
| | 1301 | // TODO Implement libSystem as a hard-coded library, or ship with |
| | 1302 | // a libSystem.B.tbd definition file? |
| | 1303 | while (self.undefs.items().len > 0) { |
| | 1304 | const entry = self.undefs.pop(); |
| | 1305 | try self.externs.putNoClobber(self.allocator, entry.key, .{ |
| | 1306 | .inner = entry.value.inner, |
| | 1307 | .file = 0, |
| | 1308 | }); |
| | 1309 | } |
| | 1310 | |
| | 1311 | // If there are any undefs left, flag an error. |
| | 1312 | if (self.undefs.items().len > 0) { |
| | 1313 | for (self.undefs.items()) |entry| { |
| | 1314 | log.err("undefined reference to symbol '{s}'", .{entry.key}); |
| | 1315 | } |
| | 1316 | |
| | 1317 | return error.UndefinedSymbolReference; |
| | 1318 | } |
| 1288 | } | 1319 | } |
| 1289 | | 1320 | |
| 1290 | fn doRelocs(self: *Zld) !void { | 1321 | fn doRelocs(self: *Zld) !void { |
| ... | @@ -3203,6 +3234,11 @@ fn printSymtab(self: Zld) void { | ... | @@ -3203,6 +3234,11 @@ fn printSymtab(self: Zld) void { |
| 3203 | log.warn(" | {s} => {any}", .{ entry.key, entry.value }); | 3234 | log.warn(" | {s} => {any}", .{ entry.key, entry.value }); |
| 3204 | } | 3235 | } |
| 3205 | | 3236 | |
| | 3237 | log.warn("externs", .{}); |
| | 3238 | for (self.externs.items()) |entry| { |
| | 3239 | log.warn(" | {s} => {any}", .{ entry.key, entry.value }); |
| | 3240 | } |
| | 3241 | |
| 3206 | log.warn("undefs", .{}); | 3242 | log.warn("undefs", .{}); |
| 3207 | for (self.undefs.items()) |entry| { | 3243 | for (self.undefs.items()) |entry| { |
| 3208 | log.warn(" | {s} => {any}", .{ entry.key, entry.value }); | 3244 | log.warn(" | {s} => {any}", .{ entry.key, entry.value }); |