Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(457)

Side by Side Diff: build/android/pylib/valgrind_tools.py

Issue 2392643003: Removes files from //build that we don't need (Closed)
Patch Set: Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « build/android/pylib/utils/zip_utils.py ('k') | build/android/rezip.gyp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 # Copyright (c) 2012 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.
4
5 """
6 Classes in this file define additional actions that need to be taken to run a
7 test under some kind of runtime error detection tool.
8
9 The interface is intended to be used as follows.
10
11 1. For tests that simply run a native process (i.e. no activity is spawned):
12
13 Call tool.CopyFiles(device).
14 Prepend test command line with tool.GetTestWrapper().
15
16 2. For tests that spawn an activity:
17
18 Call tool.CopyFiles(device).
19 Call tool.SetupEnvironment().
20 Run the test as usual.
21 Call tool.CleanUpEnvironment().
22 """
23 # pylint: disable=R0201
24
25 import glob
26 import logging
27 import os.path
28 import subprocess
29 import sys
30
31 from pylib.constants import DIR_SOURCE_ROOT
32 from pylib.device import device_errors
33
34
35 def SetChromeTimeoutScale(device, scale):
36 """Sets the timeout scale in /data/local/tmp/chrome_timeout_scale to scale."""
37 path = '/data/local/tmp/chrome_timeout_scale'
38 if not scale or scale == 1.0:
39 # Delete if scale is None/0.0/1.0 since the default timeout scale is 1.0
40 device.RunShellCommand('rm %s' % path)
41 else:
42 device.WriteFile(path, '%f' % scale, as_root=True)
43
44
45 class BaseTool(object):
46 """A tool that does nothing."""
47
48 def __init__(self):
49 """Does nothing."""
50 pass
51
52 def GetTestWrapper(self):
53 """Returns a string that is to be prepended to the test command line."""
54 return ''
55
56 def GetUtilWrapper(self):
57 """Returns the wrapper name for the utilities.
58
59 Returns:
60 A string that is to be prepended to the command line of utility
61 processes (forwarder, etc.).
62 """
63 return ''
64
65 @classmethod
66 def CopyFiles(cls, device):
67 """Copies tool-specific files to the device, create directories, etc."""
68 pass
69
70 def SetupEnvironment(self):
71 """Sets up the system environment for a test.
72
73 This is a good place to set system properties.
74 """
75 pass
76
77 def CleanUpEnvironment(self):
78 """Cleans up environment."""
79 pass
80
81 def GetTimeoutScale(self):
82 """Returns a multiplier that should be applied to timeout values."""
83 return 1.0
84
85 def NeedsDebugInfo(self):
86 """Whether this tool requires debug info.
87
88 Returns:
89 True if this tool can not work with stripped binaries.
90 """
91 return False
92
93
94 class AddressSanitizerTool(BaseTool):
95 """AddressSanitizer tool."""
96
97 WRAPPER_NAME = '/system/bin/asanwrapper'
98 # Disable memcmp overlap check.There are blobs (gl drivers)
99 # on some android devices that use memcmp on overlapping regions,
100 # nothing we can do about that.
101 EXTRA_OPTIONS = 'strict_memcmp=0,use_sigaltstack=1'
102
103 def __init__(self, device):
104 super(AddressSanitizerTool, self).__init__()
105 self._device = device
106 # Configure AndroidCommands to run utils (such as md5sum_bin) under ASan.
107 # This is required because ASan is a compiler-based tool, and md5sum
108 # includes instrumented code from base.
109 device.old_interface.SetUtilWrapper(self.GetUtilWrapper())
110
111 @classmethod
112 def CopyFiles(cls, device):
113 """Copies ASan tools to the device."""
114 libs = glob.glob(os.path.join(DIR_SOURCE_ROOT,
115 'third_party/llvm-build/Release+Asserts/',
116 'lib/clang/*/lib/linux/',
117 'libclang_rt.asan-arm-android.so'))
118 assert len(libs) == 1
119 subprocess.call(
120 [os.path.join(
121 DIR_SOURCE_ROOT,
122 'tools/android/asan/third_party/asan_device_setup.sh'),
123 '--device', str(device),
124 '--lib', libs[0],
125 '--extra-options', AddressSanitizerTool.EXTRA_OPTIONS])
126 device.WaitUntilFullyBooted()
127
128 def GetTestWrapper(self):
129 return AddressSanitizerTool.WRAPPER_NAME
130
131 def GetUtilWrapper(self):
132 """Returns the wrapper for utilities, such as forwarder.
133
134 AddressSanitizer wrapper must be added to all instrumented binaries,
135 including forwarder and the like. This can be removed if such binaries
136 were built without instrumentation. """
137 return self.GetTestWrapper()
138
139 def SetupEnvironment(self):
140 try:
141 self._device.EnableRoot()
142 except device_errors.CommandFailedError as e:
143 # Try to set the timeout scale anyway.
144 # TODO(jbudorick) Handle this exception appropriately after interface
145 # conversions are finished.
146 logging.error(str(e))
147 SetChromeTimeoutScale(self._device, self.GetTimeoutScale())
148
149 def CleanUpEnvironment(self):
150 SetChromeTimeoutScale(self._device, None)
151
152 def GetTimeoutScale(self):
153 # Very slow startup.
154 return 20.0
155
156
157 class ValgrindTool(BaseTool):
158 """Base abstract class for Valgrind tools."""
159
160 VG_DIR = '/data/local/tmp/valgrind'
161 VGLOGS_DIR = '/data/local/tmp/vglogs'
162
163 def __init__(self, device):
164 super(ValgrindTool, self).__init__()
165 self._device = device
166 # exactly 31 chars, SystemProperties::PROP_NAME_MAX
167 self._wrap_properties = ['wrap.com.google.android.apps.ch',
168 'wrap.org.chromium.native_test']
169
170 @classmethod
171 def CopyFiles(cls, device):
172 """Copies Valgrind tools to the device."""
173 device.RunShellCommand(
174 'rm -r %s; mkdir %s' % (ValgrindTool.VG_DIR, ValgrindTool.VG_DIR))
175 device.RunShellCommand(
176 'rm -r %s; mkdir %s' % (ValgrindTool.VGLOGS_DIR,
177 ValgrindTool.VGLOGS_DIR))
178 files = cls.GetFilesForTool()
179 device.PushChangedFiles(
180 [((os.path.join(DIR_SOURCE_ROOT, f),
181 os.path.join(ValgrindTool.VG_DIR, os.path.basename(f)))
182 for f in files)])
183
184 def SetupEnvironment(self):
185 """Sets up device environment."""
186 self._device.RunShellCommand('chmod 777 /data/local/tmp')
187 self._device.RunShellCommand('setenforce 0')
188 for prop in self._wrap_properties:
189 self._device.RunShellCommand(
190 'setprop %s "logwrapper %s"' % (prop, self.GetTestWrapper()))
191 SetChromeTimeoutScale(self._device, self.GetTimeoutScale())
192
193 def CleanUpEnvironment(self):
194 """Cleans up device environment."""
195 for prop in self._wrap_properties:
196 self._device.RunShellCommand('setprop %s ""' % (prop,))
197 SetChromeTimeoutScale(self._device, None)
198
199 @staticmethod
200 def GetFilesForTool():
201 """Returns a list of file names for the tool."""
202 raise NotImplementedError()
203
204 def NeedsDebugInfo(self):
205 """Whether this tool requires debug info.
206
207 Returns:
208 True if this tool can not work with stripped binaries.
209 """
210 return True
211
212
213 class MemcheckTool(ValgrindTool):
214 """Memcheck tool."""
215
216 def __init__(self, device):
217 super(MemcheckTool, self).__init__(device)
218
219 @staticmethod
220 def GetFilesForTool():
221 """Returns a list of file names for the tool."""
222 return ['tools/valgrind/android/vg-chrome-wrapper.sh',
223 'tools/valgrind/memcheck/suppressions.txt',
224 'tools/valgrind/memcheck/suppressions_android.txt']
225
226 def GetTestWrapper(self):
227 """Returns a string that is to be prepended to the test command line."""
228 return ValgrindTool.VG_DIR + '/' + 'vg-chrome-wrapper.sh'
229
230 def GetTimeoutScale(self):
231 """Returns a multiplier that should be applied to timeout values."""
232 return 30
233
234
235 class TSanTool(ValgrindTool):
236 """ThreadSanitizer tool. See http://code.google.com/p/data-race-test ."""
237
238 def __init__(self, device):
239 super(TSanTool, self).__init__(device)
240
241 @staticmethod
242 def GetFilesForTool():
243 """Returns a list of file names for the tool."""
244 return ['tools/valgrind/android/vg-chrome-wrapper-tsan.sh',
245 'tools/valgrind/tsan/suppressions.txt',
246 'tools/valgrind/tsan/suppressions_android.txt',
247 'tools/valgrind/tsan/ignores.txt']
248
249 def GetTestWrapper(self):
250 """Returns a string that is to be prepended to the test command line."""
251 return ValgrindTool.VG_DIR + '/' + 'vg-chrome-wrapper-tsan.sh'
252
253 def GetTimeoutScale(self):
254 """Returns a multiplier that should be applied to timeout values."""
255 return 30.0
256
257
258 TOOL_REGISTRY = {
259 'memcheck': MemcheckTool,
260 'memcheck-renderer': MemcheckTool,
261 'tsan': TSanTool,
262 'tsan-renderer': TSanTool,
263 'asan': AddressSanitizerTool,
264 }
265
266
267 def CreateTool(tool_name, device):
268 """Creates a tool with the specified tool name.
269
270 Args:
271 tool_name: Name of the tool to create.
272 device: A DeviceUtils instance.
273 Returns:
274 A tool for the specified tool_name.
275 """
276 if not tool_name:
277 return BaseTool()
278
279 ctor = TOOL_REGISTRY.get(tool_name)
280 if ctor:
281 return ctor(device)
282 else:
283 print 'Unknown tool %s, available tools: %s' % (
284 tool_name, ', '.join(sorted(TOOL_REGISTRY.keys())))
285 sys.exit(1)
286
287 def PushFilesForTool(tool_name, device):
288 """Pushes the files required for |tool_name| to |device|.
289
290 Args:
291 tool_name: Name of the tool to create.
292 device: A DeviceUtils instance.
293 """
294 if not tool_name:
295 return
296
297 clazz = TOOL_REGISTRY.get(tool_name)
298 if clazz:
299 clazz.CopyFiles(device)
300 else:
301 print 'Unknown tool %s, available tools: %s' % (
302 tool_name, ', '.join(sorted(TOOL_REGISTRY.keys())))
303 sys.exit(1)
304
OLDNEW
« no previous file with comments | « build/android/pylib/utils/zip_utils.py ('k') | build/android/rezip.gyp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698