Source code for angr.analyses.typehoon.lifter

from typing import Union, TYPE_CHECKING

from ...sim_type import (
    SimType,
    SimTypeChar,
    SimTypeShort,
    SimTypeInt,
    SimTypeLong,
    SimTypeLongLong,
    SimTypePointer,
    SimStruct,
    SimTypeArray,
)
from .typeconsts import BottomType, Int8, Int16, Int32, Int64, Pointer32, Pointer64, Struct, Array

if TYPE_CHECKING:
    from .typeconsts import TypeConstant


[docs]class TypeLifter: """ Lift SimTypes to type constants. """ __slots__ = ("bits", "memo")
[docs] def __init__(self, bits: int): if bits not in (32, 64): raise ValueError("TypeLifter only supports 32-bit or 64-bit pointers.") self.bits = bits self.memo = {}
[docs] def lift(self, ty: SimType): handler = _mapping.get(type(ty), None) if handler is None: return BottomType() return handler(self, ty)
def _lift_SimTypeChar(self, ty): # pylint:disable=unused-argument,no-self-use return Int8() def _lift_SimTypeShort(self, ty): # pylint:disable=unused-argument,no-self-use return Int16() def _lift_SimTypeInt(self, ty): # pylint:disable=unused-argument,no-self-use return Int32() def _lift_SimTypeLongLong(self, ty): # pylint:disable=unused-argument,no-self-use return Int64() def _lift_SimTypePointer(self, ty: SimTypePointer): if self.bits == 32: return Pointer32(self.lift(ty.pts_to)) elif self.bits == 64: return Pointer64(self.lift(ty.pts_to)) raise ValueError("Unsupported bits %s." % self.bits) def _lift_SimStruct(self, ty: SimStruct) -> Union["TypeConstant", BottomType]: if ty in self.memo: return BottomType() obj = Struct(fields={}, name=ty.name) self.memo[ty] = obj converted_fields = {} field_names = {} ty_offsets = ty.offsets for field_name, simtype in ty.fields.items(): if field_name not in ty_offsets: return BottomType() converted_fields[ty_offsets[field_name]] = self.lift(simtype) field_names[ty_offsets[field_name]] = field_name obj.fields = converted_fields obj.field_names = field_names return obj def _lift_SimTypeArray(self, ty: SimTypeArray) -> Array: elem_type = self.lift(ty.elem_type) return Array(elem_type, count=ty.length)
_mapping = { SimTypeChar: TypeLifter._lift_SimTypeChar, SimTypeShort: TypeLifter._lift_SimTypeShort, SimTypeInt: TypeLifter._lift_SimTypeInt, SimTypeLong: TypeLifter._lift_SimTypeInt, SimTypeLongLong: TypeLifter._lift_SimTypeLongLong, SimTypePointer: TypeLifter._lift_SimTypePointer, SimStruct: TypeLifter._lift_SimStruct, SimTypeArray: TypeLifter._lift_SimTypeArray, }