@propertydefvalue(self)->int:returnself._value@staticmethoddef_from_c(c_const):ifc_const[0]==ffi.NULL:returnNonetag=get_enum_from_int(c_const.tag)try:returntag_to_const_class(tag)._from_c(c_const)exceptKeyError:raisePyVEXError("Unknown/unsupported IRConstTag %s\n"%tag)_translate=_from_c@classmethoddef_to_c(cls,const):# libvex throws an exception when constructing a U1 with a value other than 0 or 1ifconst.tag=="Ico_U1"andconst.valuenotin(0,1):raisePyVEXError("Invalid U1 value: %d"%const.value)try:returncls.c_constructor(const.value)exceptKeyError:raisePyVEXError("Unknown/unsupported IRConstTag %s]n"%const.tag)def__eq__(self,other):ifnotisinstance(other,type(self)):returnFalsereturnself._value==other._valuedef__hash__(self):returnhash((type(self),self._value))
_U64_POOL=[U64(i)foriinrange(1024)]+[U64(i)foriinrange(0xFFFFFFFFFFFFFC00,0xFFFFFFFFFFFFFFFF+1)]# Integer Type Imaginationclass_cache={1:U1,8:U8,16:U16,32:U32,64:U64}
def__str__(self):return"%x"%self.value# vex doesn't store a full 128 bit constant, instead it stores 1 bit per 8 bits of data# and duplicates each bit 8 times@staticmethoddef_from_c(c_const):base_const=c_const.Ico.V128real_const=0foriinrange(16):if(base_const>>i)&1==1:real_const|=0xFF<<(8*i)returnV128(real_const)
def__str__(self):return"%x"%self.value# see above@staticmethoddef_from_c(c_const):base_const=c_const.Ico.V256real_const=0foriinrange(32):if(base_const>>i)&1==1:real_const|=0xFF<<(8*i)returnV256(real_const)
[docs]defget_type_size(ty):""" Returns the size, in BITS, of a VEX type specifier e.g., Ity_I16 -> 16 :param ty: :return: """m=type_str_re.match(ty)ifmisNone:raiseValueError("Type %s does not have size"%ty)returnint(m.group("size"))
[docs]defget_type_spec_size(ty):""" Get the width of a "type specifier" like I16U or F16 or just 16 (Yes, this really just takes the int out. If we must special-case, do it here. :param tyspec: :return: """m=type_tag_str_re.match(ty)ifmisNone:raiseValueError("Type specifier %s does not have size"%ty)returnint(m.group("size"))
[docs]defty_to_const_class(ty):try:returnpredefined_types_map[ty]exceptKeyError:ifis_int_ty(ty):size=get_type_size(ty)returnvex_int_class(size)else:raiseValueError("Type %s does not exist"%ty)
[docs]deftag_to_const_class(tag):try:returnpredefined_classes_map[tag]exceptKeyError:ifis_int_tag(tag):size=get_tag_size(tag)returnvex_int_class(size)else:raiseValueError("Tag %s does not exist"%tag)