Package FuzzManager :: Package FTB :: Package Signatures :: Module test_CrashSignature
[hide private]
[frames] | no frames]

Source Code for Module FuzzManager.FTB.Signatures.test_CrashSignature

  1  ''' 
  2  Created on Oct 9, 2014 
  3   
  4  @author: decoder 
  5  ''' 
  6  import json 
  7  import unittest 
  8   
  9  from FTB.ProgramConfiguration import ProgramConfiguration 
 10  from FTB.Signatures.CrashInfo import CrashInfo, NoCrashInfo 
 11  from FTB.Signatures.CrashSignature import CrashSignature 
 12  from FTB.Signatures.Matchers import StringMatch 
 13  from FTB.Signatures.Symptom import StackFramesSymptom 
 14   
 15   
 16  testTrace1 = """Program received signal SIGSEGV, Segmentation fault. 
 17  GetObjectAllocKindForCopy (obj=0x7ffff54001b0, nursery=...) at /srv/repos/mozilla-central/js/src/gc/Nursery.cpp:369 
 18  369         if (obj->is<ArrayObject>()) { 
 19  #0  GetObjectAllocKindForCopy (obj=0x7ffff54001b0, nursery=...) at /srv/repos/mozilla-central/js/src/gc/Nursery.cpp:369 
 20  #1  js::Nursery::moveToTenured (this=0x1673be0, trc=0x7fffffffa2d0, src=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Nursery.cpp:570 
 21  #2  0x00000000004d167a in MinorGCCallback (thingp=0x7fffffff9fd0, jstrc=<optimized out>, kind=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Nursery.cpp:721 
 22  #3  js::Nursery::MinorGCCallback (jstrc=<optimized out>, thingp=0x7fffffff9fd0, kind=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Nursery.cpp:717 
 23  #4  0x00000000004b8690 in MarkInternal<JSObject> (trc=0x7fffffffa2d0, thingp=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:317 
 24  #5  0x00000000004cc55e in MarkValueInternal (v=0x7fffffffa5d8, trc=0x7fffffffa2d0) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:804 
 25  #6  MarkValueInternal (v=0x7fffffffa5d8, trc=0x7fffffffa2d0) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:827 
 26  #7  js::gc::MarkValueRoot (trc=<optimized out>, v=0x7fffffffa5d8, name=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:831 
 27  rax     0x2b2b2b2b      3110627432037296939 
 28  rbx     0xf54001b0      140737308000688 
 29  rcx     0xbad0bad1      3134241489 
 30  rdx     0x1656120       23421216 
 31  rsi     0xffffa2d0      140737488331472 
 32  rdi     0x1673be0       23542752 
 33  rbp     0xf54001b0      140737308000688 
 34  rsp     0xffff9f10      140737488330512 
 35  r8      0x0     0 
 36  r9      0x0     0 
 37  r10     0x1     1 
 38  r11     0x1     1 
 39  r12     0x0     -1266637395197952 
 40  r13     0xffffa2d0      140737488331472 
 41  r14     0x1673be0       23542752 
 42  r15     0x201   513 
 43  rip     0x4d0b32 <js::Nursery::moveToTenured(js::gc::MinorCollectionTracer*, JSObject*)+34> 
 44  => 0x4d0b32 <js::Nursery::moveToTenured(js::gc::MinorCollectionTracer*, JSObject*)+34>: mov    (%rax),%r8 
 45  """ 
 46   
 47  testTrace2 = """Program terminated with signal 11, Segmentation fault. 
 48  #0  JSObject::markChildren (this=0x7fc33ef5a060, trc=0x3538be0) 
 49      at /srv/repos/mozilla-central/js/src/jsobj.cpp:4081 
 50  4081        if (clasp->trace) 
 51  Loading JavaScript value pretty-printers; see js/src/gdb/README. 
 52  If they cause trouble, type: disable pretty-printer .* SpiderMonkey 
 53  #0  JSObject::markChildren (this=(JSObject * const) 0x7fc33ef5a060 Cannot access memory at address 0x4949494949494949, trc=0x3538be0) at /srv/repos/mozilla-central/js/src/jsobj.cpp:4081 
 54  #1  0x00000000004e11e3 in MarkChildren (obj=(JSObject *) 0x7fc33ef5a060 Cannot access memory at address 0x4949494949494949, trc=0x3538be0) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:1323 
 55  #2  js::TraceChildren (trc=0x3538be0, thing=0x7fc33ef5a060, kind=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Marking.cpp:1934 
 56  #3  0x0000000000625d87 in js::gc::GCRuntime::startVerifyPreBarriers (this=this@entry=0x33ac568) at /srv/repos/mozilla-central/js/src/gc/Verifier.cpp:239 
 57  #4  0x0000000000633a5e in maybeVerifyPreBarriers (always=<optimized out>, this=0x33ac568) at /srv/repos/mozilla-central/js/src/gc/Verifier.cpp:563 
 58  #5  js::gc::MaybeVerifyBarriers (cx=<optimized out>, always=<optimized out>) at /srv/repos/mozilla-central/js/src/gc/Verifier.cpp:588 
 59  #6  0x00000000007c8660 in js::jit::CheckOverRecursedWithExtra (cx=0x33ce390, frame=<optimized out>, extra=<optimized out>, earlyCheck=<optimized out>) at /srv/repos/mozilla-central/js/src/jit/VMFunctions.cpp:153 
 60  #7  0x00007fc33ee95394 in ?? () 
 61  #8  0x0000000000000000 in ?? () 
 62  rax    0x4949494949494949    5280832617179597129 
 63  rbx    0x7fc33ef5a060    140476551635040 
 64  rcx    0x4949494949494949    5280832617179597129 
 65  rdx    0x4    4 
 66  rsi    0xa8ae16    11054614 
 67  rdi    0x3538be0    55806944 
 68  rbp    0x3538be0    55806944 
 69  rsp    0x7fff9aec80c0    140735792578752 
 70  r8    0x0    0 
 71  r9    0x2cd1    11473 
 72  r10    0x37d2580    58533248 
 73  r11    0x4000    16384 
 74  r12    0x7fc3240c5030    140476100137008 
 75  r13    0x2    2 
 76  r14    0x7fc3240c4ff0    140476100136944 
 77  r15    0x0    0 
 78  rip    0x84de35 <JSObject::markChildren(JSTracer*)+53> 
 79  => 0x84de35 <JSObject::markChildren(JSTracer*)+53>:    mov    (%rax),%rax 
 80     0x84de38 <JSObject::markChildren(JSTracer*)+56>:    mov    0x68(%rax),%rax 
 81  """ 
 82   
 83  testTrace3 = """ASAN:SIGSEGV 
 84  ================================================================= 
 85  ==7116==ERROR: AddressSanitizer: SEGV on unknown address 0x000000000010 (pc 0x0000014662ba sp 0x7fffe804f180 bp 0x7fffe804f250 T0) 
 86      #0 0x14662b9 in JSObject::getClass() const /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jsobj.h:128 
 87      #1 0x14662b9 in bool JSObject::is<js::PropertyIteratorObject>() const /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jsobj.h:520 
 88      #2 0x14662b9 in js::CloseIterator(JSContext*, JS::Handle<JSObject*>) /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jsiter.cpp:1065 
 89      #3 0x14668e2 in js::UnwindIteratorForException(JSContext*, JS::Handle<JSObject*>) /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jsiter.cpp:1100 
 90      #4 0xe989c0 in js::jit::CloseLiveIterator(JSContext*, js::jit::InlineFrameIterator const&, unsigned int) /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jit/JitFrames.cpp:388 
 91      #5 0xe989c0 in js::jit::HandleExceptionIon(JSContext*, js::jit::InlineFrameIterator const&, js::jit::ResumeFromException*, bool*) /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jit/JitFrames.cpp:464 
 92      #6 0xe989c0 in js::jit::HandleException(js::jit::ResumeFromException*) /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jit/JitFrames.cpp:782 
 93   
 94  AddressSanitizer can not provide additional info. 
 95  SUMMARY: AddressSanitizer: SEGV /home/ownhero/homes/mozilla/repos/mozilla-central/js/src/jsobj.h:128 JSObject::getClass() const 
 96  ==7116==ABORTING 
 97  """ 
 98   
 99  testTraceHeapWithCrashAddress = """ 
100  Program terminated with signal 11, Segmentation fault. 
101  #0  0xe1afa070 in ?? () 
102  #0  0xe1afa070 in ?? () 
103  #1  0x00000000 in ?? () 
104  eax    0xfff869cc    -497204 
105  ebx    0x9469ff4    155623412 
106  ecx    0xe20f6cc0    -502305600 
107  edx    0xe1afa070    -508583824 
108  esi    0xfff86934    -497356 
109  edi    0xfff868cc    -497460 
110  ebp    0xe20f8790    3792668560 
111  esp    0xfff8682c    4294469676 
112  eip    0xe1afa070    3786383472 
113  => 0xe1afa070:    push   %edi 
114     0xe1afa071:    push   %esi 
115  """ 
116   
117  testTraceHeapWithoutCrashAddress = """ 
118  Program terminated with signal SIGSEGV, Segmentation fault. 
119  #0  0x00007f2b41e78087 in ?? () 
120  #1  0xfff9000000000000 in ?? () 
121  #2  0x4275203ba1949000 in ?? () 
122  #3  0x00007fff5330bb01 in ?? () 
123  #4  0x00007f2b44d83e40 in ?? () 
124  rax    0x7f2b42c45bc0    139823780486080 
125  rbx    0x0    0 
126  rcx    0x4275203ba1949000    4788769219264417792 
127  rdx    0x1    1 
128  rsi    0x7f2b42c4a310    139823780504336 
129  rdi    0x7f2b4aa19000    139823912423424 
130  rbp    0x7f2b42c4a310    139823780504336 
131  rsp    0x7fff5330bae0    140734589090528 
132  r8    0x7f2b46261678    139823837222520 
133  r9    0x0    0 
134  r10    0x7f2b46261688    139823837222536 
135  r11    0x7f2b4aa6a1e8    139823912755688 
136  r12    0x0    0 
137  r13    0x7b2    1970 
138  r14    0x404    1028 
139  r15    0x7f2b4aa19000    139823912423424 
140  rip    0x7f2b41e78087    139823766012039 
141  => 0x7f2b41e78087:    xorpd  %xmm5,%xmm5 
142     0x7f2b41e7808b:    ucomisd %xmm5,%xmm4 
143  """ 
144   
145  testSignature1 = '''{"symptoms": [ 
146      { 
147      "functionName": "GetObjectAllocKindForCopy", 
148      "frameNumber": 0, 
149      "type": "stackFrame" 
150    }, 
151      { 
152      "functionName": "js::Nursery::moveToTenured", 
153      "frameNumber": 1, 
154      "type": "stackFrame" 
155    }, 
156      { 
157      "functionName": "MinorGCCallback", 
158      "frameNumber": 2, 
159      "type": "stackFrame" 
160    }, 
161      { 
162      "functionName": "js::Nursery::MinorGCCallback", 
163      "frameNumber": 3, 
164      "type": "stackFrame" 
165    }, 
166      { 
167      "address": "0x2b2b2b2b", 
168      "type": "crashAddress" 
169    } 
170  ]} 
171  ''' 
172   
173  testSignature2 = '''{"symptoms": [ 
174      { 
175      "functionName": "GetObjectAllocKindForCopy", 
176      "frameNumber": 0, 
177      "type": "stackFrame" 
178    }, 
179      { 
180      "functionName": "js::Nursery::moveToTenured", 
181      "frameNumber": 1, 
182      "type": "stackFrame" 
183    }, 
184      { 
185      "functionName": "MinorGCCallback", 
186      "frameNumber": 2, 
187      "type": "stackFrame" 
188    } 
189  ]} 
190  ''' 
191   
192  testSignature3 = '''{"symptoms": [ 
193      { 
194      "functionName": "GetObjectAllocKindForCopy", 
195      "frameNumber": 0, 
196      "type": "stackFrame" 
197    }, 
198      { 
199      "functionName": "js::Nursery::moveToTenured", 
200      "frameNumber": 1, 
201      "type": "stackFrame" 
202    }, 
203    { 
204      "address": "0x2b2b2b2b", 
205      "type": "crashAddress" 
206    }, 
207      { 
208      "type": "instruction", 
209      "instructionName": "mov    (%rax),%r8" 
210    } 
211  ]} 
212  ''' 
213   
214  testSignature4 = '''{"symptoms": [ 
215      { 
216      "functionName": "GetObjectAllocKindForCopy", 
217      "frameNumber": 0, 
218      "type": "stackFrame" 
219    }, 
220      { 
221      "functionName": "js::Nursery::moveToTenured", 
222      "frameNumber": 1, 
223      "type": "stackFrame" 
224    }, 
225      { 
226      "type": "testcase",  
227      "value": { 
228        "matchType": "pcre",  
229        "value": "SIMD\\\.float\\\d+x" 
230      } 
231    } 
232  ]} 
233  ''' 
234   
235  testSignature5 = '''{"symptoms": [ 
236      { 
237      "functionName": "GetObjectAllocKindForCopy", 
238      "frameNumber": 0, 
239      "type": "stackFrame" 
240    }, 
241      { 
242      "functionName": "js::Nursery::moveToTenured", 
243      "frameNumber": 1, 
244      "type": "stackFrame" 
245    }, 
246      { 
247      "type": "testcase",  
248      "value": "SIMD.float32x4" 
249    } 
250  ]} 
251  ''' 
252   
253  testSignature6 = '''{"symptoms": [ 
254      { 
255      "functionName": "GetObjectAllocKindForCopy", 
256      "frameNumber": 0, 
257      "type": "stackFrame" 
258    }, 
259      { 
260      "functionName": "js::Nursery::moveToTenured", 
261      "frameNumber": 1, 
262      "type": "stackFrame" 
263    }, 
264      { 
265      "type": "testcase",  
266      "value": "SIMD.float64x4" 
267    } 
268  ]} 
269  ''' 
270   
271  testSignature7 = '''{"symptoms": [ 
272      { 
273        "type": "stackFrames",  
274        "functionNames": [ 
275          "js::UnwindIteratorForException",  
276          "CloseLiveIterator",  
277          "HandleExceptionIon",  
278          "js::jit::HandleException" 
279        ] 
280      } 
281  ]} 
282  ''' 
283   
284  testCase1 = ''' 
285  function test() { 
286    var a = SIMD.float32x4(); 
287    if (typeof reportCompare === "function") 
288      reportCompare(true, true); 
289  } 
290  test(); 
291  ''' 
292   
293  testSignatureStackFrames1 = '''{"symptoms": [ 
294      { 
295      "type": "stackFrames",  
296      "functionNames": [ "GetObjectAllocKindForCopy", "moveToTenured", "?", "MinorGCCallback", "MarkInternal<JSObject>" ] 
297    } 
298  ]} 
299  ''' 
300   
301  testSignatureStackFrames2 = '''{"symptoms": [ 
302      { 
303      "type": "stackFrames",  
304      "functionNames": [ "GetObjectAllocKindForCopy", "moveToTenured", "?", "MinorGCCallback", "MinorGCCallback", "MarkInternal<JSObject>" ] 
305    } 
306  ]} 
307  ''' 
308   
309  testSignatureStackFrames3 = '''{"symptoms": [ 
310      { 
311      "type": "stackFrames",  
312      "functionNames": [ "GetObjectAllocKindForCopy", "moveToTenured", "?", "?", "MarkInternal<JSObject>" ] 
313    } 
314  ]} 
315  ''' 
316   
317  testSignatureStackFrames4 = '''{"symptoms": [ 
318      { 
319      "type": "stackFrames",  
320      "functionNames": [ "GetObjectAllocKindForCopy", "moveToTenured", "???", "MarkInternal<JSObject>" ] 
321    } 
322  ]} 
323  ''' 
324   
325  testSignatureStackFrames5 = '''{"symptoms": [ 
326      { 
327      "type": "stackFrames",  
328      "functionNames": [ "GetObjectAllocKindForCopy", "moveToTenured", "?", "MarkInternal<JSObject>" ] 
329    } 
330  ]} 
331  ''' 
332   
333   
334  testSignaturePCREShort1 = '''{"symptoms": [ 
335      { 
336      "functionName": "/.+KindForCopy/", 
337      "type": "stackFrame" 
338    } 
339  ]} 
340  ''' 
341   
342  testSignaturePCREShort2 = '''{"symptoms": [ 
343      { 
344      "functionName": "/^.KindForCopy/", 
345      "type": "stackFrame" 
346    } 
347  ]} 
348  ''' 
349   
350  testSignatureEmptyCrashAddress = '''{"symptoms": [ 
351    { 
352      "address": "", 
353      "type": "crashAddress" 
354    } 
355  ]} 
356  ''' 
357   
358 -class SignatureCreateTest(unittest.TestCase):
359 - def runTest(self):
360 config = ProgramConfiguration("test", "x86", "linux") 361 362 crashInfo = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTrace1.splitlines()) 363 crashSig1 = crashInfo.createCrashSignature(forceCrashAddress=True, maxFrames=4, minimumSupportedVersion=10) 364 crashSig2 = crashInfo.createCrashSignature(forceCrashAddress=False, maxFrames=3, minimumSupportedVersion=10) 365 crashSig3 = crashInfo.createCrashSignature(forceCrashInstruction=True, maxFrames=2, minimumSupportedVersion=10) 366 367 # Check that all generated signatures match their originating crashInfo 368 self.assert_(crashSig1.matches(crashInfo)) 369 self.assert_(crashSig2.matches(crashInfo)) 370 self.assert_(crashSig3.matches(crashInfo)) 371 372 # Check that the generated signatures look as expected 373 self.assertEqual(json.loads(str(crashSig1)), json.loads(testSignature1)) 374 self.assertEqual(json.loads(str(crashSig2)), json.loads(testSignature2)) 375 376 # The third crashInfo misses 2 frames from the top 4 frames, so it will 377 # also include the crash address, even though we did not request it. 378 self.assertEqual(json.loads(str(crashSig3)), json.loads(testSignature3))
379
380 -class SignatureTestCaseMatchTest(unittest.TestCase):
381 - def runTest(self):
382 config = ProgramConfiguration("test", "x86", "linux") 383 384 crashInfo = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTrace1.splitlines()) 385 386 testSig3 = CrashSignature(testSignature3) 387 testSig4 = CrashSignature(testSignature4) 388 testSig5 = CrashSignature(testSignature5) 389 testSig6 = CrashSignature(testSignature6) 390 391 self.assertFalse(testSig3.matchRequiresTest()) 392 self.assertTrue(testSig4.matchRequiresTest()) 393 self.assertTrue(testSig5.matchRequiresTest()) 394 395 # Must not match without testcase provided 396 self.assertFalse(testSig4.matches(crashInfo)) 397 self.assertFalse(testSig5.matches(crashInfo)) 398 self.assertFalse(testSig6.matches(crashInfo)) 399 400 # Attach testcase 401 crashInfo.testcase = testCase1 402 403 # Must match with testcase provided 404 self.assertTrue(testSig4.matches(crashInfo)) 405 self.assertTrue(testSig5.matches(crashInfo)) 406 407 # This one does not match at all 408 self.assertFalse(testSig6.matches(crashInfo))
409
410 -class SignatureStackFramesTest(unittest.TestCase):
411 - def runTest(self):
412 config = ProgramConfiguration("test", "x86", "linux") 413 414 crashInfo = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTrace1.splitlines()) 415 416 testSig1 = CrashSignature(testSignatureStackFrames1) 417 testSig2 = CrashSignature(testSignatureStackFrames2) 418 testSig3 = CrashSignature(testSignatureStackFrames3) 419 testSig4 = CrashSignature(testSignatureStackFrames4) 420 testSig5 = CrashSignature(testSignatureStackFrames5) 421 422 self.assertTrue(testSig1.matches(crashInfo)) 423 self.assertTrue(testSig2.matches(crashInfo)) 424 self.assertTrue(testSig3.matches(crashInfo)) 425 self.assertTrue(testSig4.matches(crashInfo)) 426 self.assertFalse(testSig5.matches(crashInfo))
427
428 -class SignatureStackFramesAlgorithmsTest(unittest.TestCase):
429 - def runTest(self):
430 # Do some direct matcher tests on edge cases 431 self.assertTrue(StackFramesSymptom._match([], [StringMatch('???')])) 432 self.assertFalse(StackFramesSymptom._match([], [StringMatch('???'), StringMatch('a')])) 433 434 # Test the diff algorithm, test array contains: 435 # stack, signature, expected distance, proposed signature 436 testArray = [ 437 (['a', 'b', 'x', 'a', 'b', 'c'], ['a', 'b', '???', 'a', 'b', 'x', 'c'], 1, ['a', 'b', '???', 'a', 'b', '?', 'c']), 438 (['b', 'x', 'a', 'b', 'c'], ['a', 'b', '???', 'a', 'b', 'x', 'c'], 2, ['?', 'b', '???', 'a', 'b', '?', 'c']), 439 (['b', 'x', 'a', 'd', 'x'], ['a', 'b', '???', 'a', 'b', 'x', 'c'], 3, ['?', 'b', '???', 'a', '?', 'x', '?']), 440 ] 441 442 for (stack, rawSig, expectedDepth, expectedSig) in testArray: 443 for maxDepth in (expectedDepth, 3): 444 (actualDepth, actualSig) = StackFramesSymptom._diff(stack, [ StringMatch(x) for x in rawSig ], 0, 1, maxDepth) 445 self.assertEqual(expectedDepth, actualDepth) 446 self.assertEqual(expectedSig, [ str(x) for x in actualSig ])
447
448 -class SignaturePCREShortTest(unittest.TestCase):
449 - def runTest(self):
450 config = ProgramConfiguration("test", "x86", "linux") 451 452 crashInfo = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTrace1.splitlines()) 453 454 testSig1 = CrashSignature(testSignaturePCREShort1) 455 testSig2 = CrashSignature(testSignaturePCREShort2) 456 457 self.assertTrue(testSig1.matches(crashInfo)) 458 self.assertFalse(testSig2.matches(crashInfo))
459
460 -class SignatureStackFramesWildcardTailTest(unittest.TestCase):
461 - def runTest(self):
462 config = ProgramConfiguration("test", "x86", "linux") 463 464 crashInfo = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTrace2.splitlines()) 465 466 testSig = crashInfo.createCrashSignature() 467 468 # Ensure that the last frame with a symbol is at the right place and there is nothing else, 469 # espcially no wildcard, following afterwards. 470 self.assertTrue(isinstance(testSig.symptoms[0], StackFramesSymptom)) 471 self.assertEqual(str(testSig.symptoms[0].functionNames[6]), "js::jit::CheckOverRecursedWithExtra") 472 self.assertEqual(len(testSig.symptoms[0].functionNames), 7)
473
474 -class SignatureStackFramesRegressionTest(unittest.TestCase):
475 - def runTest(self):
476 config = ProgramConfiguration("test", "x86", "linux") 477 crashInfoNeg = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTraceHeapWithCrashAddress.splitlines()) 478 crashInfoPos = CrashInfo.fromRawCrashData([], [], config, auxCrashData=testTraceHeapWithoutCrashAddress.splitlines()) 479 480 testSigEmptyCrashAddress = CrashSignature(testSignatureEmptyCrashAddress) 481 482 self.assertTrue(testSigEmptyCrashAddress.matches(crashInfoPos)) 483 self.assertFalse(testSigEmptyCrashAddress.matches(crashInfoNeg))
484 485 if __name__ == "__main__": 486 # import sys;sys.argv = ['', 'Test.testName'] 487 unittest.main() 488