diff options
Diffstat (limited to 'miasm2/core/asmblock.py')
| -rw-r--r-- | miasm2/core/asmblock.py | 231 |
1 files changed, 7 insertions, 224 deletions
diff --git a/miasm2/core/asmblock.py b/miasm2/core/asmblock.py index 08ff25e9..2829737e 100644 --- a/miasm2/core/asmblock.py +++ b/miasm2/core/asmblock.py @@ -12,6 +12,7 @@ from miasm2.expression.modint import moduint, modint from miasm2.core.utils import Disasm_Exception, pck from miasm2.core.graph import DiGraph, DiGraphSimplifier, MatchGraphJoker from miasm2.core.interval import interval +from miasm2.core.locationdb import LocationDB log_asmblock = logging.getLogger("asmblock") @@ -344,235 +345,17 @@ class asm_block_bad(AsmBlockBad): warnings.warn('DEPRECATION WARNING: use "AsmBlockBad" instead of "asm_block_bad"') super(asm_block_bad, self).__init__(loc_key, alignment, *args, **kwargs) +class AsmSymbolPool(LocationDB): + """[DEPRECATED API] use 'LocationDB' instead""" -class AsmSymbolPool(object): - """ - Store symbols. - - A symbol links a name to an (optional) offset - - Rules and limitations: - - two different symbols cannot have the same offset - - two different symbols cannot have the same name - - symbols manipulation (comparison, creation ...) can only be done on - symbols generated by the same symbol pool - """ - - def __init__(self): - self._loc_keys = set() - - self._loc_key_to_offset = {} - self._loc_key_to_name = {} - - self._name_to_loc_key = {} - self._offset_to_loc_key = {} - - self._loc_key_num = 0 - - def loc_key_to_offset(self, loc_key): - """ - Return offset of @loc_key, None otherwise. - @loc_key: LocKey instance - """ - assert isinstance(loc_key, LocKey) - return self._loc_key_to_offset.get(loc_key) - - def loc_key_to_name(self, loc_key): - """ - Return name of @loc_key. - @loc_key: LocKey instance - """ - assert isinstance(loc_key, LocKey) - return self._loc_key_to_name[loc_key] - - def add_location(self, name, offset=None): - """ - Create and add a location to the symbol_pool - @name: loc_key's name (never empty). If offset is None and name is int, - generate loc_key with generic name and name as offset - @offset: (optional) loc_key's offset - """ - - if is_int(name): - assert offset is None or offset == name - offset = name - name = "loc_%.16X" % (int(name) & 0xFFFFFFFFFFFFFFFF) - if offset is not None: - offset = int(offset) - - assert name - - # Test for collisions - known_loc_key = self.getby_name(name) - if known_loc_key is not None: - known_offset = self.loc_key_to_offset(known_loc_key) - if known_offset != offset: - raise ValueError( - 'symbol %s with different offset %s %s' % ( - name, offset, known_offset - ) - ) - return known_loc_key - - elif self.getby_offset(offset) is not None: - raise ValueError( - 'offset %s with different names %s' % ( - offset, - name - ) - ) - - loc_key = LocKey(self._loc_key_num) - self._loc_key_num += 1 - - self._loc_keys.add(loc_key) - - if offset is not None: - assert offset not in self._offset_to_loc_key - self._offset_to_loc_key[offset] = loc_key - self._loc_key_to_offset[loc_key] = offset - - self._name_to_loc_key[name] = loc_key - self._loc_key_to_name[loc_key] = name - return loc_key - - def remove_loc_key(self, loc_key): - """ - Delete a @loc_key - """ - name = self._loc_key_to_name.pop(loc_key, None) - self._name_to_loc_key.pop(name, None) - - offset = self._loc_key_to_offset.pop(loc_key, None) - self._offset_to_loc_key.pop(offset, None) - - self._loc_keys.remove(loc_key) - - def del_loc_key_offset(self, loc_key): - """Unpin the @loc_key from its offset""" - offset = self._loc_keys_to_offset.pop(loc_key) - self._offset_to_loc_key.pop(offset, None) - - def getby_offset(self, offset): - """ - Retrieve loc_key using its @offset, None otherwise. - @offset: int - """ - return self._offset_to_loc_key.get(offset) - - def getby_name(self, name): - """ - Retrieve loc_key using its @name, None otherwise. - @name: str - """ - return self._name_to_loc_key.get(name) - - def getby_name_create(self, name): - """Get a loc_key from its @name, create it if it doesn't exist""" - loc_key = self.getby_name(name) - if loc_key is None: - loc_key = self.add_location(name) - return loc_key - - def getby_offset_create(self, offset): - """Get a loc_key from its @offset, create it if it doesn't exist""" - loc_key = self.getby_offset(offset) - if loc_key is None: - loc_key = self.add_location(offset) - return loc_key - - def rename_location(self, loc_key, newname): - """Rename the @loc_key name to @newname""" - if newname in self._name_to_loc_key: - raise ValueError('Symbol already known') - name = self._loc_key_to_name[loc_key] - assert name is not None - self._name_to_loc_key.pop(name) - self._loc_key_to_name[loc_key] = newname - - def set_offset(self, loc_key, offset): - """Pin the @loc_key to an @offset - Note that there is a special case when the offset is a list - it happens when offsets are recomputed in resolve_symbol* - """ - assert isinstance(loc_key, LocKey) - assert offset not in self._offset_to_loc_key - if loc_key not in self._loc_keys: - raise ValueError('Foreign loc_key %s' % loc_key) - - old_offset = self._loc_key_to_offset.pop(loc_key, None) - self._offset_to_loc_key.pop(old_offset, None) - - self._loc_key_to_offset[loc_key] = offset - self._offset_to_loc_key[offset] = loc_key - - @property - def loc_keys(self): - """Return all loc_keys""" - return self._loc_keys - - @property - def items(self): - """Return all loc_keys""" - warnings.warn('DEPRECATION WARNING: use "loc_keys" instead of "items"') - return list(self._loc_keys) - - def __str__(self): - return "".join("%s\n" % loc_key for loc_key in self._loc_keys) - - def __getitem__(self, item): - warnings.warn('DEPRECATION WARNING: use "getby_name" or "getby_offset"') - if item in self._name_to_loc_key: - return self._name_to_loc_key[item] - if item in self._offset_to_loc_key: - return self._offset_to_loc_key[item] - raise KeyError('unknown symbol %r' % item) - - def __contains__(self, item): - warnings.warn('DEPRECATION WARNING: use "getby_name" or "getby_offset"') - return item in self._name_to_loc_key or item in self._offset_to_loc_key - - def merge(self, symbol_pool): - """Merge with another @symbol_pool""" - self._loc_keys.update(symbol_pool.loc_keys) - self._name_to_loc_key.update(symbol_pool._name_to_loc_key) - self._offset_to_loc_key.update(symbol_pool._offset_to_loc_key) - - def canonize_to_exprloc(self, expr): - """ - If expr is ExprInt, return ExprLoc with corresponding loc_key - Else, return expr - - @expr: Expr instance - """ - if expr.is_int(): - loc_key = self.getby_offset_create(int(expr)) - ret = ExprLoc(loc_key, expr.size) - return ret - return expr - - def gen_loc_key(self): - """Generate a new unpinned loc_key""" - loc_key = self.add_location("lbl_gen_%.8X" % (self._loc_key_num)) - return loc_key - - def str_loc_key(self, loc_key): - name = self.loc_key_to_name(loc_key) - offset = self.loc_key_to_offset(loc_key) - if name is None: - name = str(loc_key) - if offset is not None: - offset = hex(offset) - out = name - if offset is not None: - out = "%s:%s" % (out, offset) - return out - + def __init__(self, *args, **kwargs): + warnings.warn("Deprecated API, use 'LocationDB' instead") + super(AsmSymbolPool, self).__init__(*args, **kwargs) class asm_symbol_pool(AsmSymbolPool): def __init__(self): - warnings.warn('DEPRECATION WARNING: use "AsmSymbolPool" instead of "asm_symbol_pool"') + warnings.warn('DEPRECATION WARNING: use "LocationDB" instead of "asm_symbol_pool"') super(asm_symbol_pool, self).__init__() |