protected override ElfRelocator CreateRelocator(ElfLoader loader, SortedList <Address, ImageSymbol> imageSymbols) { return(new x86Relocator((ElfLoader32)loader, imageSymbols)); }
public override (Address, ElfSymbol) RelocateEntry(Program program, ElfSymbol sym, ElfSection referringSection, ElfRelocation rela) { var rt = (x86_64Rt)(rela.Info & 0xFF); if (loader.Sections.Count <= sym.SectionIndex) { return(null, null); } if (rt == x86_64Rt.R_X86_64_GLOB_DAT || rt == x86_64Rt.R_X86_64_JUMP_SLOT) { var addrPfn = Address.Ptr64(rela.Offset); var st = ElfLoader.GetSymbolType(sym); if (!st.HasValue) { return(null, null); } importReferences.Add(addrPfn, new NamedImportReference(addrPfn, null, sym.Name, st.Value)); var gotSym = loader.CreateGotSymbol(addrPfn, sym.Name); imageSymbols.Add(addrPfn, gotSym); return(addrPfn, null); } ulong S = 0; if (sym.SectionIndex != 0) { var symSection = loader.Sections[(int)sym.SectionIndex]; S = (ulong)sym.Value + symSection.Address.ToLinear(); } long A = 0; int sh = 0; uint mask = ~0u; Address addr; ulong P; if (referringSection?.Address != null) { addr = referringSection.Address + rela.Offset; P = addr.ToLinear(); } else { addr = Address.Ptr64(rela.Offset); P = 0; } var arch = program.Architecture; var relR = program.CreateImageReader(arch, addr); var relW = program.CreateImageWriter(arch, addr); ulong PP = P; switch (rt) { case x86_64Rt.R_X86_64_NONE: // just ignore (common) break; case x86_64Rt.R_X86_64_COPY: break; default: Debug.Print("x86_64 ELF relocation type {0} not implemented yet.", rt); break; //throw new NotImplementedException(string.Format( // "x86_64 ELF relocation type {0} not implemented yet.", // rt)); } if (relR != null) { var w = relR.ReadUInt64(); w += ((ulong)(S + (ulong)A + P) >> sh) & mask; relW.WriteUInt64(w); } return(addr, null); }
protected abstract ElfRelocator CreateRelocator(ElfLoader loader, SortedList <Address, ImageSymbol> imageSymbols);
public override (Address?, ElfSymbol?) RelocateEntry(Program program, ElfSymbol sym, ElfSection?referringSection, ElfRelocation rela) { if (loader.Sections.Count <= sym.SectionIndex) { return(null, null); } var rt = (SparcRt)(rela.Info & 0xFF); var addr = referringSection != null ? referringSection.Address !+rela.Offset : loader.CreateAddress(rela.Offset); if (sym.SectionIndex == 0) { if (rt == SparcRt.R_SPARC_GLOB_DAT || rt == SparcRt.R_SPARC_JMP_SLOT) { var addrPfn = Address.Ptr32((uint)rela.Offset); ElfImageLoader.trace.Verbose("Import reference {0} - {1}", addrPfn, sym.Name); var st = ElfLoader.GetSymbolType(sym); if (st.HasValue) { importReferences[addrPfn] = new NamedImportReference(addrPfn, null, sym.Name, st.Value); } return(addrPfn, null); } } var symSection = loader.Sections[(int)sym.SectionIndex]; ulong S = 0; int A = 0; int sh = 0; uint mask = ~0u; if (referringSection != null) { addr = referringSection.Address !+rela.Offset; } else { addr = Address.Ptr64(rela.Offset); } ulong P = addr.ToLinear(); ulong PP = P; ulong B = 0; ElfImageLoader.trace.Verbose(" off:{0:X8} type:{1,-16} add:{3,-20} {4,3} {2} {5}", rela.Offset, (SparcRt)(rela.Info & 0xFF), sym.Name, rela.Addend, (int)(rela.Info >> 8), "section?"); switch (rt) { case 0: return(null, null); case SparcRt.R_SPARC_HI22: A = (int)rela.Addend; sh = 10; P = 0; mask = 0x3FFFFF; return(Relocate32(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_LM22: A = (int)rela.Addend; S = sym.Value; sh = 10; P = 0; mask = 0x3FFFFF; return(Relocate32(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_LO10: A = (int)rela.Addend; S = sym.Value; mask = 0x3FF; P = 0; return(Relocate32(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_32: A = (int)rela.Addend; S = sym.Value; mask = 0xFFFFFFFF; P = 0; return(Relocate32(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_WDISP30: A = (int)rela.Addend; P = ~P + 1; sh = 2; return(Relocate32(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_RELATIVE: A = (int)rela.Addend; B = program.SegmentMap.BaseAddress.ToLinear(); P = 0; return(Relocate64(program, sym, addr, S, A, sh, mask, P, B)); case SparcRt.R_SPARC_COPY: ElfImageLoader.trace.Warn("Relocation type {0} not handled yet.", rt); return(addr, null); default: ElfImageLoader.trace.Error( "SPARC ELF relocation type {0} not implemented yet.", rt); return(addr, null); } }