blob: 691c66b2bf2694659cddeb0d3897852e00d17443 [file] [log] [blame]
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001"""
2LLDB module which provides the abstract base class of lldb test case.
3
4The concrete subclass can override lldbtest.TesBase in order to inherit the
5common behavior for unitest.TestCase.setUp/tearDown implemented in this file.
6
7The subclass should override the attribute mydir in order for the python runtime
8to locate the individual test cases when running as part of a large test suite
9or when running each test case as a separate python invocation.
10
11./dotest.py provides a test driver which sets up the environment to run the
Johnny Chenc98892e2012-05-16 20:41:28 +000012entire of part of the test suite . Example:
Johnny Chenbf6ffa32010-07-03 03:41:59 +000013
Johnny Chenc98892e2012-05-16 20:41:28 +000014# Exercises the test suite in the types directory....
15/Volumes/data/lldb/svn/ToT/test $ ./dotest.py -A x86_64 types
Johnny Chen57b47382010-09-02 22:25:47 +000016...
Johnny Chend0190a62010-08-23 17:10:44 +000017
Johnny Chenc98892e2012-05-16 20:41:28 +000018Session logs for test failures/errors/unexpected successes will go into directory '2012-05-16-13_35_42'
19Command invoked: python ./dotest.py -A x86_64 types
20compilers=['clang']
Johnny Chend0190a62010-08-23 17:10:44 +000021
Johnny Chenc98892e2012-05-16 20:41:28 +000022Configuration: arch=x86_64 compiler=clang
Johnny Chend0190a62010-08-23 17:10:44 +000023----------------------------------------------------------------------
Johnny Chenc98892e2012-05-16 20:41:28 +000024Collected 72 tests
25
26........................................................................
27----------------------------------------------------------------------
28Ran 72 tests in 135.468s
Johnny Chend0190a62010-08-23 17:10:44 +000029
30OK
Johnny Chenbf6ffa32010-07-03 03:41:59 +000031$
32"""
33
Johnny Chen90312a82010-09-21 22:34:45 +000034import os, sys, traceback
Enrico Granata7e137e32012-10-24 18:14:21 +000035import os.path
Johnny Chenea88e942010-09-21 21:08:53 +000036import re
Daniel Malea69207462013-06-05 21:07:02 +000037import signal
Johnny Chen8952a2d2010-08-30 21:35:00 +000038from subprocess import *
Johnny Chen150c3cc2010-10-15 01:18:29 +000039import StringIO
Johnny Chenf2b70232010-08-25 18:49:48 +000040import time
Johnny Chena33a93c2010-08-30 23:08:52 +000041import types
Johnny Chen73258832010-08-05 23:42:46 +000042import unittest2
Johnny Chenbf6ffa32010-07-03 03:41:59 +000043import lldb
44
Johnny Chen707b3c92010-10-11 22:25:46 +000045# See also dotest.parseOptionsAndInitTestdirs(), where the environment variables
Johnny Chend2047fa2011-01-19 18:18:47 +000046# LLDB_COMMAND_TRACE and LLDB_DO_CLEANUP are set from '-t' and '-r dir' options.
Johnny Chen707b3c92010-10-11 22:25:46 +000047
48# By default, traceAlways is False.
Johnny Chen8d55a342010-08-31 17:42:54 +000049if "LLDB_COMMAND_TRACE" in os.environ and os.environ["LLDB_COMMAND_TRACE"]=="YES":
50 traceAlways = True
51else:
52 traceAlways = False
53
Johnny Chen707b3c92010-10-11 22:25:46 +000054# By default, doCleanup is True.
55if "LLDB_DO_CLEANUP" in os.environ and os.environ["LLDB_DO_CLEANUP"]=="NO":
56 doCleanup = False
57else:
58 doCleanup = True
59
Johnny Chen8d55a342010-08-31 17:42:54 +000060
Johnny Chen00778092010-08-09 22:01:17 +000061#
62# Some commonly used assert messages.
63#
64
Johnny Chenaa902922010-09-17 22:45:27 +000065COMMAND_FAILED_AS_EXPECTED = "Command has failed as expected"
66
Johnny Chen00778092010-08-09 22:01:17 +000067CURRENT_EXECUTABLE_SET = "Current executable set successfully"
68
Johnny Chen7d1d7532010-09-02 21:23:12 +000069PROCESS_IS_VALID = "Process is valid"
70
71PROCESS_KILLED = "Process is killed successfully"
72
Johnny Chend5f66fc2010-12-23 01:12:19 +000073PROCESS_EXITED = "Process exited successfully"
74
75PROCESS_STOPPED = "Process status should be stopped"
76
Johnny Chen5ee88192010-08-27 23:47:36 +000077RUN_SUCCEEDED = "Process is launched successfully"
Johnny Chen00778092010-08-09 22:01:17 +000078
Johnny Chen17941842010-08-09 23:44:24 +000079RUN_COMPLETED = "Process exited successfully"
Johnny Chen00778092010-08-09 22:01:17 +000080
Johnny Chen67af43f2010-10-05 19:27:32 +000081BACKTRACE_DISPLAYED_CORRECTLY = "Backtrace displayed correctly"
82
Johnny Chen17941842010-08-09 23:44:24 +000083BREAKPOINT_CREATED = "Breakpoint created successfully"
84
Johnny Chenf10af382010-12-04 00:07:24 +000085BREAKPOINT_STATE_CORRECT = "Breakpoint state is correct"
86
Johnny Chene76896c2010-08-17 21:33:31 +000087BREAKPOINT_PENDING_CREATED = "Pending breakpoint created successfully"
88
Johnny Chen17941842010-08-09 23:44:24 +000089BREAKPOINT_HIT_ONCE = "Breakpoint resolved with hit cout = 1"
Johnny Chen00778092010-08-09 22:01:17 +000090
Johnny Chen703dbd02010-09-30 17:06:24 +000091BREAKPOINT_HIT_TWICE = "Breakpoint resolved with hit cout = 2"
92
Johnny Chen164f1e12010-10-15 18:07:09 +000093BREAKPOINT_HIT_THRICE = "Breakpoint resolved with hit cout = 3"
94
Greg Clayton5db6b792012-10-24 18:24:14 +000095MISSING_EXPECTED_REGISTERS = "At least one expected register is unavailable."
96
Johnny Chen89109ed12011-06-27 20:05:23 +000097OBJECT_PRINTED_CORRECTLY = "Object printed correctly"
98
Johnny Chen5b3a3572010-12-09 18:22:12 +000099SOURCE_DISPLAYED_CORRECTLY = "Source code displayed correctly"
100
Johnny Chenc70b02a2010-09-22 23:00:20 +0000101STEP_OUT_SUCCEEDED = "Thread step-out succeeded"
102
Johnny Chen1691a162011-04-15 16:44:48 +0000103STOPPED_DUE_TO_EXC_BAD_ACCESS = "Process should be stopped due to bad access exception"
104
Ashok Thirumurthib4e51342013-05-17 15:35:15 +0000105STOPPED_DUE_TO_ASSERT = "Process should be stopped due to an assertion"
106
Johnny Chen5d6c4642010-11-10 23:46:38 +0000107STOPPED_DUE_TO_BREAKPOINT = "Process should be stopped due to breakpoint"
Johnny Chende0338b2010-11-10 20:20:06 +0000108
Johnny Chen5d6c4642010-11-10 23:46:38 +0000109STOPPED_DUE_TO_BREAKPOINT_WITH_STOP_REASON_AS = "%s, %s" % (
110 STOPPED_DUE_TO_BREAKPOINT, "instead, the actual stop reason is: '%s'")
Johnny Chen00778092010-08-09 22:01:17 +0000111
Johnny Chen2e431ce2010-10-20 18:38:48 +0000112STOPPED_DUE_TO_BREAKPOINT_CONDITION = "Stopped due to breakpoint condition"
113
Johnny Chen0a3d1ca2010-12-13 21:49:58 +0000114STOPPED_DUE_TO_BREAKPOINT_IGNORE_COUNT = "Stopped due to breakpoint and ignore count"
115
Johnny Chenc066ab42010-10-14 01:22:03 +0000116STOPPED_DUE_TO_SIGNAL = "Process state is stopped due to signal"
117
Johnny Chen00778092010-08-09 22:01:17 +0000118STOPPED_DUE_TO_STEP_IN = "Process state is stopped due to step in"
119
Johnny Chenf68cc122011-09-15 21:09:59 +0000120STOPPED_DUE_TO_WATCHPOINT = "Process should be stopped due to watchpoint"
121
Johnny Chen3c884a02010-08-24 22:07:56 +0000122DATA_TYPES_DISPLAYED_CORRECTLY = "Data type(s) displayed correctly"
123
Johnny Chen5fca8ca2010-08-26 20:04:17 +0000124VALID_BREAKPOINT = "Got a valid breakpoint"
125
Johnny Chen5bfb8ee2010-10-22 18:10:25 +0000126VALID_BREAKPOINT_LOCATION = "Got a valid breakpoint location"
127
Johnny Chen7209d84f2011-05-06 23:26:12 +0000128VALID_COMMAND_INTERPRETER = "Got a valid command interpreter"
129
Johnny Chen5ee88192010-08-27 23:47:36 +0000130VALID_FILESPEC = "Got a valid filespec"
131
Johnny Chen025d1b82010-12-08 01:25:21 +0000132VALID_MODULE = "Got a valid module"
133
Johnny Chen5fca8ca2010-08-26 20:04:17 +0000134VALID_PROCESS = "Got a valid process"
135
Johnny Chen025d1b82010-12-08 01:25:21 +0000136VALID_SYMBOL = "Got a valid symbol"
137
Johnny Chen5fca8ca2010-08-26 20:04:17 +0000138VALID_TARGET = "Got a valid target"
139
Matthew Gardinerc928de32014-10-22 07:22:56 +0000140VALID_PLATFORM = "Got a valid platform"
141
Johnny Chen15f247a2012-02-03 20:43:00 +0000142VALID_TYPE = "Got a valid type"
143
Johnny Chen5819ab42011-07-15 22:28:10 +0000144VALID_VARIABLE = "Got a valid variable"
145
Johnny Chen981463d2010-08-25 19:00:04 +0000146VARIABLES_DISPLAYED_CORRECTLY = "Variable(s) displayed correctly"
Johnny Chen00778092010-08-09 22:01:17 +0000147
Johnny Chenf68cc122011-09-15 21:09:59 +0000148WATCHPOINT_CREATED = "Watchpoint created successfully"
Johnny Chen5fca8ca2010-08-26 20:04:17 +0000149
Johnny Chenc0c67f22010-11-09 18:42:22 +0000150def CMD_MSG(str):
Johnny Chenaacf92e2011-05-31 22:16:51 +0000151 '''A generic "Command '%s' returns successfully" message generator.'''
Johnny Chenc0c67f22010-11-09 18:42:22 +0000152 return "Command '%s' returns successfully" % str
153
Johnny Chen3bc8ae42012-03-15 19:10:00 +0000154def COMPLETION_MSG(str_before, str_after):
Johnny Chen98aceb02012-01-20 23:02:51 +0000155 '''A generic message generator for the completion mechanism.'''
156 return "'%s' successfully completes to '%s'" % (str_before, str_after)
157
Johnny Chenc0c67f22010-11-09 18:42:22 +0000158def EXP_MSG(str, exe):
Johnny Chenaacf92e2011-05-31 22:16:51 +0000159 '''A generic "'%s' returns expected result" message generator if exe.
160 Otherwise, it generates "'%s' matches expected result" message.'''
Johnny Chenc0c67f22010-11-09 18:42:22 +0000161 return "'%s' %s expected result" % (str, 'returns' if exe else 'matches')
Johnny Chen17941842010-08-09 23:44:24 +0000162
Johnny Chen3343f042010-10-19 19:11:38 +0000163def SETTING_MSG(setting):
Johnny Chenaacf92e2011-05-31 22:16:51 +0000164 '''A generic "Value of setting '%s' is correct" message generator.'''
Johnny Chen3343f042010-10-19 19:11:38 +0000165 return "Value of setting '%s' is correct" % setting
166
Johnny Chen27c41232010-08-26 21:49:29 +0000167def EnvArray():
Johnny Chenaacf92e2011-05-31 22:16:51 +0000168 """Returns an env variable array from the os.environ map object."""
Johnny Chen27c41232010-08-26 21:49:29 +0000169 return map(lambda k,v: k+"="+v, os.environ.keys(), os.environ.values())
170
Johnny Chen47ceb032010-10-11 23:52:19 +0000171def line_number(filename, string_to_match):
172 """Helper function to return the line number of the first matched string."""
173 with open(filename, 'r') as f:
174 for i, line in enumerate(f):
175 if line.find(string_to_match) != -1:
176 # Found our match.
Johnny Chencd9b7772010-10-12 00:09:25 +0000177 return i+1
Johnny Chen1691a162011-04-15 16:44:48 +0000178 raise Exception("Unable to find '%s' within file %s" % (string_to_match, filename))
Johnny Chen47ceb032010-10-11 23:52:19 +0000179
Johnny Chen67af43f2010-10-05 19:27:32 +0000180def pointer_size():
181 """Return the pointer size of the host system."""
182 import ctypes
183 a_pointer = ctypes.c_void_p(0xffff)
184 return 8 * ctypes.sizeof(a_pointer)
185
Johnny Chen57816732012-02-09 02:01:59 +0000186def is_exe(fpath):
187 """Returns true if fpath is an executable."""
188 return os.path.isfile(fpath) and os.access(fpath, os.X_OK)
189
190def which(program):
191 """Returns the full path to a program; None otherwise."""
192 fpath, fname = os.path.split(program)
193 if fpath:
194 if is_exe(program):
195 return program
196 else:
197 for path in os.environ["PATH"].split(os.pathsep):
198 exe_file = os.path.join(path, program)
199 if is_exe(exe_file):
200 return exe_file
201 return None
202
Johnny Chen150c3cc2010-10-15 01:18:29 +0000203class recording(StringIO.StringIO):
204 """
205 A nice little context manager for recording the debugger interactions into
206 our session object. If trace flag is ON, it also emits the interactions
207 into the stderr.
208 """
209 def __init__(self, test, trace):
Johnny Chen690fcef2010-10-15 23:55:05 +0000210 """Create a StringIO instance; record the session obj and trace flag."""
Johnny Chen150c3cc2010-10-15 01:18:29 +0000211 StringIO.StringIO.__init__(self)
Johnny Chen0241f142011-08-16 22:06:17 +0000212 # The test might not have undergone the 'setUp(self)' phase yet, so that
213 # the attribute 'session' might not even exist yet.
Johnny Chenbfcf37f2011-08-16 17:06:45 +0000214 self.session = getattr(test, "session", None) if test else None
Johnny Chen150c3cc2010-10-15 01:18:29 +0000215 self.trace = trace
216
217 def __enter__(self):
218 """
219 Context management protocol on entry to the body of the with statement.
220 Just return the StringIO object.
221 """
222 return self
223
224 def __exit__(self, type, value, tb):
225 """
226 Context management protocol on exit from the body of the with statement.
227 If trace is ON, it emits the recordings into stderr. Always add the
228 recordings to our session object. And close the StringIO object, too.
229 """
230 if self.trace:
Johnny Chen690fcef2010-10-15 23:55:05 +0000231 print >> sys.stderr, self.getvalue()
232 if self.session:
233 print >> self.session, self.getvalue()
Johnny Chen150c3cc2010-10-15 01:18:29 +0000234 self.close()
235
Johnny Chen690fcef2010-10-15 23:55:05 +0000236# From 2.7's subprocess.check_output() convenience function.
Johnny Chenac77f3b2011-03-23 20:28:59 +0000237# Return a tuple (stdoutdata, stderrdata).
Zachary Turner9ef307b2014-07-22 16:19:29 +0000238def system(commands, **kwargs):
Johnny Chen8eb14a92011-11-16 22:44:28 +0000239 r"""Run an os command with arguments and return its output as a byte string.
Johnny Chen690fcef2010-10-15 23:55:05 +0000240
241 If the exit code was non-zero it raises a CalledProcessError. The
242 CalledProcessError object will have the return code in the returncode
243 attribute and output in the output attribute.
244
245 The arguments are the same as for the Popen constructor. Example:
246
247 >>> check_output(["ls", "-l", "/dev/null"])
248 'crw-rw-rw- 1 root root 1, 3 Oct 18 2007 /dev/null\n'
249
250 The stdout argument is not allowed as it is used internally.
251 To capture standard error in the result, use stderr=STDOUT.
252
253 >>> check_output(["/bin/sh", "-c",
254 ... "ls -l non_existent_file ; exit 0"],
255 ... stderr=STDOUT)
256 'ls: non_existent_file: No such file or directory\n'
257 """
258
259 # Assign the sender object to variable 'test' and remove it from kwargs.
260 test = kwargs.pop('sender', None)
261
Zachary Turner9ef307b2014-07-22 16:19:29 +0000262 separator = None
263 separator = " && " if os.name == "nt" else "; "
264 # [['make', 'clean', 'foo'], ['make', 'foo']] -> ['make clean foo', 'make foo']
265 commandList = [' '.join(x) for x in commands]
266 # ['make clean foo', 'make foo'] -> 'make clean foo; make foo'
267 shellCommand = separator.join(commandList)
268
Johnny Chen690fcef2010-10-15 23:55:05 +0000269 if 'stdout' in kwargs:
270 raise ValueError('stdout argument not allowed, it will be overridden.')
Zachary Turner9ef307b2014-07-22 16:19:29 +0000271 if 'shell' in kwargs and kwargs['shell']==False:
272 raise ValueError('shell=False not allowed')
273 process = Popen(shellCommand, stdout=PIPE, stderr=PIPE, shell=True, **kwargs)
Johnny Chen0bd8c312011-11-16 22:41:53 +0000274 pid = process.pid
Johnny Chen690fcef2010-10-15 23:55:05 +0000275 output, error = process.communicate()
276 retcode = process.poll()
277
Ed Maste6e496332014-08-05 20:33:17 +0000278 # Enable trace on failure return while tracking down FreeBSD buildbot issues
279 trace = traceAlways
280 if not trace and retcode and sys.platform.startswith("freebsd"):
281 trace = True
282
283 with recording(test, trace) as sbuf:
Johnny Chen690fcef2010-10-15 23:55:05 +0000284 print >> sbuf
Zachary Turner9ef307b2014-07-22 16:19:29 +0000285 print >> sbuf, "os command:", shellCommand
Johnny Chen0bd8c312011-11-16 22:41:53 +0000286 print >> sbuf, "with pid:", pid
Johnny Chen690fcef2010-10-15 23:55:05 +0000287 print >> sbuf, "stdout:", output
288 print >> sbuf, "stderr:", error
289 print >> sbuf, "retcode:", retcode
290 print >> sbuf
291
292 if retcode:
293 cmd = kwargs.get("args")
294 if cmd is None:
Zachary Turner9ef307b2014-07-22 16:19:29 +0000295 cmd = shellCommand
Johnny Chen690fcef2010-10-15 23:55:05 +0000296 raise CalledProcessError(retcode, cmd)
Johnny Chenac77f3b2011-03-23 20:28:59 +0000297 return (output, error)
Johnny Chen690fcef2010-10-15 23:55:05 +0000298
Johnny Chenab9c1dd2010-11-01 20:35:01 +0000299def getsource_if_available(obj):
300 """
301 Return the text of the source code for an object if available. Otherwise,
302 a print representation is returned.
303 """
304 import inspect
305 try:
306 return inspect.getsource(obj)
307 except:
308 return repr(obj)
309
Peter Collingbourne19f48d52011-06-20 19:06:20 +0000310def builder_module():
Ed Maste4d90f0f2013-07-25 13:24:34 +0000311 if sys.platform.startswith("freebsd"):
312 return __import__("builder_freebsd")
Peter Collingbourne19f48d52011-06-20 19:06:20 +0000313 return __import__("builder_" + sys.platform)
314
Johnny Chena74bb0a2011-08-01 18:46:13 +0000315#
316# Decorators for categorizing test cases.
317#
318
319from functools import wraps
320def python_api_test(func):
321 """Decorate the item as a Python API only test."""
322 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
323 raise Exception("@python_api_test can only be used to decorate a test method")
324 @wraps(func)
325 def wrapper(self, *args, **kwargs):
326 try:
327 if lldb.dont_do_python_api_test:
328 self.skipTest("python api tests")
329 except AttributeError:
330 pass
331 return func(self, *args, **kwargs)
332
333 # Mark this function as such to separate them from lldb command line tests.
334 wrapper.__python_api_test__ = True
335 return wrapper
336
Hafiz Abid Qadeer1cbac4e2014-11-25 10:41:57 +0000337def lldbmi_test(func):
338 """Decorate the item as a lldb-mi only test."""
339 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
340 raise Exception("@lldbmi_test can only be used to decorate a test method")
341 @wraps(func)
342 def wrapper(self, *args, **kwargs):
343 try:
344 if lldb.dont_do_lldbmi_test:
345 self.skipTest("lldb-mi tests")
346 except AttributeError:
347 pass
348 return func(self, *args, **kwargs)
349
350 # Mark this function as such to separate them from lldb command line tests.
351 wrapper.__lldbmi_test__ = True
352 return wrapper
353
Johnny Chena74bb0a2011-08-01 18:46:13 +0000354def benchmarks_test(func):
355 """Decorate the item as a benchmarks test."""
356 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
357 raise Exception("@benchmarks_test can only be used to decorate a test method")
358 @wraps(func)
359 def wrapper(self, *args, **kwargs):
360 try:
361 if not lldb.just_do_benchmarks_test:
362 self.skipTest("benchmarks tests")
363 except AttributeError:
364 pass
365 return func(self, *args, **kwargs)
366
367 # Mark this function as such to separate them from the regular tests.
368 wrapper.__benchmarks_test__ = True
369 return wrapper
370
Johnny Chenf1548d42012-04-06 00:56:05 +0000371def dsym_test(func):
372 """Decorate the item as a dsym test."""
373 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
374 raise Exception("@dsym_test can only be used to decorate a test method")
375 @wraps(func)
376 def wrapper(self, *args, **kwargs):
377 try:
378 if lldb.dont_do_dsym_test:
379 self.skipTest("dsym tests")
380 except AttributeError:
381 pass
382 return func(self, *args, **kwargs)
383
384 # Mark this function as such to separate them from the regular tests.
385 wrapper.__dsym_test__ = True
386 return wrapper
387
388def dwarf_test(func):
389 """Decorate the item as a dwarf test."""
390 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
391 raise Exception("@dwarf_test can only be used to decorate a test method")
392 @wraps(func)
393 def wrapper(self, *args, **kwargs):
394 try:
395 if lldb.dont_do_dwarf_test:
396 self.skipTest("dwarf tests")
397 except AttributeError:
398 pass
399 return func(self, *args, **kwargs)
400
401 # Mark this function as such to separate them from the regular tests.
402 wrapper.__dwarf_test__ = True
403 return wrapper
404
Todd Fialaa41d48c2014-04-28 04:49:40 +0000405def debugserver_test(func):
406 """Decorate the item as a debugserver test."""
407 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
408 raise Exception("@debugserver_test can only be used to decorate a test method")
409 @wraps(func)
410 def wrapper(self, *args, **kwargs):
411 try:
412 if lldb.dont_do_debugserver_test:
413 self.skipTest("debugserver tests")
414 except AttributeError:
415 pass
416 return func(self, *args, **kwargs)
417
418 # Mark this function as such to separate them from the regular tests.
419 wrapper.__debugserver_test__ = True
420 return wrapper
421
422def llgs_test(func):
423 """Decorate the item as a lldb-gdbserver test."""
424 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
425 raise Exception("@llgs_test can only be used to decorate a test method")
426 @wraps(func)
427 def wrapper(self, *args, **kwargs):
428 try:
429 if lldb.dont_do_llgs_test:
430 self.skipTest("llgs tests")
431 except AttributeError:
432 pass
433 return func(self, *args, **kwargs)
434
435 # Mark this function as such to separate them from the regular tests.
436 wrapper.__llgs_test__ = True
437 return wrapper
438
Daniel Maleae0f8f572013-08-26 23:57:52 +0000439def not_remote_testsuite_ready(func):
440 """Decorate the item as a test which is not ready yet for remote testsuite."""
441 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
442 raise Exception("@not_remote_testsuite_ready can only be used to decorate a test method")
443 @wraps(func)
444 def wrapper(self, *args, **kwargs):
445 try:
446 if lldb.lldbtest_remote_sandbox:
447 self.skipTest("not ready for remote testsuite")
448 except AttributeError:
449 pass
450 return func(self, *args, **kwargs)
451
452 # Mark this function as such to separate them from the regular tests.
453 wrapper.__not_ready_for_remote_testsuite_test__ = True
454 return wrapper
455
Ed Maste433790a2014-04-23 12:55:41 +0000456def expectedFailure(expected_fn, bugnumber=None):
457 def expectedFailure_impl(func):
458 @wraps(func)
459 def wrapper(*args, **kwargs):
Enrico Granata43f62132013-02-23 01:28:30 +0000460 from unittest2 import case
461 self = args[0]
Enrico Granata43f62132013-02-23 01:28:30 +0000462 try:
Ed Maste433790a2014-04-23 12:55:41 +0000463 func(*args, **kwargs)
Enrico Granata43f62132013-02-23 01:28:30 +0000464 except Exception:
Ed Maste433790a2014-04-23 12:55:41 +0000465 if expected_fn(self):
466 raise case._ExpectedFailure(sys.exc_info(), bugnumber)
Enrico Granata43f62132013-02-23 01:28:30 +0000467 else:
468 raise
Ed Maste433790a2014-04-23 12:55:41 +0000469 if expected_fn(self):
470 raise case._UnexpectedSuccess(sys.exc_info(), bugnumber)
471 return wrapper
Enrico Granatacf3ab582014-10-17 01:11:29 +0000472 if bugnumber:
473 if callable(bugnumber):
474 return expectedFailure_impl(bugnumber)
475 else:
476 return expectedFailure_impl
Ed Maste433790a2014-04-23 12:55:41 +0000477
478def expectedFailureCompiler(compiler, compiler_version=None, bugnumber=None):
479 if compiler_version is None:
480 compiler_version=['=', None]
481 def fn(self):
482 return compiler in self.getCompiler() and self.expectedCompilerVersion(compiler_version)
Enrico Granatacf3ab582014-10-17 01:11:29 +0000483 if bugnumber: return expectedFailure(fn, bugnumber)
Daniel Malea249287a2013-02-19 16:08:57 +0000484
Enrico Granata2b3a0c42013-02-23 01:35:21 +0000485def expectedFailureClang(bugnumber=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000486 if bugnumber: return expectedFailureCompiler('clang', None, bugnumber)
Ed Maste433790a2014-04-23 12:55:41 +0000487
488def expectedFailureGcc(bugnumber=None, compiler_version=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000489 if bugnumber: return expectedFailureCompiler('gcc', compiler_version, bugnumber)
Daniel Malea249287a2013-02-19 16:08:57 +0000490
Matt Kopec0de53f02013-03-15 19:10:12 +0000491def expectedFailureIcc(bugnumber=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000492 if bugnumber: return expectedFailureCompiler('icc', None, bugnumber)
Matt Kopec0de53f02013-03-15 19:10:12 +0000493
Ed Maste433790a2014-04-23 12:55:41 +0000494def expectedFailureArch(arch, bugnumber=None):
495 def fn(self):
496 return arch in self.getArchitecture()
Enrico Granatacf3ab582014-10-17 01:11:29 +0000497 if bugnumber: return expectedFailure(fn, bugnumber)
Daniel Malea249287a2013-02-19 16:08:57 +0000498
Enrico Granatae6cedc12013-02-23 01:05:23 +0000499def expectedFailurei386(bugnumber=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000500 if bugnumber: return expectedFailureArch('i386', bugnumber)
Johnny Chena33843f2011-12-22 21:14:31 +0000501
Matt Kopecee969f92013-09-26 23:30:59 +0000502def expectedFailurex86_64(bugnumber=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000503 if bugnumber: return expectedFailureArch('x86_64', bugnumber)
Ed Maste433790a2014-04-23 12:55:41 +0000504
505def expectedFailureOS(os, bugnumber=None, compilers=None):
506 def fn(self):
507 return os in sys.platform and self.expectedCompiler(compilers)
Enrico Granatacf3ab582014-10-17 01:11:29 +0000508 if bugnumber: return expectedFailure(fn, bugnumber)
Ed Maste433790a2014-04-23 12:55:41 +0000509
510def expectedFailureDarwin(bugnumber=None, compilers=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000511 if bugnumber: return expectedFailureOS('darwin', bugnumber, compilers)
Matt Kopecee969f92013-09-26 23:30:59 +0000512
Ed Maste24a7f7d2013-07-24 19:47:08 +0000513def expectedFailureFreeBSD(bugnumber=None, compilers=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000514 if bugnumber: return expectedFailureOS('freebsd', bugnumber, compilers)
Ed Maste24a7f7d2013-07-24 19:47:08 +0000515
Ashok Thirumurthic97a6082013-05-17 20:15:07 +0000516def expectedFailureLinux(bugnumber=None, compilers=None):
Enrico Granatacf3ab582014-10-17 01:11:29 +0000517 if bugnumber: return expectedFailureOS('linux', bugnumber, compilers)
Matt Kopece9ea0da2013-05-07 19:29:28 +0000518
Zachary Turner80c2c602014-12-09 19:28:00 +0000519def expectedFailureWindows(bugnumber=None, compilers=None):
520 if bugnumber: return expectedFailureOS('win32', bugnumber, compilers)
521
Chaoren Lin72b8f052015-02-03 01:51:18 +0000522def expectedFailureLLGS(bugnumber=None, compilers=None):
523 def fn(self):
524 return 'PLATFORM_LINUX_FORCE_LLGS_LOCAL' in os.environ and self.expectedCompiler(compilers)
525 if bugnumber: return expectedFailure(fn, bugnumber)
526
Greg Clayton12514562013-12-05 22:22:32 +0000527def skipIfRemote(func):
528 """Decorate the item to skip tests if testing remotely."""
529 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
530 raise Exception("@skipIfRemote can only be used to decorate a test method")
531 @wraps(func)
532 def wrapper(*args, **kwargs):
533 from unittest2 import case
534 if lldb.remote_platform:
535 self = args[0]
536 self.skipTest("skip on remote platform")
537 else:
538 func(*args, **kwargs)
539 return wrapper
540
541def skipIfRemoteDueToDeadlock(func):
542 """Decorate the item to skip tests if testing remotely due to the test deadlocking."""
543 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
544 raise Exception("@skipIfRemote can only be used to decorate a test method")
545 @wraps(func)
546 def wrapper(*args, **kwargs):
547 from unittest2 import case
548 if lldb.remote_platform:
549 self = args[0]
550 self.skipTest("skip on remote platform (deadlocks)")
551 else:
552 func(*args, **kwargs)
553 return wrapper
554
Ed Maste09617a52013-06-25 19:11:36 +0000555def skipIfFreeBSD(func):
556 """Decorate the item to skip tests that should be skipped on FreeBSD."""
557 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
558 raise Exception("@skipIfFreeBSD can only be used to decorate a test method")
559 @wraps(func)
560 def wrapper(*args, **kwargs):
561 from unittest2 import case
562 self = args[0]
563 platform = sys.platform
564 if "freebsd" in platform:
565 self.skipTest("skip on FreeBSD")
566 else:
567 func(*args, **kwargs)
568 return wrapper
569
Daniel Maleae8bdd1f2013-05-15 18:48:32 +0000570def skipIfLinux(func):
Daniel Malea93aec0f2012-11-23 21:59:29 +0000571 """Decorate the item to skip tests that should be skipped on Linux."""
572 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
Daniel Maleae8bdd1f2013-05-15 18:48:32 +0000573 raise Exception("@skipIfLinux can only be used to decorate a test method")
Daniel Malea93aec0f2012-11-23 21:59:29 +0000574 @wraps(func)
575 def wrapper(*args, **kwargs):
576 from unittest2 import case
577 self = args[0]
578 platform = sys.platform
579 if "linux" in platform:
580 self.skipTest("skip on linux")
581 else:
Jim Ingham9732e082012-11-27 01:21:28 +0000582 func(*args, **kwargs)
Daniel Malea93aec0f2012-11-23 21:59:29 +0000583 return wrapper
584
Enrico Granatab633e432014-10-06 21:37:06 +0000585def skipIfNoSBHeaders(func):
586 """Decorate the item to mark tests that should be skipped when LLDB is built with no SB API headers."""
587 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
Ed Maste59cca5d2014-10-07 01:57:52 +0000588 raise Exception("@skipIfNoSBHeaders can only be used to decorate a test method")
Enrico Granatab633e432014-10-06 21:37:06 +0000589 @wraps(func)
590 def wrapper(*args, **kwargs):
591 from unittest2 import case
592 self = args[0]
Shawn Best181b09b2014-11-08 00:04:04 +0000593 if sys.platform.startswith("darwin"):
594 header = os.path.join(self.lib_dir, 'LLDB.framework', 'Versions','Current','Headers','LLDB.h')
595 else:
596 header = os.path.join(os.environ["LLDB_SRC"], "include", "lldb", "API", "LLDB.h")
Enrico Granatab633e432014-10-06 21:37:06 +0000597 platform = sys.platform
Enrico Granatab633e432014-10-06 21:37:06 +0000598 if not os.path.exists(header):
599 self.skipTest("skip because LLDB.h header not found")
600 else:
601 func(*args, **kwargs)
602 return wrapper
603
Zachary Turnerc7826522014-08-13 17:44:53 +0000604def skipIfWindows(func):
605 """Decorate the item to skip tests that should be skipped on Windows."""
606 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
607 raise Exception("@skipIfWindows can only be used to decorate a test method")
608 @wraps(func)
609 def wrapper(*args, **kwargs):
610 from unittest2 import case
611 self = args[0]
612 platform = sys.platform
613 if "win32" in platform:
614 self.skipTest("skip on Windows")
615 else:
616 func(*args, **kwargs)
617 return wrapper
618
Daniel Maleab3d41a22013-07-09 00:08:01 +0000619def skipIfDarwin(func):
620 """Decorate the item to skip tests that should be skipped on Darwin."""
621 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
Ed Mastea7f13f02013-07-09 00:24:52 +0000622 raise Exception("@skipIfDarwin can only be used to decorate a test method")
Daniel Maleab3d41a22013-07-09 00:08:01 +0000623 @wraps(func)
624 def wrapper(*args, **kwargs):
625 from unittest2 import case
626 self = args[0]
627 platform = sys.platform
628 if "darwin" in platform:
629 self.skipTest("skip on darwin")
630 else:
631 func(*args, **kwargs)
632 return wrapper
633
634
Daniel Malea48359902013-05-14 20:48:54 +0000635def skipIfLinuxClang(func):
636 """Decorate the item to skip tests that should be skipped if building on
637 Linux with clang.
638 """
639 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
640 raise Exception("@skipIfLinuxClang can only be used to decorate a test method")
641 @wraps(func)
642 def wrapper(*args, **kwargs):
643 from unittest2 import case
644 self = args[0]
645 compiler = self.getCompiler()
646 platform = sys.platform
647 if "clang" in compiler and "linux" in platform:
648 self.skipTest("skipping because Clang is used on Linux")
649 else:
650 func(*args, **kwargs)
651 return wrapper
652
Daniel Maleabe230792013-01-24 23:52:09 +0000653def skipIfGcc(func):
654 """Decorate the item to skip tests that should be skipped if building with gcc ."""
655 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
Daniel Malea0aea0162013-02-27 17:29:46 +0000656 raise Exception("@skipIfGcc can only be used to decorate a test method")
Daniel Maleabe230792013-01-24 23:52:09 +0000657 @wraps(func)
658 def wrapper(*args, **kwargs):
659 from unittest2 import case
660 self = args[0]
661 compiler = self.getCompiler()
662 if "gcc" in compiler:
663 self.skipTest("skipping because gcc is the test compiler")
664 else:
665 func(*args, **kwargs)
666 return wrapper
667
Matt Kopec0de53f02013-03-15 19:10:12 +0000668def skipIfIcc(func):
669 """Decorate the item to skip tests that should be skipped if building with icc ."""
670 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
671 raise Exception("@skipIfIcc can only be used to decorate a test method")
672 @wraps(func)
673 def wrapper(*args, **kwargs):
674 from unittest2 import case
675 self = args[0]
676 compiler = self.getCompiler()
677 if "icc" in compiler:
678 self.skipTest("skipping because icc is the test compiler")
679 else:
680 func(*args, **kwargs)
681 return wrapper
682
Daniel Malea55faa402013-05-02 21:44:31 +0000683def skipIfi386(func):
684 """Decorate the item to skip tests that should be skipped if building 32-bit."""
685 if isinstance(func, type) and issubclass(func, unittest2.TestCase):
686 raise Exception("@skipIfi386 can only be used to decorate a test method")
687 @wraps(func)
688 def wrapper(*args, **kwargs):
689 from unittest2 import case
690 self = args[0]
691 if "i386" == self.getArchitecture():
692 self.skipTest("skipping because i386 is not a supported architecture")
693 else:
694 func(*args, **kwargs)
695 return wrapper
696
697
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +0000698class _PlatformContext(object):
699 """Value object class which contains platform-specific options."""
700
701 def __init__(self, shlib_environment_var, shlib_prefix, shlib_extension):
702 self.shlib_environment_var = shlib_environment_var
703 self.shlib_prefix = shlib_prefix
704 self.shlib_extension = shlib_extension
705
706
Johnny Chena74bb0a2011-08-01 18:46:13 +0000707class Base(unittest2.TestCase):
Johnny Chen8334dad2010-10-22 23:15:46 +0000708 """
Johnny Chena74bb0a2011-08-01 18:46:13 +0000709 Abstract base for performing lldb (see TestBase) or other generic tests (see
710 BenchBase for one example). lldbtest.Base works with the test driver to
711 accomplish things.
712
Johnny Chen8334dad2010-10-22 23:15:46 +0000713 """
Enrico Granata5020f952012-10-24 21:42:49 +0000714
Enrico Granata19186272012-10-24 21:44:48 +0000715 # The concrete subclass should override this attribute.
716 mydir = None
Johnny Chenbf6ffa32010-07-03 03:41:59 +0000717
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000718 # Keep track of the old current working directory.
719 oldcwd = None
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +0000720
Greg Clayton4570d3e2013-12-10 23:19:29 +0000721 @staticmethod
722 def compute_mydir(test_file):
723 '''Subclasses should call this function to correctly calculate the required "mydir" attribute as follows:
724
725 mydir = TestBase.compute_mydir(__file__)'''
726 test_dir = os.path.dirname(test_file)
727 return test_dir[len(os.environ["LLDB_TEST"])+1:]
728
Johnny Chenfb4264c2011-08-01 19:50:58 +0000729 def TraceOn(self):
730 """Returns True if we are in trace mode (tracing detailed test execution)."""
731 return traceAlways
Greg Clayton4570d3e2013-12-10 23:19:29 +0000732
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000733 @classmethod
734 def setUpClass(cls):
Johnny Chenda884342010-10-01 22:59:49 +0000735 """
736 Python unittest framework class setup fixture.
737 Do current directory manipulation.
738 """
739
Johnny Chenf02ec122010-07-03 20:41:42 +0000740 # Fail fast if 'mydir' attribute is not overridden.
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000741 if not cls.mydir or len(cls.mydir) == 0:
Johnny Chenf02ec122010-07-03 20:41:42 +0000742 raise Exception("Subclasses must override the 'mydir' attribute.")
Enrico Granata7e137e32012-10-24 18:14:21 +0000743
Johnny Chenbf6ffa32010-07-03 03:41:59 +0000744 # Save old working directory.
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000745 cls.oldcwd = os.getcwd()
Johnny Chenbf6ffa32010-07-03 03:41:59 +0000746
747 # Change current working directory if ${LLDB_TEST} is defined.
748 # See also dotest.py which sets up ${LLDB_TEST}.
749 if ("LLDB_TEST" in os.environ):
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000750 if traceAlways:
Johnny Chen703dbd02010-09-30 17:06:24 +0000751 print >> sys.stderr, "Change dir to:", os.path.join(os.environ["LLDB_TEST"], cls.mydir)
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000752 os.chdir(os.path.join(os.environ["LLDB_TEST"], cls.mydir))
753
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +0000754 # Set platform context.
755 if sys.platform.startswith('darwin'):
756 cls.platformContext = _PlatformContext('DYLD_LIBRARY_PATH', 'lib', 'dylib')
757 elif sys.platform.startswith('linux') or sys.platform.startswith('freebsd'):
758 cls.platformContext = _PlatformContext('LD_LIBRARY_PATH', 'lib', 'so')
Zachary Turnerbe40b2f2014-12-02 21:32:44 +0000759 else:
760 cls.platformContext = None
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +0000761
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000762 @classmethod
763 def tearDownClass(cls):
Johnny Chenda884342010-10-01 22:59:49 +0000764 """
765 Python unittest framework class teardown fixture.
766 Do class-wide cleanup.
767 """
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000768
Johnny Chen0fddfb22011-11-17 19:57:27 +0000769 if doCleanup and not lldb.skip_build_and_cleanup:
Johnny Chen707b3c92010-10-11 22:25:46 +0000770 # First, let's do the platform-specific cleanup.
Peter Collingbourne19f48d52011-06-20 19:06:20 +0000771 module = builder_module()
Johnny Chen707b3c92010-10-11 22:25:46 +0000772 if not module.cleanup():
773 raise Exception("Don't know how to do cleanup")
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000774
Johnny Chen707b3c92010-10-11 22:25:46 +0000775 # Subclass might have specific cleanup function defined.
776 if getattr(cls, "classCleanup", None):
777 if traceAlways:
778 print >> sys.stderr, "Call class-specific cleanup function for class:", cls
779 try:
780 cls.classCleanup()
781 except:
782 exc_type, exc_value, exc_tb = sys.exc_info()
783 traceback.print_exception(exc_type, exc_value, exc_tb)
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000784
785 # Restore old working directory.
786 if traceAlways:
Johnny Chen703dbd02010-09-30 17:06:24 +0000787 print >> sys.stderr, "Restore dir to:", cls.oldcwd
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000788 os.chdir(cls.oldcwd)
789
Johnny Chena74bb0a2011-08-01 18:46:13 +0000790 @classmethod
791 def skipLongRunningTest(cls):
792 """
793 By default, we skip long running test case.
794 This can be overridden by passing '-l' to the test driver (dotest.py).
795 """
796 if "LLDB_SKIP_LONG_RUNNING_TEST" in os.environ and "NO" == os.environ["LLDB_SKIP_LONG_RUNNING_TEST"]:
797 return False
798 else:
799 return True
Johnny Chened492022011-06-21 00:53:00 +0000800
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000801 def setUp(self):
Johnny Chenfb4264c2011-08-01 19:50:58 +0000802 """Fixture for unittest test case setup.
803
804 It works with the test driver to conditionally skip tests and does other
805 initializations."""
Johnny Chen1a9f4dd2010-09-16 01:53:04 +0000806 #import traceback
807 #traceback.print_stack()
Johnny Chenbf6ffa32010-07-03 03:41:59 +0000808
Daniel Malea9115f072013-08-06 15:02:32 +0000809 if "LIBCXX_PATH" in os.environ:
810 self.libcxxPath = os.environ["LIBCXX_PATH"]
811 else:
812 self.libcxxPath = None
813
Johnny Chenaaa82ff2011-08-02 22:54:37 +0000814 if "LLDB_EXEC" in os.environ:
815 self.lldbExec = os.environ["LLDB_EXEC"]
Johnny Chend890bfc2011-08-26 00:00:01 +0000816 else:
817 self.lldbExec = None
Hafiz Abid Qadeer1cbac4e2014-11-25 10:41:57 +0000818 if "LLDBMI_EXEC" in os.environ:
819 self.lldbMiExec = os.environ["LLDBMI_EXEC"]
820 else:
821 self.lldbMiExec = None
822 self.dont_do_lldbmi_test = True
Johnny Chend890bfc2011-08-26 00:00:01 +0000823 if "LLDB_HERE" in os.environ:
824 self.lldbHere = os.environ["LLDB_HERE"]
825 else:
826 self.lldbHere = None
Johnny Chenebe51722011-10-07 19:21:09 +0000827 # If we spawn an lldb process for test (via pexpect), do not load the
828 # init file unless told otherwise.
829 if "NO_LLDBINIT" in os.environ and "NO" == os.environ["NO_LLDBINIT"]:
830 self.lldbOption = ""
831 else:
832 self.lldbOption = "--no-lldbinit"
Johnny Chenaaa82ff2011-08-02 22:54:37 +0000833
Johnny Chen985e7402011-08-01 21:13:26 +0000834 # Assign the test method name to self.testMethodName.
835 #
836 # For an example of the use of this attribute, look at test/types dir.
837 # There are a bunch of test cases under test/types and we don't want the
838 # module cacheing subsystem to be confused with executable name "a.out"
839 # used for all the test cases.
840 self.testMethodName = self._testMethodName
841
Johnny Chenf3e22ac2010-12-10 18:52:10 +0000842 # Python API only test is decorated with @python_api_test,
843 # which also sets the "__python_api_test__" attribute of the
844 # function object to True.
Johnny Chen4533dad2011-05-31 23:21:42 +0000845 try:
846 if lldb.just_do_python_api_test:
847 testMethod = getattr(self, self._testMethodName)
848 if getattr(testMethod, "__python_api_test__", False):
849 pass
850 else:
Johnny Chen5ccbccf2011-07-30 01:39:58 +0000851 self.skipTest("non python api test")
852 except AttributeError:
853 pass
854
Hafiz Abid Qadeer1cbac4e2014-11-25 10:41:57 +0000855 # lldb-mi only test is decorated with @lldbmi_test,
856 # which also sets the "__lldbmi_test__" attribute of the
857 # function object to True.
858 try:
859 if lldb.just_do_lldbmi_test:
860 testMethod = getattr(self, self._testMethodName)
861 if getattr(testMethod, "__lldbmi_test__", False):
862 pass
863 else:
864 self.skipTest("non lldb-mi test")
865 except AttributeError:
866 pass
867
Johnny Chen5ccbccf2011-07-30 01:39:58 +0000868 # Benchmarks test is decorated with @benchmarks_test,
869 # which also sets the "__benchmarks_test__" attribute of the
870 # function object to True.
871 try:
872 if lldb.just_do_benchmarks_test:
873 testMethod = getattr(self, self._testMethodName)
874 if getattr(testMethod, "__benchmarks_test__", False):
875 pass
876 else:
877 self.skipTest("non benchmarks test")
Johnny Chen4533dad2011-05-31 23:21:42 +0000878 except AttributeError:
879 pass
Johnny Chenf3e22ac2010-12-10 18:52:10 +0000880
Johnny Chen985e7402011-08-01 21:13:26 +0000881 # This is for the case of directly spawning 'lldb'/'gdb' and interacting
882 # with it using pexpect.
883 self.child = None
884 self.child_prompt = "(lldb) "
885 # If the child is interacting with the embedded script interpreter,
886 # there are two exits required during tear down, first to quit the
887 # embedded script interpreter and second to quit the lldb command
888 # interpreter.
889 self.child_in_script_interpreter = False
890
Johnny Chenfb4264c2011-08-01 19:50:58 +0000891 # These are for customized teardown cleanup.
892 self.dict = None
893 self.doTearDownCleanup = False
894 # And in rare cases where there are multiple teardown cleanups.
895 self.dicts = []
896 self.doTearDownCleanups = False
897
Daniel Malea2dd69bb2013-02-15 21:21:52 +0000898 # List of spawned subproces.Popen objects
899 self.subprocesses = []
900
Daniel Malea69207462013-06-05 21:07:02 +0000901 # List of forked process PIDs
902 self.forkedProcessPids = []
903
Johnny Chenfb4264c2011-08-01 19:50:58 +0000904 # Create a string buffer to record the session info, to be dumped into a
905 # test case specific file if test failure is encountered.
906 self.session = StringIO.StringIO()
907
908 # Optimistically set __errored__, __failed__, __expected__ to False
909 # initially. If the test errored/failed, the session info
910 # (self.session) is then dumped into a session specific file for
911 # diagnosis.
912 self.__errored__ = False
913 self.__failed__ = False
914 self.__expected__ = False
915 # We are also interested in unexpected success.
916 self.__unexpected__ = False
Johnny Chenf79b0762011-08-16 00:48:58 +0000917 # And skipped tests.
918 self.__skipped__ = False
Johnny Chenfb4264c2011-08-01 19:50:58 +0000919
920 # See addTearDownHook(self, hook) which allows the client to add a hook
921 # function to be run during tearDown() time.
922 self.hooks = []
923
924 # See HideStdout(self).
925 self.sys_stdout_hidden = False
926
Zachary Turnerbe40b2f2014-12-02 21:32:44 +0000927 if self.platformContext:
928 # set environment variable names for finding shared libraries
929 self.dylibPath = self.platformContext.shlib_environment_var
Daniel Malea179ff292012-11-26 21:21:11 +0000930
Johnny Chen2a808582011-10-19 16:48:07 +0000931 def runHooks(self, child=None, child_prompt=None, use_cmd_api=False):
Johnny Chena737ba52011-10-19 01:06:21 +0000932 """Perform the run hooks to bring lldb debugger to the desired state.
933
Johnny Chen2a808582011-10-19 16:48:07 +0000934 By default, expect a pexpect spawned child and child prompt to be
935 supplied (use_cmd_api=False). If use_cmd_api is true, ignore the child
936 and child prompt and use self.runCmd() to run the hooks one by one.
937
Johnny Chena737ba52011-10-19 01:06:21 +0000938 Note that child is a process spawned by pexpect.spawn(). If not, your
939 test case is mostly likely going to fail.
940
941 See also dotest.py where lldb.runHooks are processed/populated.
942 """
943 if not lldb.runHooks:
944 self.skipTest("No runhooks specified for lldb, skip the test")
Johnny Chen2a808582011-10-19 16:48:07 +0000945 if use_cmd_api:
946 for hook in lldb.runhooks:
947 self.runCmd(hook)
948 else:
949 if not child or not child_prompt:
950 self.fail("Both child and child_prompt need to be defined.")
951 for hook in lldb.runHooks:
952 child.sendline(hook)
953 child.expect_exact(child_prompt)
Johnny Chena737ba52011-10-19 01:06:21 +0000954
Daniel Malea249287a2013-02-19 16:08:57 +0000955 def setAsync(self, value):
956 """ Sets async mode to True/False and ensures it is reset after the testcase completes."""
957 old_async = self.dbg.GetAsync()
958 self.dbg.SetAsync(value)
959 self.addTearDownHook(lambda: self.dbg.SetAsync(old_async))
960
Daniel Malea2dd69bb2013-02-15 21:21:52 +0000961 def cleanupSubprocesses(self):
962 # Ensure any subprocesses are cleaned up
963 for p in self.subprocesses:
964 if p.poll() == None:
965 p.terminate()
966 del p
967 del self.subprocesses[:]
Daniel Malea69207462013-06-05 21:07:02 +0000968 # Ensure any forked processes are cleaned up
969 for pid in self.forkedProcessPids:
970 if os.path.exists("/proc/" + str(pid)):
971 os.kill(pid, signal.SIGTERM)
Daniel Malea2dd69bb2013-02-15 21:21:52 +0000972
973 def spawnSubprocess(self, executable, args=[]):
974 """ Creates a subprocess.Popen object with the specified executable and arguments,
975 saves it in self.subprocesses, and returns the object.
976 NOTE: if using this function, ensure you also call:
977
978 self.addTearDownHook(self.cleanupSubprocesses)
979
980 otherwise the test suite will leak processes.
981 """
982
983 # Don't display the stdout if not in TraceOn() mode.
984 proc = Popen([executable] + args,
985 stdout = open(os.devnull) if not self.TraceOn() else None,
986 stdin = PIPE)
987 self.subprocesses.append(proc)
988 return proc
989
Daniel Malea69207462013-06-05 21:07:02 +0000990 def forkSubprocess(self, executable, args=[]):
991 """ Fork a subprocess with its own group ID.
992 NOTE: if using this function, ensure you also call:
993
994 self.addTearDownHook(self.cleanupSubprocesses)
995
996 otherwise the test suite will leak processes.
997 """
998 child_pid = os.fork()
999 if child_pid == 0:
1000 # If more I/O support is required, this can be beefed up.
1001 fd = os.open(os.devnull, os.O_RDWR)
Daniel Malea69207462013-06-05 21:07:02 +00001002 os.dup2(fd, 1)
1003 os.dup2(fd, 2)
1004 # This call causes the child to have its of group ID
1005 os.setpgid(0,0)
1006 os.execvp(executable, [executable] + args)
1007 # Give the child time to get through the execvp() call
1008 time.sleep(0.1)
1009 self.forkedProcessPids.append(child_pid)
1010 return child_pid
1011
Johnny Chenfb4264c2011-08-01 19:50:58 +00001012 def HideStdout(self):
1013 """Hide output to stdout from the user.
1014
1015 During test execution, there might be cases where we don't want to show the
1016 standard output to the user. For example,
1017
1018 self.runCmd(r'''sc print "\n\n\tHello!\n"''')
1019
1020 tests whether command abbreviation for 'script' works or not. There is no
1021 need to show the 'Hello' output to the user as long as the 'script' command
1022 succeeds and we are not in TraceOn() mode (see the '-t' option).
1023
1024 In this case, the test method calls self.HideStdout(self) to redirect the
1025 sys.stdout to a null device, and restores the sys.stdout upon teardown.
1026
1027 Note that you should only call this method at most once during a test case
1028 execution. Any subsequent call has no effect at all."""
1029 if self.sys_stdout_hidden:
1030 return
1031
1032 self.sys_stdout_hidden = True
1033 old_stdout = sys.stdout
1034 sys.stdout = open(os.devnull, 'w')
1035 def restore_stdout():
1036 sys.stdout = old_stdout
1037 self.addTearDownHook(restore_stdout)
1038
1039 # =======================================================================
1040 # Methods for customized teardown cleanups as well as execution of hooks.
1041 # =======================================================================
1042
1043 def setTearDownCleanup(self, dictionary=None):
1044 """Register a cleanup action at tearDown() time with a dictinary"""
1045 self.dict = dictionary
1046 self.doTearDownCleanup = True
1047
1048 def addTearDownCleanup(self, dictionary):
1049 """Add a cleanup action at tearDown() time with a dictinary"""
1050 self.dicts.append(dictionary)
1051 self.doTearDownCleanups = True
1052
1053 def addTearDownHook(self, hook):
1054 """
1055 Add a function to be run during tearDown() time.
1056
1057 Hooks are executed in a first come first serve manner.
1058 """
1059 if callable(hook):
1060 with recording(self, traceAlways) as sbuf:
1061 print >> sbuf, "Adding tearDown hook:", getsource_if_available(hook)
1062 self.hooks.append(hook)
Enrico Granataab0e8312014-11-05 21:31:57 +00001063
1064 return self
Johnny Chenfb4264c2011-08-01 19:50:58 +00001065
Jim Inghamda3a3862014-10-16 23:02:14 +00001066 def deletePexpectChild(self):
Johnny Chen985e7402011-08-01 21:13:26 +00001067 # This is for the case of directly spawning 'lldb' and interacting with it
1068 # using pexpect.
Johnny Chen985e7402011-08-01 21:13:26 +00001069 if self.child and self.child.isalive():
Zachary Turner9ef307b2014-07-22 16:19:29 +00001070 import pexpect
Johnny Chen985e7402011-08-01 21:13:26 +00001071 with recording(self, traceAlways) as sbuf:
1072 print >> sbuf, "tearing down the child process...."
Johnny Chen985e7402011-08-01 21:13:26 +00001073 try:
Daniel Maleac9a0ec32013-02-22 00:41:26 +00001074 if self.child_in_script_interpreter:
1075 self.child.sendline('quit()')
1076 self.child.expect_exact(self.child_prompt)
1077 self.child.sendline('settings set interpreter.prompt-on-quit false')
1078 self.child.sendline('quit')
Johnny Chen985e7402011-08-01 21:13:26 +00001079 self.child.expect(pexpect.EOF)
Hafiz Abid Qadeera73d1ce2015-01-26 12:03:05 +00001080 except (ValueError, OSError, pexpect.ExceptionPexpect):
Daniel Maleac9a0ec32013-02-22 00:41:26 +00001081 # child is already terminated
Johnny Chen985e7402011-08-01 21:13:26 +00001082 pass
Shawn Besteb3e9052014-11-06 17:52:15 +00001083 finally:
1084 # Give it one final blow to make sure the child is terminated.
1085 self.child.close()
Jim Inghamda3a3862014-10-16 23:02:14 +00001086
1087 def tearDown(self):
1088 """Fixture for unittest test case teardown."""
1089 #import traceback
1090 #traceback.print_stack()
1091
1092 self.deletePexpectChild()
1093
Johnny Chenfb4264c2011-08-01 19:50:58 +00001094 # Check and run any hook functions.
1095 for hook in reversed(self.hooks):
1096 with recording(self, traceAlways) as sbuf:
1097 print >> sbuf, "Executing tearDown hook:", getsource_if_available(hook)
Enrico Granataab0e8312014-11-05 21:31:57 +00001098 import inspect
1099 hook_argc = len(inspect.getargspec(hook).args)
Enrico Granata6e0566c2014-11-17 19:00:20 +00001100 if hook_argc == 0 or getattr(hook,'im_self',None):
Enrico Granataab0e8312014-11-05 21:31:57 +00001101 hook()
1102 elif hook_argc == 1:
1103 hook(self)
1104 else:
1105 hook() # try the plain call and hope it works
Johnny Chenfb4264c2011-08-01 19:50:58 +00001106
1107 del self.hooks
1108
1109 # Perform registered teardown cleanup.
1110 if doCleanup and self.doTearDownCleanup:
Johnny Chen0fddfb22011-11-17 19:57:27 +00001111 self.cleanup(dictionary=self.dict)
Johnny Chenfb4264c2011-08-01 19:50:58 +00001112
1113 # In rare cases where there are multiple teardown cleanups added.
1114 if doCleanup and self.doTearDownCleanups:
Johnny Chenfb4264c2011-08-01 19:50:58 +00001115 if self.dicts:
1116 for dict in reversed(self.dicts):
Johnny Chen0fddfb22011-11-17 19:57:27 +00001117 self.cleanup(dictionary=dict)
Johnny Chenfb4264c2011-08-01 19:50:58 +00001118
1119 # Decide whether to dump the session info.
1120 self.dumpSessionInfo()
1121
1122 # =========================================================
1123 # Various callbacks to allow introspection of test progress
1124 # =========================================================
1125
1126 def markError(self):
1127 """Callback invoked when an error (unexpected exception) errored."""
1128 self.__errored__ = True
1129 with recording(self, False) as sbuf:
1130 # False because there's no need to write "ERROR" to the stderr twice.
1131 # Once by the Python unittest framework, and a second time by us.
1132 print >> sbuf, "ERROR"
1133
1134 def markFailure(self):
1135 """Callback invoked when a failure (test assertion failure) occurred."""
1136 self.__failed__ = True
1137 with recording(self, False) as sbuf:
1138 # False because there's no need to write "FAIL" to the stderr twice.
1139 # Once by the Python unittest framework, and a second time by us.
1140 print >> sbuf, "FAIL"
1141
Enrico Granatae6cedc12013-02-23 01:05:23 +00001142 def markExpectedFailure(self,err,bugnumber):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001143 """Callback invoked when an expected failure/error occurred."""
1144 self.__expected__ = True
1145 with recording(self, False) as sbuf:
1146 # False because there's no need to write "expected failure" to the
1147 # stderr twice.
1148 # Once by the Python unittest framework, and a second time by us.
Enrico Granatae6cedc12013-02-23 01:05:23 +00001149 if bugnumber == None:
1150 print >> sbuf, "expected failure"
1151 else:
1152 print >> sbuf, "expected failure (problem id:" + str(bugnumber) + ")"
Johnny Chenfb4264c2011-08-01 19:50:58 +00001153
Johnny Chenc5cc6252011-08-15 23:09:08 +00001154 def markSkippedTest(self):
1155 """Callback invoked when a test is skipped."""
1156 self.__skipped__ = True
1157 with recording(self, False) as sbuf:
1158 # False because there's no need to write "skipped test" to the
1159 # stderr twice.
1160 # Once by the Python unittest framework, and a second time by us.
1161 print >> sbuf, "skipped test"
1162
Enrico Granatae6cedc12013-02-23 01:05:23 +00001163 def markUnexpectedSuccess(self, bugnumber):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001164 """Callback invoked when an unexpected success occurred."""
1165 self.__unexpected__ = True
1166 with recording(self, False) as sbuf:
1167 # False because there's no need to write "unexpected success" to the
1168 # stderr twice.
1169 # Once by the Python unittest framework, and a second time by us.
Enrico Granatae6cedc12013-02-23 01:05:23 +00001170 if bugnumber == None:
1171 print >> sbuf, "unexpected success"
1172 else:
1173 print >> sbuf, "unexpected success (problem id:" + str(bugnumber) + ")"
Johnny Chenfb4264c2011-08-01 19:50:58 +00001174
Greg Clayton70995582015-01-07 22:25:50 +00001175 def getRerunArgs(self):
1176 return " -f %s.%s" % (self.__class__.__name__, self._testMethodName)
1177
Johnny Chenfb4264c2011-08-01 19:50:58 +00001178 def dumpSessionInfo(self):
1179 """
1180 Dump the debugger interactions leading to a test error/failure. This
1181 allows for more convenient postmortem analysis.
1182
1183 See also LLDBTestResult (dotest.py) which is a singlton class derived
1184 from TextTestResult and overwrites addError, addFailure, and
1185 addExpectedFailure methods to allow us to to mark the test instance as
1186 such.
1187 """
1188
1189 # We are here because self.tearDown() detected that this test instance
1190 # either errored or failed. The lldb.test_result singleton contains
1191 # two lists (erros and failures) which get populated by the unittest
1192 # framework. Look over there for stack trace information.
1193 #
1194 # The lists contain 2-tuples of TestCase instances and strings holding
1195 # formatted tracebacks.
1196 #
1197 # See http://docs.python.org/library/unittest.html#unittest.TestResult.
1198 if self.__errored__:
1199 pairs = lldb.test_result.errors
1200 prefix = 'Error'
1201 elif self.__failed__:
1202 pairs = lldb.test_result.failures
1203 prefix = 'Failure'
1204 elif self.__expected__:
1205 pairs = lldb.test_result.expectedFailures
1206 prefix = 'ExpectedFailure'
Johnny Chenc5cc6252011-08-15 23:09:08 +00001207 elif self.__skipped__:
1208 prefix = 'SkippedTest'
Johnny Chenfb4264c2011-08-01 19:50:58 +00001209 elif self.__unexpected__:
1210 prefix = "UnexpectedSuccess"
1211 else:
1212 # Simply return, there's no session info to dump!
1213 return
1214
Johnny Chenc5cc6252011-08-15 23:09:08 +00001215 if not self.__unexpected__ and not self.__skipped__:
Johnny Chenfb4264c2011-08-01 19:50:58 +00001216 for test, traceback in pairs:
1217 if test is self:
1218 print >> self.session, traceback
1219
Johnny Chen8082a002011-08-11 00:16:28 +00001220 testMethod = getattr(self, self._testMethodName)
1221 if getattr(testMethod, "__benchmarks_test__", False):
1222 benchmarks = True
1223 else:
1224 benchmarks = False
1225
Johnny Chenfb4264c2011-08-01 19:50:58 +00001226 dname = os.path.join(os.environ["LLDB_TEST"],
1227 os.environ["LLDB_SESSION_DIRNAME"])
1228 if not os.path.isdir(dname):
1229 os.mkdir(dname)
Zachary Turner756acba2014-10-14 21:54:14 +00001230 compiler = self.getCompiler()
1231 if compiler[1] == ':':
1232 compiler = compiler[2:]
1233
1234 fname = os.path.join(dname, "%s-%s-%s-%s.log" % (prefix, self.getArchitecture(), "_".join(compiler.split(os.path.sep)), self.id()))
Johnny Chenfb4264c2011-08-01 19:50:58 +00001235 with open(fname, "w") as f:
1236 import datetime
1237 print >> f, "Session info generated @", datetime.datetime.now().ctime()
1238 print >> f, self.session.getvalue()
1239 print >> f, "To rerun this test, issue the following command from the 'test' directory:\n"
Greg Clayton70995582015-01-07 22:25:50 +00001240 print >> f, "./dotest.py %s -v %s %s" % (self.getRunOptions(),
1241 ('+b' if benchmarks else '-t'),
1242 self.getRerunArgs())
Johnny Chenfb4264c2011-08-01 19:50:58 +00001243
1244 # ====================================================
1245 # Config. methods supported through a plugin interface
1246 # (enables reading of the current test configuration)
1247 # ====================================================
1248
1249 def getArchitecture(self):
1250 """Returns the architecture in effect the test suite is running with."""
1251 module = builder_module()
1252 return module.getArchitecture()
1253
1254 def getCompiler(self):
1255 """Returns the compiler in effect the test suite is running with."""
1256 module = builder_module()
1257 return module.getCompiler()
1258
Oleksiy Vyalovdc4067c2014-11-26 18:30:04 +00001259 def getCompilerBinary(self):
1260 """Returns the compiler binary the test suite is running with."""
1261 return self.getCompiler().split()[0]
1262
Daniel Malea0aea0162013-02-27 17:29:46 +00001263 def getCompilerVersion(self):
1264 """ Returns a string that represents the compiler version.
1265 Supports: llvm, clang.
1266 """
1267 from lldbutil import which
1268 version = 'unknown'
1269
Oleksiy Vyalovdc4067c2014-11-26 18:30:04 +00001270 compiler = self.getCompilerBinary()
Zachary Turner9ef307b2014-07-22 16:19:29 +00001271 version_output = system([[which(compiler), "-v"]])[1]
Daniel Malea0aea0162013-02-27 17:29:46 +00001272 for line in version_output.split(os.linesep):
Greg Clayton2a844b72013-03-06 02:34:51 +00001273 m = re.search('version ([0-9\.]+)', line)
Daniel Malea0aea0162013-02-27 17:29:46 +00001274 if m:
1275 version = m.group(1)
1276 return version
1277
Daniel Maleaadaaec92013-08-06 20:51:41 +00001278 def isIntelCompiler(self):
1279 """ Returns true if using an Intel (ICC) compiler, false otherwise. """
1280 return any([x in self.getCompiler() for x in ["icc", "icpc", "icl"]])
1281
Ashok Thirumurthi3b037282013-06-06 14:23:31 +00001282 def expectedCompilerVersion(self, compiler_version):
1283 """Returns True iff compiler_version[1] matches the current compiler version.
1284 Use compiler_version[0] to specify the operator used to determine if a match has occurred.
1285 Any operator other than the following defaults to an equality test:
1286 '>', '>=', "=>", '<', '<=', '=<', '!=', "!" or 'not'
1287 """
Ashok Thirumurthic97a6082013-05-17 20:15:07 +00001288 if (compiler_version == None):
1289 return True
1290 operator = str(compiler_version[0])
1291 version = compiler_version[1]
1292
1293 if (version == None):
1294 return True
1295 if (operator == '>'):
1296 return self.getCompilerVersion() > version
1297 if (operator == '>=' or operator == '=>'):
1298 return self.getCompilerVersion() >= version
1299 if (operator == '<'):
1300 return self.getCompilerVersion() < version
1301 if (operator == '<=' or operator == '=<'):
1302 return self.getCompilerVersion() <= version
1303 if (operator == '!=' or operator == '!' or operator == 'not'):
1304 return str(version) not in str(self.getCompilerVersion())
1305 return str(version) in str(self.getCompilerVersion())
1306
1307 def expectedCompiler(self, compilers):
Ashok Thirumurthi3b037282013-06-06 14:23:31 +00001308 """Returns True iff any element of compilers is a sub-string of the current compiler."""
Ashok Thirumurthic97a6082013-05-17 20:15:07 +00001309 if (compilers == None):
1310 return True
Ashok Thirumurthi3b037282013-06-06 14:23:31 +00001311
1312 for compiler in compilers:
1313 if compiler in self.getCompiler():
1314 return True
1315
1316 return False
Ashok Thirumurthic97a6082013-05-17 20:15:07 +00001317
Johnny Chenfb4264c2011-08-01 19:50:58 +00001318 def getRunOptions(self):
1319 """Command line option for -A and -C to run this test again, called from
1320 self.dumpSessionInfo()."""
1321 arch = self.getArchitecture()
1322 comp = self.getCompiler()
Johnny Chenb7bdd102011-08-24 19:48:51 +00001323 if arch:
1324 option_str = "-A " + arch
Johnny Chenfb4264c2011-08-01 19:50:58 +00001325 else:
Johnny Chenb7bdd102011-08-24 19:48:51 +00001326 option_str = ""
1327 if comp:
Johnny Chen531c0852012-03-16 20:44:00 +00001328 option_str += " -C " + comp
Johnny Chenb7bdd102011-08-24 19:48:51 +00001329 return option_str
Johnny Chenfb4264c2011-08-01 19:50:58 +00001330
1331 # ==================================================
1332 # Build methods supported through a plugin interface
1333 # ==================================================
1334
Ed Mastec97323e2014-04-01 18:47:58 +00001335 def getstdlibFlag(self):
1336 """ Returns the proper -stdlib flag, or empty if not required."""
1337 if sys.platform.startswith("darwin") or sys.platform.startswith("freebsd"):
1338 stdlibflag = "-stdlib=libc++"
1339 else:
1340 stdlibflag = ""
1341 return stdlibflag
1342
Matt Kopec7663b3a2013-09-25 17:44:00 +00001343 def getstdFlag(self):
1344 """ Returns the proper stdflag. """
Daniel Malea55faa402013-05-02 21:44:31 +00001345 if "gcc" in self.getCompiler() and "4.6" in self.getCompilerVersion():
Daniel Malea0b7c6112013-05-06 19:31:31 +00001346 stdflag = "-std=c++0x"
Daniel Malea55faa402013-05-02 21:44:31 +00001347 else:
1348 stdflag = "-std=c++11"
Matt Kopec7663b3a2013-09-25 17:44:00 +00001349 return stdflag
1350
1351 def buildDriver(self, sources, exe_name):
1352 """ Platform-specific way to build a program that links with LLDB (via the liblldb.so
1353 or LLDB.framework).
1354 """
1355
1356 stdflag = self.getstdFlag()
Ed Mastec97323e2014-04-01 18:47:58 +00001357 stdlibflag = self.getstdlibFlag()
Daniel Malea55faa402013-05-02 21:44:31 +00001358
1359 if sys.platform.startswith("darwin"):
1360 dsym = os.path.join(self.lib_dir, 'LLDB.framework', 'LLDB')
1361 d = {'CXX_SOURCES' : sources,
1362 'EXE' : exe_name,
Ed Mastec97323e2014-04-01 18:47:58 +00001363 'CFLAGS_EXTRAS' : "%s %s" % (stdflag, stdlibflag),
Daniel Malea55faa402013-05-02 21:44:31 +00001364 'FRAMEWORK_INCLUDES' : "-F%s" % self.lib_dir,
Stefanus Du Toit04004442013-07-30 19:19:49 +00001365 'LD_EXTRAS' : "%s -Wl,-rpath,%s" % (dsym, self.lib_dir),
Daniel Malea55faa402013-05-02 21:44:31 +00001366 }
Ed Maste372c24d2013-07-25 21:02:34 +00001367 elif sys.platform.startswith('freebsd') or sys.platform.startswith("linux") or os.environ.get('LLDB_BUILD_TYPE') == 'Makefile':
Daniel Malea55faa402013-05-02 21:44:31 +00001368 d = {'CXX_SOURCES' : sources,
1369 'EXE' : exe_name,
Ed Mastec97323e2014-04-01 18:47:58 +00001370 'CFLAGS_EXTRAS' : "%s %s -I%s" % (stdflag, stdlibflag, os.path.join(os.environ["LLDB_SRC"], "include")),
Daniel Malea55faa402013-05-02 21:44:31 +00001371 'LD_EXTRAS' : "-L%s -llldb" % self.lib_dir}
1372 if self.TraceOn():
1373 print "Building LLDB Driver (%s) from sources %s" % (exe_name, sources)
1374
1375 self.buildDefault(dictionary=d)
1376
Matt Kopec7663b3a2013-09-25 17:44:00 +00001377 def buildLibrary(self, sources, lib_name):
1378 """Platform specific way to build a default library. """
1379
1380 stdflag = self.getstdFlag()
1381
1382 if sys.platform.startswith("darwin"):
1383 dsym = os.path.join(self.lib_dir, 'LLDB.framework', 'LLDB')
1384 d = {'DYLIB_CXX_SOURCES' : sources,
1385 'DYLIB_NAME' : lib_name,
1386 'CFLAGS_EXTRAS' : "%s -stdlib=libc++" % stdflag,
1387 'FRAMEWORK_INCLUDES' : "-F%s" % self.lib_dir,
1388 'LD_EXTRAS' : "%s -Wl,-rpath,%s -dynamiclib" % (dsym, self.lib_dir),
1389 }
1390 elif sys.platform.startswith('freebsd') or sys.platform.startswith("linux") or os.environ.get('LLDB_BUILD_TYPE') == 'Makefile':
1391 d = {'DYLIB_CXX_SOURCES' : sources,
1392 'DYLIB_NAME' : lib_name,
1393 'CFLAGS_EXTRAS' : "%s -I%s -fPIC" % (stdflag, os.path.join(os.environ["LLDB_SRC"], "include")),
1394 'LD_EXTRAS' : "-shared -L%s -llldb" % self.lib_dir}
1395 if self.TraceOn():
1396 print "Building LLDB Library (%s) from sources %s" % (lib_name, sources)
1397
1398 self.buildDefault(dictionary=d)
1399
Daniel Malea55faa402013-05-02 21:44:31 +00001400 def buildProgram(self, sources, exe_name):
1401 """ Platform specific way to build an executable from C/C++ sources. """
1402 d = {'CXX_SOURCES' : sources,
1403 'EXE' : exe_name}
1404 self.buildDefault(dictionary=d)
1405
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001406 def buildDefault(self, architecture=None, compiler=None, dictionary=None, clean=True):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001407 """Platform specific way to build the default binaries."""
Johnny Chen0fddfb22011-11-17 19:57:27 +00001408 if lldb.skip_build_and_cleanup:
1409 return
Johnny Chenfb4264c2011-08-01 19:50:58 +00001410 module = builder_module()
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001411 if not module.buildDefault(self, architecture, compiler, dictionary, clean):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001412 raise Exception("Don't know how to build default binary")
1413
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001414 def buildDsym(self, architecture=None, compiler=None, dictionary=None, clean=True):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001415 """Platform specific way to build binaries with dsym info."""
Johnny Chen0fddfb22011-11-17 19:57:27 +00001416 if lldb.skip_build_and_cleanup:
1417 return
Johnny Chenfb4264c2011-08-01 19:50:58 +00001418 module = builder_module()
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001419 if not module.buildDsym(self, architecture, compiler, dictionary, clean):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001420 raise Exception("Don't know how to build binary with dsym")
1421
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001422 def buildDwarf(self, architecture=None, compiler=None, dictionary=None, clean=True):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001423 """Platform specific way to build binaries with dwarf maps."""
Johnny Chen0fddfb22011-11-17 19:57:27 +00001424 if lldb.skip_build_and_cleanup:
1425 return
Johnny Chenfb4264c2011-08-01 19:50:58 +00001426 module = builder_module()
Johnny Chenfdc80a5c2012-02-01 01:49:50 +00001427 if not module.buildDwarf(self, architecture, compiler, dictionary, clean):
Johnny Chenfb4264c2011-08-01 19:50:58 +00001428 raise Exception("Don't know how to build binary with dwarf")
Johnny Chena74bb0a2011-08-01 18:46:13 +00001429
Oleksiy Vyalov49b71c62015-01-22 20:03:21 +00001430 def signBinary(self, binary_path):
1431 if sys.platform.startswith("darwin"):
1432 codesign_cmd = "codesign --force --sign lldb_codesign %s" % (binary_path)
1433 call(codesign_cmd, shell=True)
1434
Kuba Breckabeed8212014-09-04 01:03:18 +00001435 def findBuiltClang(self):
1436 """Tries to find and use Clang from the build directory as the compiler (instead of the system compiler)."""
1437 paths_to_try = [
1438 "llvm-build/Release+Asserts/x86_64/Release+Asserts/bin/clang",
1439 "llvm-build/Debug+Asserts/x86_64/Debug+Asserts/bin/clang",
1440 "llvm-build/Release/x86_64/Release/bin/clang",
1441 "llvm-build/Debug/x86_64/Debug/bin/clang",
1442 ]
1443 lldb_root_path = os.path.join(os.path.dirname(__file__), "..")
1444 for p in paths_to_try:
1445 path = os.path.join(lldb_root_path, p)
1446 if os.path.exists(path):
1447 return path
1448
1449 return os.environ["CC"]
1450
Daniel Malea9115f072013-08-06 15:02:32 +00001451 def getBuildFlags(self, use_cpp11=True, use_libcxx=False, use_libstdcxx=False, use_pthreads=True):
Andrew Kaylor93132f52013-05-28 23:04:25 +00001452 """ Returns a dictionary (which can be provided to build* functions above) which
1453 contains OS-specific build flags.
1454 """
1455 cflags = ""
Daniel Malea9115f072013-08-06 15:02:32 +00001456
1457 # On Mac OS X, unless specifically requested to use libstdc++, use libc++
1458 if not use_libstdcxx and sys.platform.startswith('darwin'):
1459 use_libcxx = True
1460
1461 if use_libcxx and self.libcxxPath:
1462 cflags += "-stdlib=libc++ "
1463 if self.libcxxPath:
1464 libcxxInclude = os.path.join(self.libcxxPath, "include")
1465 libcxxLib = os.path.join(self.libcxxPath, "lib")
1466 if os.path.isdir(libcxxInclude) and os.path.isdir(libcxxLib):
1467 cflags += "-nostdinc++ -I%s -L%s -Wl,-rpath,%s " % (libcxxInclude, libcxxLib, libcxxLib)
1468
Andrew Kaylor93132f52013-05-28 23:04:25 +00001469 if use_cpp11:
1470 cflags += "-std="
1471 if "gcc" in self.getCompiler() and "4.6" in self.getCompilerVersion():
1472 cflags += "c++0x"
1473 else:
1474 cflags += "c++11"
Ed Mastedbd59502014-02-02 19:24:15 +00001475 if sys.platform.startswith("darwin") or sys.platform.startswith("freebsd"):
Andrew Kaylor93132f52013-05-28 23:04:25 +00001476 cflags += " -stdlib=libc++"
1477 elif "clang" in self.getCompiler():
1478 cflags += " -stdlib=libstdc++"
1479
1480 if use_pthreads:
1481 ldflags = "-lpthread"
1482
1483 return {'CFLAGS_EXTRAS' : cflags,
1484 'LD_EXTRAS' : ldflags,
1485 }
1486
Johnny Chen9f4f5d92011-08-12 20:19:22 +00001487 def cleanup(self, dictionary=None):
1488 """Platform specific way to do cleanup after build."""
Johnny Chen0fddfb22011-11-17 19:57:27 +00001489 if lldb.skip_build_and_cleanup:
1490 return
Johnny Chen9f4f5d92011-08-12 20:19:22 +00001491 module = builder_module()
1492 if not module.cleanup(self, dictionary):
Johnny Chen0fddfb22011-11-17 19:57:27 +00001493 raise Exception("Don't know how to do cleanup with dictionary: "+dictionary)
Johnny Chen9f4f5d92011-08-12 20:19:22 +00001494
Daniel Malea55faa402013-05-02 21:44:31 +00001495 def getLLDBLibraryEnvVal(self):
1496 """ Returns the path that the OS-specific library search environment variable
1497 (self.dylibPath) should be set to in order for a program to find the LLDB
1498 library. If an environment variable named self.dylibPath is already set,
1499 the new path is appended to it and returned.
1500 """
1501 existing_library_path = os.environ[self.dylibPath] if self.dylibPath in os.environ else None
1502 if existing_library_path:
1503 return "%s:%s" % (existing_library_path, self.lib_dir)
1504 elif sys.platform.startswith("darwin"):
1505 return os.path.join(self.lib_dir, 'LLDB.framework')
1506 else:
1507 return self.lib_dir
Johnny Chena74bb0a2011-08-01 18:46:13 +00001508
Ed Maste437f8f62013-09-09 14:04:04 +00001509 def getLibcPlusPlusLibs(self):
1510 if sys.platform.startswith('freebsd'):
1511 return ['libc++.so.1']
1512 else:
1513 return ['libc++.1.dylib','libc++abi.dylib']
1514
Johnny Chena74bb0a2011-08-01 18:46:13 +00001515class TestBase(Base):
1516 """
1517 This abstract base class is meant to be subclassed. It provides default
1518 implementations for setUpClass(), tearDownClass(), setUp(), and tearDown(),
1519 among other things.
1520
1521 Important things for test class writers:
1522
1523 - Overwrite the mydir class attribute, otherwise your test class won't
1524 run. It specifies the relative directory to the top level 'test' so
1525 the test harness can change to the correct working directory before
1526 running your test.
1527
1528 - The setUp method sets up things to facilitate subsequent interactions
1529 with the debugger as part of the test. These include:
1530 - populate the test method name
1531 - create/get a debugger set with synchronous mode (self.dbg)
1532 - get the command interpreter from with the debugger (self.ci)
1533 - create a result object for use with the command interpreter
1534 (self.res)
1535 - plus other stuffs
1536
1537 - The tearDown method tries to perform some necessary cleanup on behalf
1538 of the test to return the debugger to a good state for the next test.
1539 These include:
1540 - execute any tearDown hooks registered by the test method with
1541 TestBase.addTearDownHook(); examples can be found in
1542 settings/TestSettings.py
1543 - kill the inferior process associated with each target, if any,
1544 and, then delete the target from the debugger's target list
1545 - perform build cleanup before running the next test method in the
1546 same test class; examples of registering for this service can be
1547 found in types/TestIntegerTypes.py with the call:
1548 - self.setTearDownCleanup(dictionary=d)
1549
1550 - Similarly setUpClass and tearDownClass perform classwise setup and
1551 teardown fixtures. The tearDownClass method invokes a default build
1552 cleanup for the entire test class; also, subclasses can implement the
1553 classmethod classCleanup(cls) to perform special class cleanup action.
1554
1555 - The instance methods runCmd and expect are used heavily by existing
1556 test cases to send a command to the command interpreter and to perform
1557 string/pattern matching on the output of such command execution. The
1558 expect method also provides a mode to peform string/pattern matching
1559 without running a command.
1560
1561 - The build methods buildDefault, buildDsym, and buildDwarf are used to
1562 build the binaries used during a particular test scenario. A plugin
1563 should be provided for the sys.platform running the test suite. The
1564 Mac OS X implementation is located in plugins/darwin.py.
1565 """
1566
1567 # Maximum allowed attempts when launching the inferior process.
1568 # Can be overridden by the LLDB_MAX_LAUNCH_COUNT environment variable.
1569 maxLaunchCount = 3;
1570
1571 # Time to wait before the next launching attempt in second(s).
1572 # Can be overridden by the LLDB_TIME_WAIT_NEXT_LAUNCH environment variable.
1573 timeWaitNextLaunch = 1.0;
1574
1575 def doDelay(self):
1576 """See option -w of dotest.py."""
1577 if ("LLDB_WAIT_BETWEEN_TEST_CASES" in os.environ and
1578 os.environ["LLDB_WAIT_BETWEEN_TEST_CASES"] == 'YES'):
1579 waitTime = 1.0
1580 if "LLDB_TIME_WAIT_BETWEEN_TEST_CASES" in os.environ:
1581 waitTime = float(os.environ["LLDB_TIME_WAIT_BETWEEN_TEST_CASES"])
1582 time.sleep(waitTime)
1583
Enrico Granata165f8af2012-09-21 19:10:53 +00001584 # Returns the list of categories to which this test case belongs
1585 # by default, look for a ".categories" file, and read its contents
1586 # if no such file exists, traverse the hierarchy - we guarantee
1587 # a .categories to exist at the top level directory so we do not end up
1588 # looping endlessly - subclasses are free to define their own categories
1589 # in whatever way makes sense to them
1590 def getCategories(self):
1591 import inspect
1592 import os.path
1593 folder = inspect.getfile(self.__class__)
1594 folder = os.path.dirname(folder)
1595 while folder != '/':
1596 categories_file_name = os.path.join(folder,".categories")
1597 if os.path.exists(categories_file_name):
1598 categories_file = open(categories_file_name,'r')
1599 categories = categories_file.readline()
1600 categories_file.close()
1601 categories = str.replace(categories,'\n','')
1602 categories = str.replace(categories,'\r','')
1603 return categories.split(',')
1604 else:
1605 folder = os.path.dirname(folder)
1606 continue
1607
Johnny Chena74bb0a2011-08-01 18:46:13 +00001608 def setUp(self):
1609 #import traceback
1610 #traceback.print_stack()
1611
1612 # Works with the test driver to conditionally skip tests via decorators.
1613 Base.setUp(self)
1614
Johnny Chena74bb0a2011-08-01 18:46:13 +00001615 try:
1616 if lldb.blacklist:
1617 className = self.__class__.__name__
1618 classAndMethodName = "%s.%s" % (className, self._testMethodName)
1619 if className in lldb.blacklist:
1620 self.skipTest(lldb.blacklist.get(className))
1621 elif classAndMethodName in lldb.blacklist:
1622 self.skipTest(lldb.blacklist.get(classAndMethodName))
1623 except AttributeError:
1624 pass
1625
Johnny Chened492022011-06-21 00:53:00 +00001626 # Insert some delay between successive test cases if specified.
1627 self.doDelay()
Johnny Chen0ed37c92010-10-07 02:04:14 +00001628
Johnny Chenf2b70232010-08-25 18:49:48 +00001629 if "LLDB_MAX_LAUNCH_COUNT" in os.environ:
1630 self.maxLaunchCount = int(os.environ["LLDB_MAX_LAUNCH_COUNT"])
1631
Johnny Chen430eb762010-10-19 16:00:42 +00001632 if "LLDB_TIME_WAIT_NEXT_LAUNCH" in os.environ:
Johnny Chen4921b112010-11-29 20:20:34 +00001633 self.timeWaitNextLaunch = float(os.environ["LLDB_TIME_WAIT_NEXT_LAUNCH"])
Johnny Chenf2b70232010-08-25 18:49:48 +00001634
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001635 # Create the debugger instance if necessary.
1636 try:
1637 self.dbg = lldb.DBG
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001638 except AttributeError:
1639 self.dbg = lldb.SBDebugger.Create()
Johnny Chenf02ec122010-07-03 20:41:42 +00001640
Johnny Chen3cd1e552011-05-25 19:06:18 +00001641 if not self.dbg:
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001642 raise Exception('Invalid debugger instance')
1643
Daniel Maleae0f8f572013-08-26 23:57:52 +00001644 #
1645 # Warning: MAJOR HACK AHEAD!
1646 # If we are running testsuite remotely (by checking lldb.lldbtest_remote_sandbox),
1647 # redefine the self.dbg.CreateTarget(filename) method to execute a "file filename"
1648 # command, instead. See also runCmd() where it decorates the "file filename" call
1649 # with additional functionality when running testsuite remotely.
1650 #
1651 if lldb.lldbtest_remote_sandbox:
1652 def DecoratedCreateTarget(arg):
1653 self.runCmd("file %s" % arg)
1654 target = self.dbg.GetSelectedTarget()
1655 #
Greg Claytonc6947512013-12-13 19:18:59 +00001656 # SBtarget.LaunchSimple () currently not working for remote platform?
Daniel Maleae0f8f572013-08-26 23:57:52 +00001657 # johnny @ 04/23/2012
1658 #
1659 def DecoratedLaunchSimple(argv, envp, wd):
1660 self.runCmd("run")
1661 return target.GetProcess()
1662 target.LaunchSimple = DecoratedLaunchSimple
1663
1664 return target
1665 self.dbg.CreateTarget = DecoratedCreateTarget
1666 if self.TraceOn():
1667 print "self.dbg.Create is redefined to:\n%s" % getsource_if_available(DecoratedCreateTarget)
1668
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001669 # We want our debugger to be synchronous.
1670 self.dbg.SetAsync(False)
1671
1672 # Retrieve the associated command interpreter instance.
1673 self.ci = self.dbg.GetCommandInterpreter()
1674 if not self.ci:
1675 raise Exception('Could not get the command interpreter')
1676
1677 # And the result object.
1678 self.res = lldb.SBCommandReturnObject()
1679
Johnny Chen44d24972012-04-16 18:55:15 +00001680 # Run global pre-flight code, if defined via the config file.
1681 if lldb.pre_flight:
1682 lldb.pre_flight(self)
1683
Greg Claytonfb909312013-11-23 01:58:15 +00001684 if lldb.remote_platform:
1685 #remote_test_dir = os.path.join(lldb.remote_platform_working_dir, self.mydir)
Greg Clayton5fb8f792013-12-02 19:35:49 +00001686 remote_test_dir = os.path.join(lldb.remote_platform_working_dir,
1687 self.getArchitecture(),
1688 str(self.test_number),
1689 self.mydir)
Greg Claytonfb909312013-11-23 01:58:15 +00001690 error = lldb.remote_platform.MakeDirectory(remote_test_dir, 0700)
1691 if error.Success():
Greg Claytonfb909312013-11-23 01:58:15 +00001692 lldb.remote_platform.SetWorkingDirectory(remote_test_dir)
1693 else:
1694 print "error: making remote directory '%s': %s" % (remote_test_dir, error)
1695
Greg Clayton35c91342014-11-17 18:40:27 +00001696 def registerSharedLibrariesWithTarget(self, target, shlibs):
1697 '''If we are remotely running the test suite, register the shared libraries with the target so they get uploaded, otherwise do nothing
1698
1699 Any modules in the target that have their remote install file specification set will
1700 get uploaded to the remote host. This function registers the local copies of the
1701 shared libraries with the target and sets their remote install locations so they will
1702 be uploaded when the target is run.
1703 '''
Zachary Turnerbe40b2f2014-12-02 21:32:44 +00001704 if not shlibs or not self.platformContext:
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +00001705 return None
Greg Clayton35c91342014-11-17 18:40:27 +00001706
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +00001707 shlib_environment_var = self.platformContext.shlib_environment_var
1708 shlib_prefix = self.platformContext.shlib_prefix
1709 shlib_extension = '.' + self.platformContext.shlib_extension
1710
1711 working_dir = self.get_process_working_directory()
1712 environment = ['%s=%s' % (shlib_environment_var, working_dir)]
1713 # Add any shared libraries to our target if remote so they get
1714 # uploaded into the working directory on the remote side
1715 for name in shlibs:
1716 # The path can be a full path to a shared library, or a make file name like "Foo" for
1717 # "libFoo.dylib" or "libFoo.so", or "Foo.so" for "Foo.so" or "libFoo.so", or just a
1718 # basename like "libFoo.so". So figure out which one it is and resolve the local copy
1719 # of the shared library accordingly
1720 if os.path.exists(name):
1721 local_shlib_path = name # name is the full path to the local shared library
1722 else:
1723 # Check relative names
1724 local_shlib_path = os.path.join(os.getcwd(), shlib_prefix + name + shlib_extension)
1725 if not os.path.exists(local_shlib_path):
1726 local_shlib_path = os.path.join(os.getcwd(), name + shlib_extension)
Greg Clayton35c91342014-11-17 18:40:27 +00001727 if not os.path.exists(local_shlib_path):
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +00001728 local_shlib_path = os.path.join(os.getcwd(), name)
Greg Clayton35c91342014-11-17 18:40:27 +00001729
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +00001730 # Make sure we found the local shared library in the above code
1731 self.assertTrue(os.path.exists(local_shlib_path))
1732
1733 # Add the shared library to our target
1734 shlib_module = target.AddModule(local_shlib_path, None, None, None)
1735 if lldb.remote_platform:
Greg Clayton35c91342014-11-17 18:40:27 +00001736 # We must set the remote install location if we want the shared library
1737 # to get uploaded to the remote target
1738 remote_shlib_path = os.path.join(lldb.remote_platform.GetWorkingDirectory(), os.path.basename(local_shlib_path))
1739 shlib_module.SetRemoteInstallFileSpec(lldb.SBFileSpec(remote_shlib_path, False))
Oleksiy Vyalova3ff6af2014-12-01 23:21:18 +00001740
1741 return environment
1742
Enrico Granata44818162012-10-24 01:23:57 +00001743 # utility methods that tests can use to access the current objects
1744 def target(self):
1745 if not self.dbg:
1746 raise Exception('Invalid debugger instance')
1747 return self.dbg.GetSelectedTarget()
1748
1749 def process(self):
1750 if not self.dbg:
1751 raise Exception('Invalid debugger instance')
1752 return self.dbg.GetSelectedTarget().GetProcess()
1753
1754 def thread(self):
1755 if not self.dbg:
1756 raise Exception('Invalid debugger instance')
1757 return self.dbg.GetSelectedTarget().GetProcess().GetSelectedThread()
1758
1759 def frame(self):
1760 if not self.dbg:
1761 raise Exception('Invalid debugger instance')
1762 return self.dbg.GetSelectedTarget().GetProcess().GetSelectedThread().GetSelectedFrame()
1763
Greg Claytonc6947512013-12-13 19:18:59 +00001764 def get_process_working_directory(self):
1765 '''Get the working directory that should be used when launching processes for local or remote processes.'''
1766 if lldb.remote_platform:
1767 # Remote tests set the platform working directory up in TestBase.setUp()
1768 return lldb.remote_platform.GetWorkingDirectory()
1769 else:
1770 # local tests change directory into each test subdirectory
1771 return os.getcwd()
1772
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001773 def tearDown(self):
Johnny Chen7d1d7532010-09-02 21:23:12 +00001774 #import traceback
1775 #traceback.print_stack()
1776
Johnny Chenfb4264c2011-08-01 19:50:58 +00001777 Base.tearDown(self)
Johnny Chen707d8222010-10-19 23:40:13 +00001778
Johnny Chen3794ad92011-06-15 21:24:24 +00001779 # Delete the target(s) from the debugger as a general cleanup step.
1780 # This includes terminating the process for each target, if any.
1781 # We'd like to reuse the debugger for our next test without incurring
1782 # the initialization overhead.
1783 targets = []
1784 for target in self.dbg:
1785 if target:
1786 targets.append(target)
1787 process = target.GetProcess()
1788 if process:
1789 rc = self.invoke(process, "Kill")
1790 self.assertTrue(rc.Success(), PROCESS_KILLED)
1791 for target in targets:
1792 self.dbg.DeleteTarget(target)
Johnny Chen6ca006c2010-08-16 21:28:10 +00001793
Johnny Chen44d24972012-04-16 18:55:15 +00001794 # Run global post-flight code, if defined via the config file.
1795 if lldb.post_flight:
1796 lldb.post_flight(self)
1797
Johnny Chenbf6ffa32010-07-03 03:41:59 +00001798 del self.dbg
Johnny Chen150c3cc2010-10-15 01:18:29 +00001799
Johnny Chen86268e42011-09-30 21:48:35 +00001800 def switch_to_thread_with_stop_reason(self, stop_reason):
1801 """
1802 Run the 'thread list' command, and select the thread with stop reason as
1803 'stop_reason'. If no such thread exists, no select action is done.
1804 """
1805 from lldbutil import stop_reason_to_str
1806 self.runCmd('thread list')
1807 output = self.res.GetOutput()
1808 thread_line_pattern = re.compile("^[ *] thread #([0-9]+):.*stop reason = %s" %
1809 stop_reason_to_str(stop_reason))
1810 for line in output.splitlines():
1811 matched = thread_line_pattern.match(line)
1812 if matched:
1813 self.runCmd('thread select %s' % matched.group(1))
1814
Enrico Granata7594f142013-06-17 22:51:50 +00001815 def runCmd(self, cmd, msg=None, check=True, trace=False, inHistory=False):
Johnny Chen27f212d2010-08-19 23:26:59 +00001816 """
1817 Ask the command interpreter to handle the command and then check its
1818 return status.
1819 """
1820 # Fail fast if 'cmd' is not meaningful.
1821 if not cmd or len(cmd) == 0:
1822 raise Exception("Bad 'cmd' parameter encountered")
Johnny Chen5bbb88f2010-08-20 17:57:32 +00001823
Johnny Chen8d55a342010-08-31 17:42:54 +00001824 trace = (True if traceAlways else trace)
Johnny Chend0190a62010-08-23 17:10:44 +00001825
Daniel Maleae0f8f572013-08-26 23:57:52 +00001826 # This is an opportunity to insert the 'platform target-install' command if we are told so
1827 # via the settig of lldb.lldbtest_remote_sandbox.
1828 if cmd.startswith("target create "):
1829 cmd = cmd.replace("target create ", "file ")
1830 if cmd.startswith("file ") and lldb.lldbtest_remote_sandbox:
1831 with recording(self, trace) as sbuf:
1832 the_rest = cmd.split("file ")[1]
1833 # Split the rest of the command line.
1834 atoms = the_rest.split()
1835 #
1836 # NOTE: This assumes that the options, if any, follow the file command,
1837 # instead of follow the specified target.
1838 #
1839 target = atoms[-1]
1840 # Now let's get the absolute pathname of our target.
1841 abs_target = os.path.abspath(target)
1842 print >> sbuf, "Found a file command, target (with absolute pathname)=%s" % abs_target
1843 fpath, fname = os.path.split(abs_target)
1844 parent_dir = os.path.split(fpath)[0]
1845 platform_target_install_command = 'platform target-install %s %s' % (fpath, lldb.lldbtest_remote_sandbox)
1846 print >> sbuf, "Insert this command to be run first: %s" % platform_target_install_command
1847 self.ci.HandleCommand(platform_target_install_command, self.res)
1848 # And this is the file command we want to execute, instead.
1849 #
1850 # Warning: SIDE EFFECT AHEAD!!!
1851 # Populate the remote executable pathname into the lldb namespace,
1852 # so that test cases can grab this thing out of the namespace.
1853 #
1854 lldb.lldbtest_remote_sandboxed_executable = abs_target.replace(parent_dir, lldb.lldbtest_remote_sandbox)
1855 cmd = "file -P %s %s %s" % (lldb.lldbtest_remote_sandboxed_executable, the_rest.replace(target, ''), abs_target)
1856 print >> sbuf, "And this is the replaced file command: %s" % cmd
1857
Johnny Chen63dfb272010-09-01 00:15:19 +00001858 running = (cmd.startswith("run") or cmd.startswith("process launch"))
Johnny Chen5bbb88f2010-08-20 17:57:32 +00001859
Johnny Chen63dfb272010-09-01 00:15:19 +00001860 for i in range(self.maxLaunchCount if running else 1):
Enrico Granata7594f142013-06-17 22:51:50 +00001861 self.ci.HandleCommand(cmd, self.res, inHistory)
Johnny Chen5bbb88f2010-08-20 17:57:32 +00001862
Johnny Chen150c3cc2010-10-15 01:18:29 +00001863 with recording(self, trace) as sbuf:
1864 print >> sbuf, "runCmd:", cmd
Johnny Chenab254f52010-10-15 16:13:00 +00001865 if not check:
Johnny Chen27b107b2010-10-15 18:52:22 +00001866 print >> sbuf, "check of return status not required"
Johnny Chenf2b70232010-08-25 18:49:48 +00001867 if self.res.Succeeded():
Johnny Chen150c3cc2010-10-15 01:18:29 +00001868 print >> sbuf, "output:", self.res.GetOutput()
Johnny Chenf2b70232010-08-25 18:49:48 +00001869 else:
Johnny Chen150c3cc2010-10-15 01:18:29 +00001870 print >> sbuf, "runCmd failed!"
1871 print >> sbuf, self.res.GetError()
Johnny Chen5bbb88f2010-08-20 17:57:32 +00001872
Johnny Chenff3d01d2010-08-20 21:03:09 +00001873 if self.res.Succeeded():
Johnny Chenf2b70232010-08-25 18:49:48 +00001874 break
Johnny Chen150c3cc2010-10-15 01:18:29 +00001875 elif running:
Johnny Chencf7f74e2011-01-19 02:02:08 +00001876 # For process launch, wait some time before possible next try.
1877 time.sleep(self.timeWaitNextLaunch)
Johnny Chen552d6712012-08-01 19:56:04 +00001878 with recording(self, trace) as sbuf:
Johnny Chen150c3cc2010-10-15 01:18:29 +00001879 print >> sbuf, "Command '" + cmd + "' failed!"
Johnny Chen5bbb88f2010-08-20 17:57:32 +00001880
Johnny Chen27f212d2010-08-19 23:26:59 +00001881 if check:
1882 self.assertTrue(self.res.Succeeded(),
Johnny Chenc0c67f22010-11-09 18:42:22 +00001883 msg if msg else CMD_MSG(cmd))
Johnny Chen27f212d2010-08-19 23:26:59 +00001884
Jim Ingham63dfc722012-09-22 00:05:11 +00001885 def match (self, str, patterns, msg=None, trace=False, error=False, matching=True, exe=True):
1886 """run command in str, and match the result against regexp in patterns returning the match object for the first matching pattern
1887
1888 Otherwise, all the arguments have the same meanings as for the expect function"""
1889
1890 trace = (True if traceAlways else trace)
1891
1892 if exe:
1893 # First run the command. If we are expecting error, set check=False.
1894 # Pass the assert message along since it provides more semantic info.
1895 self.runCmd(str, msg=msg, trace = (True if trace else False), check = not error)
1896
1897 # Then compare the output against expected strings.
1898 output = self.res.GetError() if error else self.res.GetOutput()
1899
1900 # If error is True, the API client expects the command to fail!
1901 if error:
1902 self.assertFalse(self.res.Succeeded(),
1903 "Command '" + str + "' is expected to fail!")
1904 else:
1905 # No execution required, just compare str against the golden input.
1906 output = str
1907 with recording(self, trace) as sbuf:
1908 print >> sbuf, "looking at:", output
1909
1910 # The heading says either "Expecting" or "Not expecting".
1911 heading = "Expecting" if matching else "Not expecting"
1912
1913 for pattern in patterns:
1914 # Match Objects always have a boolean value of True.
1915 match_object = re.search(pattern, output)
1916 matched = bool(match_object)
1917 with recording(self, trace) as sbuf:
1918 print >> sbuf, "%s pattern: %s" % (heading, pattern)
1919 print >> sbuf, "Matched" if matched else "Not matched"
1920 if matched:
1921 break
1922
1923 self.assertTrue(matched if matching else not matched,
1924 msg if msg else EXP_MSG(str, exe))
1925
1926 return match_object
1927
Enrico Granata7594f142013-06-17 22:51:50 +00001928 def expect(self, str, msg=None, patterns=None, startstr=None, endstr=None, substrs=None, trace=False, error=False, matching=True, exe=True, inHistory=False):
Johnny Chen27f212d2010-08-19 23:26:59 +00001929 """
1930 Similar to runCmd; with additional expect style output matching ability.
1931
1932 Ask the command interpreter to handle the command and then check its
1933 return status. The 'msg' parameter specifies an informational assert
1934 message. We expect the output from running the command to start with
Johnny Chenea88e942010-09-21 21:08:53 +00001935 'startstr', matches the substrings contained in 'substrs', and regexp
1936 matches the patterns contained in 'patterns'.
Johnny Chenb3307862010-09-17 22:28:51 +00001937
1938 If the keyword argument error is set to True, it signifies that the API
1939 client is expecting the command to fail. In this case, the error stream
Johnny Chenaa902922010-09-17 22:45:27 +00001940 from running the command is retrieved and compared against the golden
Johnny Chenb3307862010-09-17 22:28:51 +00001941 input, instead.
Johnny Chenea88e942010-09-21 21:08:53 +00001942
1943 If the keyword argument matching is set to False, it signifies that the API
1944 client is expecting the output of the command not to match the golden
1945 input.
Johnny Chen9c48b8d2010-09-21 23:33:30 +00001946
1947 Finally, the required argument 'str' represents the lldb command to be
1948 sent to the command interpreter. In case the keyword argument 'exe' is
1949 set to False, the 'str' is treated as a string to be matched/not-matched
1950 against the golden input.
Johnny Chen27f212d2010-08-19 23:26:59 +00001951 """
Johnny Chen8d55a342010-08-31 17:42:54 +00001952 trace = (True if traceAlways else trace)
Johnny Chend0190a62010-08-23 17:10:44 +00001953
Johnny Chen9c48b8d2010-09-21 23:33:30 +00001954 if exe:
1955 # First run the command. If we are expecting error, set check=False.
Johnny Chen62d4f862010-10-28 21:10:32 +00001956 # Pass the assert message along since it provides more semantic info.
Enrico Granata7594f142013-06-17 22:51:50 +00001957 self.runCmd(str, msg=msg, trace = (True if trace else False), check = not error, inHistory=inHistory)
Johnny Chen27f212d2010-08-19 23:26:59 +00001958
Johnny Chen9c48b8d2010-09-21 23:33:30 +00001959 # Then compare the output against expected strings.
1960 output = self.res.GetError() if error else self.res.GetOutput()
Johnny Chenb3307862010-09-17 22:28:51 +00001961
Johnny Chen9c48b8d2010-09-21 23:33:30 +00001962 # If error is True, the API client expects the command to fail!
1963 if error:
1964 self.assertFalse(self.res.Succeeded(),
1965 "Command '" + str + "' is expected to fail!")
1966 else:
1967 # No execution required, just compare str against the golden input.
Enrico Granatabc08ab42012-10-23 00:09:02 +00001968 if isinstance(str,lldb.SBCommandReturnObject):
1969 output = str.GetOutput()
1970 else:
1971 output = str
Johnny Chen150c3cc2010-10-15 01:18:29 +00001972 with recording(self, trace) as sbuf:
1973 print >> sbuf, "looking at:", output
Johnny Chenb3307862010-09-17 22:28:51 +00001974
Johnny Chenea88e942010-09-21 21:08:53 +00001975 # The heading says either "Expecting" or "Not expecting".
Johnny Chen150c3cc2010-10-15 01:18:29 +00001976 heading = "Expecting" if matching else "Not expecting"
Johnny Chenea88e942010-09-21 21:08:53 +00001977
1978 # Start from the startstr, if specified.
1979 # If there's no startstr, set the initial state appropriately.
1980 matched = output.startswith(startstr) if startstr else (True if matching else False)
Johnny Chenb145bba2010-08-20 18:25:15 +00001981
Johnny Chen150c3cc2010-10-15 01:18:29 +00001982 if startstr:
1983 with recording(self, trace) as sbuf:
1984 print >> sbuf, "%s start string: %s" % (heading, startstr)
1985 print >> sbuf, "Matched" if matched else "Not matched"
Johnny Chenb145bba2010-08-20 18:25:15 +00001986
Johnny Chen86268e42011-09-30 21:48:35 +00001987 # Look for endstr, if specified.
1988 keepgoing = matched if matching else not matched
1989 if endstr:
1990 matched = output.endswith(endstr)
1991 with recording(self, trace) as sbuf:
1992 print >> sbuf, "%s end string: %s" % (heading, endstr)
1993 print >> sbuf, "Matched" if matched else "Not matched"
1994
Johnny Chenea88e942010-09-21 21:08:53 +00001995 # Look for sub strings, if specified.
1996 keepgoing = matched if matching else not matched
1997 if substrs and keepgoing:
Johnny Chen27f212d2010-08-19 23:26:59 +00001998 for str in substrs:
Johnny Chenb052f6c2010-09-23 23:35:28 +00001999 matched = output.find(str) != -1
Johnny Chen150c3cc2010-10-15 01:18:29 +00002000 with recording(self, trace) as sbuf:
2001 print >> sbuf, "%s sub string: %s" % (heading, str)
2002 print >> sbuf, "Matched" if matched else "Not matched"
Johnny Chenea88e942010-09-21 21:08:53 +00002003 keepgoing = matched if matching else not matched
2004 if not keepgoing:
Johnny Chen27f212d2010-08-19 23:26:59 +00002005 break
2006
Johnny Chenea88e942010-09-21 21:08:53 +00002007 # Search for regular expression patterns, if specified.
2008 keepgoing = matched if matching else not matched
2009 if patterns and keepgoing:
2010 for pattern in patterns:
2011 # Match Objects always have a boolean value of True.
2012 matched = bool(re.search(pattern, output))
Johnny Chen150c3cc2010-10-15 01:18:29 +00002013 with recording(self, trace) as sbuf:
2014 print >> sbuf, "%s pattern: %s" % (heading, pattern)
2015 print >> sbuf, "Matched" if matched else "Not matched"
Johnny Chenea88e942010-09-21 21:08:53 +00002016 keepgoing = matched if matching else not matched
2017 if not keepgoing:
2018 break
Johnny Chenea88e942010-09-21 21:08:53 +00002019
2020 self.assertTrue(matched if matching else not matched,
Johnny Chenc0c67f22010-11-09 18:42:22 +00002021 msg if msg else EXP_MSG(str, exe))
Johnny Chen27f212d2010-08-19 23:26:59 +00002022
Johnny Chenf3c59232010-08-25 22:52:45 +00002023 def invoke(self, obj, name, trace=False):
Johnny Chen61703c92010-08-25 22:56:10 +00002024 """Use reflection to call a method dynamically with no argument."""
Johnny Chen8d55a342010-08-31 17:42:54 +00002025 trace = (True if traceAlways else trace)
Johnny Chenf3c59232010-08-25 22:52:45 +00002026
2027 method = getattr(obj, name)
2028 import inspect
2029 self.assertTrue(inspect.ismethod(method),
2030 name + "is a method name of object: " + str(obj))
2031 result = method()
Johnny Chen150c3cc2010-10-15 01:18:29 +00002032 with recording(self, trace) as sbuf:
2033 print >> sbuf, str(method) + ":", result
Johnny Chenf3c59232010-08-25 22:52:45 +00002034 return result
Johnny Chen827edff2010-08-27 00:15:48 +00002035
Johnny Chenf359cf22011-05-27 23:36:52 +00002036 # =================================================
2037 # Misc. helper methods for debugging test execution
2038 # =================================================
2039
Johnny Chen56b92a72011-07-11 19:15:11 +00002040 def DebugSBValue(self, val):
Johnny Chen8d55a342010-08-31 17:42:54 +00002041 """Debug print a SBValue object, if traceAlways is True."""
Johnny Chende90f1d2011-04-27 17:43:07 +00002042 from lldbutil import value_type_to_str
Johnny Chen87bb5892010-11-03 21:37:58 +00002043
Johnny Chen8d55a342010-08-31 17:42:54 +00002044 if not traceAlways:
Johnny Chen827edff2010-08-27 00:15:48 +00002045 return
2046
2047 err = sys.stderr
2048 err.write(val.GetName() + ":\n")
Johnny Chen86268e42011-09-30 21:48:35 +00002049 err.write('\t' + "TypeName -> " + val.GetTypeName() + '\n')
2050 err.write('\t' + "ByteSize -> " + str(val.GetByteSize()) + '\n')
2051 err.write('\t' + "NumChildren -> " + str(val.GetNumChildren()) + '\n')
2052 err.write('\t' + "Value -> " + str(val.GetValue()) + '\n')
2053 err.write('\t' + "ValueAsUnsigned -> " + str(val.GetValueAsUnsigned())+ '\n')
2054 err.write('\t' + "ValueType -> " + value_type_to_str(val.GetValueType()) + '\n')
2055 err.write('\t' + "Summary -> " + str(val.GetSummary()) + '\n')
2056 err.write('\t' + "IsPointerType -> " + str(val.TypeIsPointerType()) + '\n')
2057 err.write('\t' + "Location -> " + val.GetLocation() + '\n')
Johnny Chen827edff2010-08-27 00:15:48 +00002058
Johnny Chen36c5eb12011-08-05 20:17:27 +00002059 def DebugSBType(self, type):
2060 """Debug print a SBType object, if traceAlways is True."""
2061 if not traceAlways:
2062 return
2063
2064 err = sys.stderr
2065 err.write(type.GetName() + ":\n")
2066 err.write('\t' + "ByteSize -> " + str(type.GetByteSize()) + '\n')
2067 err.write('\t' + "IsPointerType -> " + str(type.IsPointerType()) + '\n')
2068 err.write('\t' + "IsReferenceType -> " + str(type.IsReferenceType()) + '\n')
2069
Johnny Chenb877f1e2011-03-12 01:18:19 +00002070 def DebugPExpect(self, child):
2071 """Debug the spwaned pexpect object."""
2072 if not traceAlways:
2073 return
2074
2075 print child
Filipe Cabecinhas0eec15a2012-06-20 10:13:40 +00002076
2077 @classmethod
2078 def RemoveTempFile(cls, file):
2079 if os.path.exists(file):
2080 os.remove(file)