-
Notifications
You must be signed in to change notification settings - Fork 274
Open
Labels
Effort: LowIssues require < 1 week of workIssues require < 1 week of workImpact: MediumIssue is impactful with a bad, or no, workaroundIssue is impactful with a bad, or no, workaround
Description
- Open
thunder rush points valuably - Go to
0x4f062d - Observe zeroed out call to
_invalid_parameter_noinfo_noreturn - Relocation information:
>>> bv.relocations_at(0x4f062d + 1)[0]
<Relocation: "_invalid_parameter_noinfo_noreturn" @ 0x60fd00>Putting this as a bug because IIRC the relocations should be filled in for COFF.
binaryninja-api/arch/x86/arch_x86.cpp
Lines 4600 to 4777 in 3eda43f
| class CoffRelocationHandler: public RelocationHandler | |
| { | |
| public: | |
| virtual bool ApplyRelocation(Ref<BinaryView> view, Ref<Architecture> arch, Ref<Relocation> reloc, uint8_t* dest, size_t len) override | |
| { | |
| // Note: info.base contains preferred base address and the base where the image is actually loaded | |
| (void)view; | |
| (void)arch; | |
| uint64_t* data64 = (uint64_t*)dest; | |
| uint32_t* data32 = (uint32_t*)dest; | |
| uint16_t* data16 = (uint16_t*)dest; | |
| auto info = reloc->GetInfo(); | |
| if (len < info.size) | |
| return false; | |
| uint64_t offset = 0; | |
| if (info.pcRelative) | |
| { | |
| int64_t relative_offset = info.target - info.address; | |
| offset = (uint64_t) relative_offset; | |
| } | |
| else | |
| offset = info.target; | |
| if (! info.implicitAddend && info.addend) | |
| offset += info.addend; | |
| if (! info.baseRelative) | |
| offset -= info.base; | |
| switch (info.nativeType) | |
| { | |
| // case PE_IMAGE_REL_I386_SECTION: | |
| case PE_IMAGE_REL_AMD64_SECTION: | |
| // TODO: test this implementation, but for now, just don't warn about it | |
| data16[0] = info.sectionIndex + 1; | |
| break; | |
| // case PE_IMAGE_REL_I386_SECREL: | |
| case PE_IMAGE_REL_AMD64_SECREL: | |
| { | |
| // TODO: test this implementation, but for now, just don't warn about it | |
| auto sections = view->GetSectionsAt(info.target); | |
| if (sections.size() > 0) | |
| { | |
| data32[0] = info.target - sections[0]->GetStart(); | |
| } | |
| break; | |
| } | |
| default: | |
| if (info.size == 8) | |
| { | |
| // LogDebug("%s: address: %#" PRIx64 " target: %#" PRIx64 " base: %#" PRIx64 " offset: %#" PRIx64 " current: %#" PRIx64 " result: %#" PRIx64 "", __func__, info.address, info.target, info.base, offset, data64[0], data64[0] + offset); | |
| data64[0] += offset; | |
| } | |
| else if (info.size == 4) | |
| { | |
| // LogDebug("%s: address: %#" PRIx64 " target: %#" PRIx64 " base: %#" PRIx64 " offset: %#" PRIx32 " %+" PRId32 " current: %#" PRIx32 " result: %#" PRIx32 "", __func__, info.address, info.target, info.base, (uint32_t)offset, (uint32_t)offset, data32[0], data32[0] + (uint32_t)offset); | |
| data32[0] += (uint32_t)offset; | |
| } | |
| } | |
| return true; | |
| } | |
| virtual bool GetRelocationInfo(Ref<BinaryView> view, Ref<Architecture> arch, vector<BNRelocationInfo>& result) override | |
| { | |
| (void)arch; | |
| Ref<Logger> logger = view->CreateLogger("X86CoffReloc"); | |
| set<uint64_t> relocTypes; | |
| for (auto& reloc : result) | |
| { | |
| if (arch->GetName() == "x86_64") | |
| { | |
| switch (reloc.nativeType) | |
| { | |
| case PE_IMAGE_REL_AMD64_ABSOLUTE: | |
| reloc.type = IgnoredRelocation; | |
| break; | |
| case PE_IMAGE_REL_AMD64_ADDR64: | |
| reloc.baseRelative = true; | |
| reloc.size = 8; | |
| break; | |
| case PE_IMAGE_REL_AMD64_ADDR32NB: | |
| reloc.baseRelative = false; | |
| reloc.size = 4; | |
| break; | |
| case PE_IMAGE_REL_AMD64_ADDR32: | |
| reloc.baseRelative = true; | |
| reloc.size = 4; | |
| break; | |
| case PE_IMAGE_REL_AMD64_REL32_5: | |
| case PE_IMAGE_REL_AMD64_REL32_4: | |
| case PE_IMAGE_REL_AMD64_REL32_3: | |
| case PE_IMAGE_REL_AMD64_REL32_2: | |
| case PE_IMAGE_REL_AMD64_REL32_1: | |
| // LogDebug("%s: %#" PRIx64 "(%#" PRIx64 ")->%#" PRIx64 " %s addend: %ld", __func__, reloc.address, reloc.target, reloc.address - reloc.target, GetRelocationString((COFFx64RelocationType)reloc.nativeType), (long) reloc.addend); | |
| case PE_IMAGE_REL_AMD64_REL32: | |
| // TODO: treat reloc.addend as offset of target from its section (see llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h:67) | |
| reloc.addend = -(4 + (reloc.nativeType - PE_IMAGE_REL_AMD64_REL32)); | |
| reloc.baseRelative = false; | |
| reloc.pcRelative = true; | |
| reloc.size = 4; | |
| break; | |
| case PE_IMAGE_REL_AMD64_SECTION: | |
| // The 16-bit section index of the section that contains the target. This is used to support debugging information. | |
| reloc.baseRelative = false; | |
| reloc.size = 2; | |
| reloc.addend = 0; | |
| case PE_IMAGE_REL_AMD64_SECREL: | |
| // TODO: implement these, but for now, just don't warn about them | |
| // The 32-bit offset of the target from the beginning of its section. This is used to support debugging information and static thread local storage. reloc.baseRelative = false; | |
| reloc.baseRelative = false; | |
| reloc.size = 4; | |
| reloc.addend = 0; | |
| break; | |
| case PE_IMAGE_REL_AMD64_SECREL7: | |
| // 7-bit offset from the base of the section that contains the target | |
| case PE_IMAGE_REL_AMD64_TOKEN: | |
| case PE_IMAGE_REL_AMD64_SREL32: | |
| case PE_IMAGE_REL_AMD64_PAIR: | |
| case PE_IMAGE_REL_AMD64_SSPAN32: | |
| default: | |
| // By default, PE relocations are correct when not rebased. | |
| // Upon rebasing, support would need to be added to correctly process the relocation | |
| reloc.type = UnhandledRelocation; | |
| relocTypes.insert(reloc.nativeType); | |
| } | |
| for (auto& reloc : relocTypes) | |
| logger->LogWarn("Unsupported COFF relocation: %s", GetRelocationString((COFFx64RelocationType)reloc)); | |
| } | |
| else if (arch->GetName() == "x86") | |
| { | |
| switch (reloc.nativeType) | |
| { | |
| case PE_IMAGE_REL_I386_ABSOLUTE: | |
| reloc.type = IgnoredRelocation; | |
| break; | |
| case PE_IMAGE_REL_I386_REL32: | |
| reloc.baseRelative = false; | |
| reloc.pcRelative = true; | |
| reloc.size = 4; | |
| reloc.addend = -4; | |
| break; | |
| case PE_IMAGE_REL_I386_DIR32NB: | |
| reloc.baseRelative = false; | |
| reloc.size = 4; | |
| break; | |
| case PE_IMAGE_REL_I386_DIR32: | |
| reloc.baseRelative = true; | |
| reloc.size = 4; | |
| break; | |
| case PE_IMAGE_REL_I386_SECTION: | |
| // The 16-bit section index of the section that contains the target. This is used to support debugging information. | |
| reloc.baseRelative = false; | |
| reloc.size = 2; | |
| reloc.addend = 0; | |
| case PE_IMAGE_REL_I386_SECREL: | |
| // The 32-bit offset of the target from the beginning of its section. This is used to support debugging information and static thread local storage. reloc.baseRelative = false; | |
| reloc.baseRelative = false; | |
| reloc.size = 4; | |
| reloc.addend = 0; | |
| break; | |
| case PE_IMAGE_REL_I386_SEG12: | |
| case PE_IMAGE_REL_I386_TOKEN: | |
| case PE_IMAGE_REL_I386_SECREL7: | |
| case PE_IMAGE_REL_I386_DIR16: | |
| case PE_IMAGE_REL_I386_REL16: | |
| default: | |
| reloc.type = UnhandledRelocation; | |
| relocTypes.insert(reloc.nativeType); | |
| } | |
| for (auto& reloc : relocTypes) | |
| logger->LogWarn("Unsupported COFF relocation: %s", GetRelocationString((COFFx86RelocationType)reloc)); | |
| } | |
| } | |
| return true; | |
| } | |
| }; |
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
Effort: LowIssues require < 1 week of workIssues require < 1 week of workImpact: MediumIssue is impactful with a bad, or no, workaroundIssue is impactful with a bad, or no, workaround