1 # Copyright 2014 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file.
9 from pylib
import constants
10 from pylib
import cmd_helper
13 _PROGUARD_CLASS_RE
= re
.compile(r
'\s*?- Program class:\s*([\S]+)$')
14 _PROGUARD_SUPERCLASS_RE
= re
.compile(r
'\s*? Superclass:\s*([\S]+)$')
15 _PROGUARD_SECTION_RE
= re
.compile(
16 r
'^(?:Interfaces|Constant Pool|Fields|Methods|Class file attributes) '
18 _PROGUARD_METHOD_RE
= re
.compile(r
'\s*?- Method:\s*(\S*)[(].*$')
19 _PROGUARD_ANNOTATION_RE
= re
.compile(r
'\s*?- Annotation \[L(\S*);\]:$')
20 _PROGUARD_ANNOTATION_CONST_RE
= (
21 re
.compile(r
'\s*?- Constant element value.*$'))
22 _PROGUARD_ANNOTATION_VALUE_RE
= re
.compile(r
'\s*?- \S+? \[(.*)\]$')
24 _PROGUARD_PATH_SDK
= os
.path
.join(
25 constants
.ANDROID_SDK_ROOT
, 'tools', 'proguard', 'lib', 'proguard.jar')
26 _PROGUARD_PATH_BUILT
= (
27 os
.path
.join(os
.environ
['ANDROID_BUILD_TOP'], 'external', 'proguard',
28 'lib', 'proguard.jar')
29 if 'ANDROID_BUILD_TOP' in os
.environ
else None)
31 _PROGUARD_PATH_SDK
if os
.path
.exists(_PROGUARD_PATH_SDK
)
32 else _PROGUARD_PATH_BUILT
)
36 """Dumps class and method information from a JAR into a dict via proguard.
39 jar_path: An absolute path to the JAR file to dump.
41 A dict in the following format:
61 with tempfile
.NamedTemporaryFile() as proguard_output
:
62 cmd_helper
.RunCmd(['java', '-jar',
69 '-dump', proguard_output
.name
])
77 annotation_has_value
= False
81 for line
in proguard_output
:
82 line
= line
.strip('\r\n')
84 m
= _PROGUARD_CLASS_RE
.match(line
)
87 'class': m
.group(1).replace('/', '.'),
92 results
['classes'].append(class_result
)
94 annotation_has_value
= False
101 m
= _PROGUARD_SUPERCLASS_RE
.match(line
)
103 class_result
['superclass'] = m
.group(1).replace('/', '.')
106 m
= _PROGUARD_SECTION_RE
.match(line
)
109 annotation_has_value
= False
113 m
= _PROGUARD_METHOD_RE
.match(line
)
116 'method': m
.group(1),
119 class_result
['methods'].append(method_result
)
121 annotation_has_value
= False
124 m
= _PROGUARD_ANNOTATION_RE
.match(line
)
126 # Ignore the annotation package.
127 annotation
= m
.group(1).split('/')[-1]
129 method_result
['annotations'][annotation
] = None
131 class_result
['annotations'][annotation
] = None
135 if not annotation_has_value
:
136 m
= _PROGUARD_ANNOTATION_CONST_RE
.match(line
)
137 annotation_has_value
= bool(m
)
139 m
= _PROGUARD_ANNOTATION_VALUE_RE
.match(line
)
142 method_result
['annotations'][annotation
] = m
.group(1)
144 class_result
['annotations'][annotation
] = m
.group(1)
145 annotation_has_value
= None