EF_ARM_ABI_FLOAT_SOFT=0x00000200
EF_ARM_ABI_FLOAT_HARD=0x00000400
+ EF_PPC64_ABI_V0=0
+ EF_PPC64_ABI_V1=1
+ EF_PPC64_ABI_V2=2
+
EF_MIPS_NOREORDER=1
EF_MIPS_PIC=2
EF_MIPS_CPIC=4
from .enums import (
ENUM_D_TAG, ENUM_E_VERSION, ENUM_P_TYPE_BASE, ENUM_SH_TYPE_BASE,
ENUM_RELOC_TYPE_i386, ENUM_RELOC_TYPE_x64,
- ENUM_RELOC_TYPE_ARM, ENUM_RELOC_TYPE_AARCH64, ENUM_RELOC_TYPE_MIPS,
- ENUM_ATTR_TAG_ARM, ENUM_DT_FLAGS, ENUM_DT_FLAGS_1)
+ ENUM_RELOC_TYPE_ARM, ENUM_RELOC_TYPE_AARCH64, ENUM_RELOC_TYPE_PPC64,
+ ENUM_RELOC_TYPE_MIPS, ENUM_ATTR_TAG_ARM, ENUM_DT_FLAGS, ENUM_DT_FLAGS_1)
from .constants import (
P_FLAGS, RH_FLAGS, SH_FLAGS, SUNW_SYMINFO_FLAGS, VER_FLAGS)
from ..common.py3compat import iteritems
return _DESCR_SH_TYPE.get(x)
elif (x >= ENUM_SH_TYPE_BASE['SHT_LOOS'] and
x < ENUM_SH_TYPE_BASE['SHT_GNU_versym']):
- return 'loos+%lx' % (x - ENUM_SH_TYPE_BASE['SHT_LOOS'])
+ return 'loos+0x%lx' % (x - ENUM_SH_TYPE_BASE['SHT_LOOS'])
else:
return _unknown
SH_FLAGS.SHF_GROUP, SH_FLAGS.SHF_TLS, SH_FLAGS.SHF_MASKOS,
SH_FLAGS.SHF_EXCLUDE):
s += _DESCR_SH_FLAGS[flag] if (x & flag) else ''
- if x & SH_FLAGS.SHF_MASKPROC:
- s += 'p'
+ if not x & SH_FLAGS.SHF_EXCLUDE:
+ if x & SH_FLAGS.SHF_MASKPROC:
+ s += 'p'
return s
return _DESCR_ST_VISIBILITY.get(x, _unknown)
+def describe_symbol_local(x):
+ return '[<localentry>: ' + str(1 << x) + ']'
+
+
+def describe_symbol_other(x):
+ vis = describe_symbol_visibility(x['visibility'])
+ if x['local'] > 1 and x['local'] < 7:
+ return vis + ' ' + describe_symbol_local(x['local'])
+ return vis
+
+
def describe_symbol_shndx(x):
return _DESCR_ST_SHNDX.get(x, '%3s' % x)
return _DESCR_RELOC_TYPE_ARM.get(x, _unknown)
elif arch == 'AArch64':
return _DESCR_RELOC_TYPE_AARCH64.get(x, _unknown)
+ elif arch == '64-bit PowerPC':
+ return _DESCR_RELOC_TYPE_PPC64.get(x, _unknown)
elif arch == 'MIPS':
return _DESCR_RELOC_TYPE_MIPS.get(x, _unknown)
else:
EM_AARCH64='AArch64',
EM_BLACKFIN='Analog Devices Blackfin',
EM_PPC='PowerPC',
+ EM_PPC64='PowerPC64',
RESERVED='RESERVED',
)
_DESCR_RELOC_TYPE_x64 = _reverse_dict(ENUM_RELOC_TYPE_x64)
_DESCR_RELOC_TYPE_ARM = _reverse_dict(ENUM_RELOC_TYPE_ARM)
_DESCR_RELOC_TYPE_AARCH64 = _reverse_dict(ENUM_RELOC_TYPE_AARCH64)
+_DESCR_RELOC_TYPE_PPC64 = _reverse_dict(ENUM_RELOC_TYPE_PPC64)
_DESCR_RELOC_TYPE_MIPS = _reverse_dict(ENUM_RELOC_TYPE_MIPS)
_low_priority_D_TAG = (
_default_=Pass,
)
+ENUM_ST_LOCAL = dict(
+ _default_=Pass,
+)
+
# st_shndx
ENUM_ST_SHNDX = dict(
SHN_UNDEF=0,
TAG_VIRTUALIZATION_USE=68,
TAG_MPEXTENSION_USE_OLD=70,
)
+
+# https://openpowerfoundation.org/wp-content/uploads/2016/03/ABI64BitOpenPOWERv1.1_16July2015_pub4.pdf
+# See 3.5.3 Relocation Types Table.
+ENUM_RELOC_TYPE_PPC64 = dict(
+ R_PPC64_NONE=0,
+ R_PPC64_ADDR32=1,
+ R_PPC64_ADDR24=2,
+ R_PPC64_ADDR16=3,
+ R_PPC64_ADDR16_LO=4,
+ R_PPC64_ADDR16_HI=5,
+ R_PPC64_ADDR16_HA=6,
+ R_PPC64_ADDR14=7,
+ R_PPC64_ADDR14_BRTAKEN=8,
+ R_PPC64_ADDR14_BRNTAKEN=9,
+ R_PPC64_REL24=10,
+ R_PPC64_REL14=11,
+ R_PPC64_REL14_BRTAKEN=12,
+ R_PPC64_REL14_BRNTAKEN=13,
+ R_PPC64_GOT16=14,
+ R_PPC64_GOT16_LO=15,
+ R_PPC64_GOT16_HI=16,
+ R_PPC64_GOT16_HA=17,
+ R_PPC64_COPY=19,
+ R_PPC64_GLOB_DAT=20,
+ R_PPC64_JMP_SLOT=21,
+ R_PPC64_RELATIVE=22,
+ R_PPC64_UADDR32=24,
+ R_PPC64_UADDR16=25,
+ R_PPC64_REL32=26,
+ R_PPC64_PLT32=27,
+ R_PPC64_PLTREL32=28,
+ R_PPC64_PLT16_LO=29,
+ R_PPC64_PLT16_HI=30,
+ R_PPC64_PLT16_HA=31,
+ R_PPC64_SECTOFF=33,
+ R_PPC64_SECTOFF_LO=34,
+ R_PPC64_SECTOFF_HI=35,
+ R_PPC64_SECTOFF_HA=36,
+ R_PPC64_ADDR30=37,
+ R_PPC64_ADDR64=38,
+ R_PPC64_ADDR16_HIGHER=39,
+ R_PPC64_ADDR16_HIGHERA=40,
+ R_PPC64_ADDR16_HIGHEST=41,
+ R_PPC64_ADDR16_HIGHESTA=42,
+ R_PPC64_UADDR64=43,
+ R_PPC64_REL64=44,
+ R_PPC64_PLT64=45,
+ R_PPC64_PLTREL64=46,
+ R_PPC64_TOC16=47,
+ R_PPC64_TOC16_LO=48,
+ R_PPC64_TOC16_HI=49,
+ R_PPC64_TOC16_HA=50,
+ R_PPC64_TOC=51,
+ R_PPC64_PLTGOT16=52,
+ R_PPC64_PLTGOT16_LO=53,
+ R_PPC64_PLTGOT16_HI=54,
+ R_PPC64_PLTGOT16_HA=55,
+ R_PPC64_ADDR16_DS=56,
+ R_PPC64_ADDR16_LO_DS=57,
+ R_PPC64_GOT16_DS=58,
+ R_PPC64_GOT16_LO_DS=59,
+ R_PPC64_PLT16_LO_DS=60,
+ R_PPC64_SECTOFF_DS=61,
+ R_PPC64_SECTOFF_LO_DS=62,
+ R_PPC64_TOC16_DS=63,
+ R_PPC64_TOC16_LO_DS=64,
+ R_PPC64_PLTGOT16_DS=65,
+ R_PPC64_PLTGOT16_LO_DS=66,
+ R_PPC64_TLS=67,
+ R_PPC64_DTPMOD64=68,
+ R_PPC64_TPREL16=69,
+ R_PPC64_TPREL16_LO=70,
+ R_PPC64_TPREL16_HI=71,
+ R_PPC64_TPREL16_HA=72,
+ R_PPC64_TPREL64=73,
+ R_PPC64_DTPREL16=74,
+ R_PPC64_DTPREL16_LO=75,
+ R_PPC64_DTPREL16_HI=76,
+ R_PPC64_DTPREL16_HA=77,
+ R_PPC64_DTPREL64=78,
+ R_PPC64_GOT_TLSGD16=79,
+ R_PPC64_GOT_TLSGD16_LO=80,
+ R_PPC64_GOT_TLSGD16_HI=81,
+ R_PPC64_GOT_TLSGD16_HA=82,
+ R_PPC64_GOT_TLSLD16=83,
+ R_PPC64_GOT_TLSLD16_LO=84,
+ R_PPC64_GOT_TLSLD16_HI=85,
+ R_PPC64_GOT_TLSLD16_HA=86,
+ R_PPC64_GOT_TPREL16_DS=87,
+ R_PPC64_GOT_TPREL16_LO_DS=88,
+ R_PPC64_GOT_TPREL16_HI=89,
+ R_PPC64_GOT_TPREL16_HA=90,
+ R_PPC64_GOT_DTPREL16_DS=91,
+ R_PPC64_GOT_DTPREL16_LO_DS=92,
+ R_PPC64_GOT_DTPREL16_HI=93,
+ R_PPC64_GOT_DTPREL16_HA=94,
+ R_PPC64_TPREL16_DS=95,
+ R_PPC64_TPREL16_LO_DS=96,
+ R_PPC64_TPREL16_HIGHER=97,
+ R_PPC64_TPREL16_HIGHERA=98,
+ R_PPC64_TPREL16_HIGHEST=99,
+ R_PPC64_TPREL16_HIGHESTA=100,
+ R_PPC64_DTPREL16_DS=101,
+ R_PPC64_DTPREL16_LO_DS=102,
+ R_PPC64_DTPREL16_HIGHER=103,
+ R_PPC64_DTPREL16_HIGHERA=104,
+ R_PPC64_DTPREL16_HIGHEST=105,
+ R_PPC64_DTPREL16_HIGHESTA=106,
+ R_PPC64_TLSGD=107,
+ R_PPC64_TLSLD=108,
+ R_PPC64_TOCSAVE=109,
+ R_PPC64_ADDR16_HIGH=110,
+ R_PPC64_ADDR16_HIGHA=111,
+ R_PPC64_TPREL16_HIGH=112,
+ R_PPC64_TPREL16_HIGHA=113,
+ R_PPC64_DTPREL16_HIGH=114,
+ R_PPC64_DTPREL16_HIGHA=115,
+ R_PPC64_REL24_NOTOC=116,
+ R_PPC64_ADDR64_LOCAL=117,
+ R_PPC64_IRELATIVE=248,
+ R_PPC64_REL16=249,
+ R_PPC64_REL16_LO=250,
+ R_PPC64_REL16_HI=251,
+ R_PPC64_REL16_HA=252,
+ R_PPC64_GNU_VTINHERIT=253,
+ R_PPC64_GNU_VTENTRY=254,
+)
from .sections import Section
from .enums import (
ENUM_RELOC_TYPE_i386, ENUM_RELOC_TYPE_x64, ENUM_RELOC_TYPE_MIPS,
- ENUM_RELOC_TYPE_ARM, ENUM_RELOC_TYPE_AARCH64, ENUM_D_TAG)
+ ENUM_RELOC_TYPE_ARM, ENUM_RELOC_TYPE_AARCH64, ENUM_RELOC_TYPE_PPC64,
+ ENUM_D_TAG)
class Relocation(object):
recipe = self._RELOCATION_RECIPES_ARM.get(reloc_type, None)
elif self.elffile.get_machine_arch() == 'AArch64':
recipe = self._RELOCATION_RECIPES_AARCH64.get(reloc_type, None)
+ elif self.elffile.get_machine_arch() == '64-bit PowerPC':
+ recipe = self._RELOCATION_RECIPES_PPC64.get(reloc_type, None)
if recipe is None:
raise ELFRelocationError(
calc_func=_reloc_calc_sym_plus_value),
}
+ _RELOCATION_RECIPES_PPC64 = {
+ ENUM_RELOC_TYPE_PPC64['R_PPC64_ADDR32']: _RELOCATION_RECIPE_TYPE(
+ bytesize=4, has_addend=True, calc_func=_reloc_calc_sym_plus_addend),
+ ENUM_RELOC_TYPE_PPC64['R_PPC64_REL32']: _RELOCATION_RECIPE_TYPE(
+ bytesize=4, has_addend=True, calc_func=_reloc_calc_sym_plus_addend_pcrel),
+ ENUM_RELOC_TYPE_PPC64['R_PPC64_ADDR64']: _RELOCATION_RECIPE_TYPE(
+ bytesize=8, has_addend=True, calc_func=_reloc_calc_sym_plus_addend),
+ }
+
_RELOCATION_RECIPES_X86 = {
ENUM_RELOC_TYPE_i386['R_386_NONE']: _RELOCATION_RECIPE_TYPE(
bytesize=4, has_addend=False, calc_func=_reloc_calc_identity),
# st_other is hierarchical. To access the visibility,
# use container['st_other']['visibility']
st_other_struct = BitStruct('st_other',
- Padding(5),
+ # https://openpowerfoundation.org/wp-content/uploads/2016/03/ABI64BitOpenPOWERv1.1_16July2015_pub4.pdf
+ # See 3.4.1 Symbol Values.
+ Enum(BitField('local', 3), **ENUM_ST_LOCAL),
+ Padding(2),
Enum(BitField('visibility', 3), **ENUM_ST_VISIBILITY))
if self.elfclass == 32:
self.Elf_Sym = Struct('Elf_Sym',
describe_symbol_type, describe_symbol_bind, describe_symbol_visibility,
describe_symbol_shndx, describe_reloc_type, describe_dyn_tag,
describe_dt_flags, describe_dt_flags_1, describe_ver_flags, describe_note,
- describe_attr_tag_arm
+ describe_attr_tag_arm, describe_symbol_other
)
from elftools.elf.constants import E_FLAGS
from elftools.elf.constants import E_FLAGS_MASKS
else:
description += ', <unrecognized EABI>'
+ elif self.elffile['e_machine'] == 'EM_PPC64':
+ if flags & E_FLAGS.EF_PPC64_ABI_V2:
+ description += ', abiv2'
+
elif self.elffile['e_machine'] == "EM_MIPS":
if flags & E_FLAGS.EF_MIPS_NOREORDER:
description += ", noreorder"
"%5d" % symbol['st_size'] if symbol['st_size'] < 100000 else hex(symbol['st_size']),
describe_symbol_type(symbol['st_info']['type']),
describe_symbol_bind(symbol['st_info']['bind']),
- describe_symbol_visibility(symbol['st_other']['visibility']),
+ describe_symbol_other(symbol['st_other']),
describe_symbol_shndx(self._get_symbol_shndx(symbol,
nsym,
section_index)),
# readelf doesn't print the state after end_sequence
# instructions. I think it's a bug but to be compatible
# I don't print them too.
- if lineprogram['version'] < 4:
+ if lineprogram['version'] < 4 or self.elffile['e_machine'] == 'EM_PPC64':
self._emitline('%-35s %11d %18s' % (
bytes2str(lineprogram['file_entry'][state.file - 1].name),
state.line,
--- /dev/null
+/* This source was compiled for ppc64le.
+ clang --target=powerpc64le -c -o powerpc64-relocs-le.o.elf powerpc64-relocs.c -g
+*/
+
+extern struct {
+ int i, j;
+} data;
+
+extern int bar (void);
+
+int
+foo (int a)
+{
+ data.i += a;
+ data.j -= bar();
+}