diff paraspace/dexfile.py @ 25:670167ed06bb

test dex_deptracker._link_dependencies()
author Thinker K.F. Li <thinker@codemud.net>
date Tue, 07 Jun 2011 00:21:17 +0800
parents a57ec6a76fe3
children 15cb829ac442
line wrap: on
line diff
--- a/paraspace/dexfile.py	Thu Jun 02 21:50:49 2011 +0800
+++ b/paraspace/dexfile.py	Tue Jun 07 00:21:17 2011 +0800
@@ -341,6 +341,10 @@
 
     def compute_size(self):
         pass
+
+    def children(self):
+        raise NotImplementedError, \
+            '%s: does not implement children' % (self.__class__.__name__)
     pass
 
 
@@ -390,6 +394,9 @@
         to_str = self.child_type.to_str
         strs = [to_str(item) for item in self.items]
         return ''.join(strs)
+
+    def children(self):
+        return ('items',)
     pass
 
 
@@ -441,6 +448,9 @@
                              child_clazz.to_str(child),
                          child_clazzs, children)
         return ''.join(child_strs)
+
+    def children(self):
+        return self.child_names
     pass
 
 
@@ -453,7 +463,7 @@
         self.condition = cond
         self.child_type = child_type
         pass
-    
+
     def parse(self, parent, data, off):
         if self.condition(parent, data, off):
             value = self.child_type.parse(parent, data, off)
@@ -485,6 +495,9 @@
 
         data = self.child_type.to_str(self.value)
         return data
+
+    def children(self):
+        return ('value',)
     pass
 
 
@@ -494,17 +507,23 @@
     child_type = None
     value = None
     
+    _parent = None
+    
     def __init__(self, selector, map):
         self.selector = selector
         self.map = map
         pass
 
-    def _get_child_type(self, parent):
+    def switch_key(self, parent):
         selector = self.selector
         sel_value = parent
         for name in selector.split('.'):
             sel_value = getattr(sel_value, name)
             pass
+        return sel_value
+    
+    def _get_child_type(self, parent):
+        sel_value = self.switch_key(parent)
 
         child_type = self.map[sel_value]
         return child_type
@@ -517,6 +536,7 @@
         obj.value = value
         obj.child_type = child_type
         obj.data_size = self.sizeof(obj)
+        obj._parent = parent
         return obj
     
     @staticmethod
@@ -534,10 +554,14 @@
     def to_str(self):
         data = self.child_type.to_str(self.value)
         return data
+
+    def children(self):
+        key = self.switch_key(self._parent)
+        return (repr(key),)
     pass
 
 
-class abs_value(object):
+class abs_value(relocatable):
     value = None
     
     def __init__(self, value):
@@ -553,6 +577,9 @@
 
     def to_str(self):
         return ''
+
+    def children(self):
+        return ('value',)
     pass
 
 
@@ -584,10 +611,32 @@
 
     def to_str(self, child):
         return self.child_type.to_str(child)
+
+    def link(self, child, name_path, parents, markers_info):
+        raise NotImplementedError, 'does not support link() method'
+    pass
+
+
+def _set_name_path_name(parent, name, obj):
+    if isinstance(parent, (list, dict)):
+        key = eval(name)
+        parent[key] = obj
+        return
+    setattr(parent, name, obj)
     pass
 
 
 class depend_off(depend):
+    def link(self, child, name_path, parents, markers_info):
+        parent = parents[-1]
+        name = name_path.split('.')[-1]
+        
+        dep_on_name_path = self.depend_on
+        id_item_map = markers_info[dep_on_name_path]
+        dep_on = id_item_map[child.data_offset]
+
+        _set_name_path_name(parent, name, dep_on)
+        pass
     pass
 
 
@@ -596,6 +645,7 @@
 
     def __init__(self, relative_to, depend_on):
         super(depend_off_rel, self).__init__(depend_on)
+        self.relative_to = relative_to
         pass
     pass
 
@@ -1110,7 +1160,7 @@
                 opcodes.append((opcode,))
                 pass
             pass
-        self.opcodes = opcodes
+        self.opcodes = tuple(opcodes)
 
         self.data_size = moff() - off
         
@@ -1205,6 +1255,9 @@
             pass
 
         return ''.join(opcodebins)
+
+    def children(self):
+        return ('opcodes',)
     pass
 
 
@@ -1218,10 +1271,16 @@
     pass
 
 
-class _DEX_StringDataItem(relocatable):
-    size = None
-    data = None
+class _DEX_StringDataItem(composite):
+    size = uleb128
+    data = rawstr_size_name('size')
+    padding = rawstr(1)
+
+    child_names = 'size data padding'.split()
+    pass
     
+
+class dummy(object):
     data_size = None
 
     @staticmethod
@@ -1347,11 +1406,17 @@
         self._parse_maps()
         self._parse_blocks()
         pass
+
+    def children(self):
+        return 'header stringIds typeIds protoIds fieldIds methodIds ' \
+            'classDefs typeLists annotationSetItems classDatas codeItems ' \
+            'stringDataItems debugInfoItems annotationItems ' \
+            'encodedArrayItems annotationsDirectoryItems'.split()
     pass
 
 
 if __name__ == '__main__':
-    dex = DEXFile.open('../data/testdata1.dex')
+    dex = DEXFile.open('data/testdata1.dex')
     
     print 'Header'
     h = dex.header