| 4485 | { |
| 4486 | public: |
| 4487 | virtual bool ApplyRelocation(Ref<BinaryView> view, Ref<Architecture> arch, Ref<Relocation> reloc, uint8_t* dest, size_t len) override |
| 4488 | { |
| 4489 | // Note: info.base contains preferred base address and the base where the image is actually loaded |
| 4490 | (void)view; |
| 4491 | (void)arch; |
| 4492 | uint64_t* data64 = (uint64_t*)dest; |
| 4493 | uint32_t* data32 = (uint32_t*)dest; |
| 4494 | uint16_t* data16 = (uint16_t*)dest; |
| 4495 | auto info = reloc->GetInfo(); |
| 4496 | if (len < info.size) |
| 4497 | return false; |
| 4498 | uint64_t offset = 0; |
| 4499 | |
| 4500 | if (info.pcRelative) |
| 4501 | { |
| 4502 | int64_t relative_offset = info.target - info.address; |
| 4503 | offset = (uint64_t) relative_offset; |
| 4504 | } |
| 4505 | else |
| 4506 | offset = info.target; |
| 4507 | |
| 4508 | if (! info.implicitAddend && info.addend) |
| 4509 | offset += info.addend; |
| 4510 | |
| 4511 | if (! info.baseRelative) |
| 4512 | offset -= info.base; |
| 4513 | |
| 4514 | switch (info.nativeType) |
| 4515 | { |
| 4516 | // case PE_IMAGE_REL_I386_SECTION: |
| 4517 | case PE_IMAGE_REL_AMD64_SECTION: |
| 4518 | // TODO: test this implementation, but for now, just don't warn about it |
| 4519 | data16[0] = info.sectionIndex + 1; |
| 4520 | break; |
| 4521 | // case PE_IMAGE_REL_I386_SECREL: |
| 4522 | case PE_IMAGE_REL_AMD64_SECREL: |
| 4523 | { |
| 4524 | // TODO: test this implementation, but for now, just don't warn about it |
| 4525 | auto sections = view->GetSectionsAt(info.target); |
| 4526 | if (sections.size() > 0) |
| 4527 | { |
| 4528 | data32[0] = info.target - sections[0]->GetStart(); |
| 4529 | } |
| 4530 | break; |
| 4531 | } |
| 4532 | default: |
| 4533 | if (info.size == 8) |
| 4534 | { |
| 4535 | // 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); |
| 4536 | data64[0] += offset; |
| 4537 | } |
| 4538 | else if (info.size == 4) |
| 4539 | { |
| 4540 | // 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); |
| 4541 | data32[0] += (uint32_t)offset; |
| 4542 | } |
| 4543 | } |
| 4544 | return true; |
nothing calls this directly
no test coverage detected