aboutsummaryrefslogtreecommitdiff
path: root/src/link/Coff
diff options
context:
space:
mode:
authorJakub Konka <kubkon@jakubkonka.com>2023-04-26 13:04:24 +0200
committerJacob Young <jacobly0@users.noreply.github.com>2023-04-26 19:08:38 -0400
commitf56054d129d19a006ff19c56b48bc9c7d9c04593 (patch)
treeaa2880b4c127a39563232b7db8c851d13def8596 /src/link/Coff
parentbc69d5a00fb197a7bafc716b84c8675382074c19 (diff)
downloadzig-f56054d129d19a006ff19c56b48bc9c7d9c04593.tar.gz
zig-f56054d129d19a006ff19c56b48bc9c7d9c04593.zip
coff: invalidate GOT relocs after segment shift in memory
Diffstat (limited to 'src/link/Coff')
-rw-r--r--src/link/Coff/Relocation.zig30
1 files changed, 18 insertions, 12 deletions
diff --git a/src/link/Coff/Relocation.zig b/src/link/Coff/Relocation.zig
index 4449691ac0..10d4eed92b 100644
--- a/src/link/Coff/Relocation.zig
+++ b/src/link/Coff/Relocation.zig
@@ -45,6 +45,19 @@ pcrel: bool,
length: u2,
dirty: bool = true,
+/// Returns true if and only if the reloc can be resolved.
+pub fn isResolvable(self: Relocation, coff_file: *Coff) bool {
+ _ = self.getTargetAddress(coff_file) orelse return false;
+ return true;
+}
+
+pub fn isGotIndirection(self: Relocation) bool {
+ return switch (self.type) {
+ .got, .got_page, .got_pageoff => true,
+ else => false,
+ };
+}
+
/// Returns address of the target if any.
pub fn getTargetAddress(self: Relocation, coff_file: *const Coff) ?u32 {
switch (self.type) {
@@ -53,11 +66,6 @@ pub fn getTargetAddress(self: Relocation, coff_file: *const Coff) ?u32 {
const header = coff_file.sections.items(.header)[coff_file.got_section_index.?];
return header.virtual_address + got_index * coff_file.ptr_width.size();
},
- .direct, .page, .pageoff => {
- const target_atom_index = coff_file.getAtomIndexForSymbol(self.target) orelse return null;
- const target_atom = coff_file.getAtom(target_atom_index);
- return target_atom.getSymbol(coff_file).value;
- },
.import, .import_page, .import_pageoff => {
const sym = coff_file.getSymbol(self.target);
const index = coff_file.import_tables.getIndex(sym.value) orelse return null;
@@ -68,16 +76,14 @@ pub fn getTargetAddress(self: Relocation, coff_file: *const Coff) ?u32 {
.name_off = sym.value,
});
},
+ else => {
+ const target_atom_index = coff_file.getAtomIndexForSymbol(self.target) orelse return null;
+ const target_atom = coff_file.getAtom(target_atom_index);
+ return target_atom.getSymbol(coff_file).value;
+ },
}
}
-/// Returns true if and only if the reloc is dirty AND the target address is available.
-pub fn isResolvable(self: Relocation, coff_file: *Coff) bool {
- const addr = self.getTargetAddress(coff_file) orelse return false;
- if (addr == 0) return false;
- return self.dirty;
-}
-
pub fn resolve(self: Relocation, atom_index: Atom.Index, code: []u8, image_base: u64, coff_file: *Coff) void {
const atom = coff_file.getAtom(atom_index);
const source_sym = atom.getSymbol(coff_file);