memory/replace/dmd/check_test_output.py

Tue, 06 Jan 2015 21:39:09 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Tue, 06 Jan 2015 21:39:09 +0100
branch
TOR_BUG_9701
changeset 8
97036ab72558
permissions
-rwxr-xr-x

Conditionally force memory storage according to privacy.thirdparty.isolate;
This solves Tor bug #9701, complying with disk avoidance documented in
https://www.torproject.org/projects/torbrowser/design/#disk-avoidance.

michael@0 1 #! /usr/bin/python
michael@0 2
michael@0 3 """This script takes the file produced by DMD's test mode and checks its
michael@0 4 correctness.
michael@0 5
michael@0 6 It produces the following output files: $TMP/test-{fixed,filtered,diff}.dmd.
michael@0 7
michael@0 8 It runs the appropriate fix* script to get nice stack traces. It also
michael@0 9 filters out platform-specific details from the test output file.
michael@0 10
michael@0 11 Note: you must run this from the same directory that you invoked DMD's test
michael@0 12 mode, otherwise the fix* script will not work properly, because some of the
michael@0 13 paths in the test output are relative.
michael@0 14
michael@0 15 """
michael@0 16
michael@0 17 from __future__ import print_function
michael@0 18
michael@0 19 import os
michael@0 20 import platform
michael@0 21 import re
michael@0 22 import subprocess
michael@0 23 import sys
michael@0 24 import tempfile
michael@0 25
michael@0 26
michael@0 27 def main():
michael@0 28
michael@0 29 # Arguments
michael@0 30
michael@0 31 if (len(sys.argv) != 3):
michael@0 32 print("usage:", sys.argv[0], "<topsrcdir> <test.dmd>")
michael@0 33 sys.exit(1)
michael@0 34
michael@0 35 srcdir = sys.argv[1]
michael@0 36
michael@0 37 # Filenames
michael@0 38
michael@0 39 tempdir = tempfile.gettempdir()
michael@0 40 in_name = sys.argv[2]
michael@0 41 fixed_name = tempdir + os.sep + "test-fixed.dmd"
michael@0 42 filtered_name = tempdir + os.sep + "test-filtered.dmd"
michael@0 43 diff_name = tempdir + os.sep + "test-diff.dmd"
michael@0 44 expected_name = srcdir + os.sep + \
michael@0 45 "memory/replace/dmd/test-expected.dmd"
michael@0 46
michael@0 47 # Fix stack traces
michael@0 48
michael@0 49 print("fixing output to", fixed_name)
michael@0 50
michael@0 51 sysname = platform.system()
michael@0 52 if sysname == "Linux":
michael@0 53 fix = srcdir + os.sep + "tools/rb/fix-linux-stack.pl"
michael@0 54 elif sysname == "Darwin":
michael@0 55 fix = srcdir + os.sep + "tools/rb/fix_macosx_stack.py"
michael@0 56 else:
michael@0 57 print("unhandled platform: " + sysname, file=sys.stderr)
michael@0 58 sys.exit(1)
michael@0 59
michael@0 60 subprocess.call(fix, stdin=open(in_name, "r"),
michael@0 61 stdout=open(fixed_name, "w"))
michael@0 62
michael@0 63 # Filter output
michael@0 64
michael@0 65 # In stack trace records we filter out most stack frames. The only thing
michael@0 66 # we leave behind is a "DMD.cpp" entry if we see one or more frames that
michael@0 67 # have DMD.cpp in them. There is simply too much variation to do anything
michael@0 68 # better than that.
michael@0 69 #
michael@0 70 # As for stack frame records, alas, we filter them out entirely because
michael@0 71 # they have even more variation.
michael@0 72
michael@0 73 print("filtering output to", filtered_name)
michael@0 74
michael@0 75 with open(fixed_name, "r") as fin, \
michael@0 76 open(filtered_name, "w") as fout:
michael@0 77
michael@0 78 test_frame_re = re.compile(r".*(DMD.cpp)")
michael@0 79
michael@0 80 for line in fin:
michael@0 81 if re.match(r" (Allocated at|Reported( again)? at)", line):
michael@0 82 # It's a stack trace record.
michael@0 83 print(line, end='', file=fout)
michael@0 84
michael@0 85 # Filter the stack trace -- print a single line if we see one
michael@0 86 # or more frames involving DMD.cpp.
michael@0 87 seen_DMD_frame = False
michael@0 88 for frame in fin:
michael@0 89 if re.match(r" ", frame):
michael@0 90 m = test_frame_re.match(frame)
michael@0 91 if m:
michael@0 92 seen_DMD_frame = True
michael@0 93 else:
michael@0 94 # We're past the stack trace.
michael@0 95 if seen_DMD_frame:
michael@0 96 print(" ... DMD.cpp", file=fout)
michael@0 97 print(frame, end='', file=fout)
michael@0 98 break
michael@0 99
michael@0 100 elif re.search("in stack frame record", line):
michael@0 101 # Stack frame record. Get the whole thing (we know how many
michael@0 102 # lines it has).
michael@0 103 line2 = fin.next()
michael@0 104 line3 = fin.next()
michael@0 105 line4 = fin.next()
michael@0 106 line5 = fin.next()
michael@0 107 line6 = fin.next()
michael@0 108
michael@0 109 else:
michael@0 110 # A line that needs no special handling. Copy it through.
michael@0 111 print(line, end='', file=fout)
michael@0 112
michael@0 113 # Compare with expected output
michael@0 114
michael@0 115 print("diffing output to", diff_name)
michael@0 116
michael@0 117 ret = subprocess.call(["diff", "-u", expected_name, filtered_name],
michael@0 118 stdout=open(diff_name, "w"))
michael@0 119
michael@0 120 if ret == 0:
michael@0 121 print("test PASSED")
michael@0 122 else:
michael@0 123 print("test FAILED (did you remember to run this script and Firefox "
michael@0 124 "in the same directory?)")
michael@0 125
michael@0 126
michael@0 127 if __name__ == "__main__":
michael@0 128 main()

mercurial