OLD | NEW |
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # | 2 # |
3 # Copyright 2008 the V8 project authors. All rights reserved. | 3 # Copyright 2008 the V8 project authors. All rights reserved. |
4 # Redistribution and use in source and binary forms, with or without | 4 # Redistribution and use in source and binary forms, with or without |
5 # modification, are permitted provided that the following conditions are | 5 # modification, are permitted provided that the following conditions are |
6 # met: | 6 # met: |
7 # | 7 # |
8 # * Redistributions of source code must retain the above copyright | 8 # * Redistributions of source code must retain the above copyright |
9 # notice, this list of conditions and the following disclaimer. | 9 # notice, this list of conditions and the following disclaimer. |
10 # * Redistributions in binary form must reproduce the above | 10 # * Redistributions in binary form must reproduce the above |
(...skipping 19 matching lines...) Expand all Loading... |
30 | 30 |
31 """A cross-platform execution counter viewer. | 31 """A cross-platform execution counter viewer. |
32 | 32 |
33 The stats viewer reads counters from a binary file and displays them | 33 The stats viewer reads counters from a binary file and displays them |
34 in a window, re-reading and re-displaying with regular intervals. | 34 in a window, re-reading and re-displaying with regular intervals. |
35 """ | 35 """ |
36 | 36 |
37 | 37 |
38 import mmap | 38 import mmap |
39 import os | 39 import os |
| 40 import re |
40 import struct | 41 import struct |
41 import sys | 42 import sys |
42 import time | 43 import time |
43 import Tkinter | 44 import Tkinter |
44 | 45 |
45 | 46 |
46 # The interval, in milliseconds, between ui updates | 47 # The interval, in milliseconds, between ui updates |
47 UPDATE_INTERVAL_MS = 100 | 48 UPDATE_INTERVAL_MS = 100 |
48 | 49 |
49 | 50 |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
88 # OpenWindow blocks until the main window is closed | 89 # OpenWindow blocks until the main window is closed |
89 self.OpenWindow() | 90 self.OpenWindow() |
90 finally: | 91 finally: |
91 self.CleanUp() | 92 self.CleanUp() |
92 | 93 |
93 def MountSharedData(self): | 94 def MountSharedData(self): |
94 """Mount the binary counters file as a memory-mapped file. If | 95 """Mount the binary counters file as a memory-mapped file. If |
95 something goes wrong print an informative message and exit the | 96 something goes wrong print an informative message and exit the |
96 program.""" | 97 program.""" |
97 if not os.path.exists(self.data_name): | 98 if not os.path.exists(self.data_name): |
98 print "File %s doesn't exist." % self.data_name | 99 maps_name = "/proc/%s/maps" % self.data_name |
99 sys.exit(1) | 100 if not os.path.exists(maps_name): |
| 101 print "\"%s\" is neither a counter file nor a PID." % self.data_name |
| 102 sys.exit(1) |
| 103 maps_file = open(maps_name, "r") |
| 104 try: |
| 105 m = re.search(r"/dev/shm/\S*", maps_file.read()) |
| 106 if m is not None and os.path.exists(m.group(0)): |
| 107 self.data_name = m.group(0) |
| 108 else: |
| 109 print "Can't find counter file in maps for PID %s." % self.data_name |
| 110 sys.exit(1) |
| 111 finally: |
| 112 maps_file.close() |
100 data_file = open(self.data_name, "r") | 113 data_file = open(self.data_name, "r") |
101 size = os.fstat(data_file.fileno()).st_size | 114 size = os.fstat(data_file.fileno()).st_size |
102 fileno = data_file.fileno() | 115 fileno = data_file.fileno() |
103 self.shared_mmap = mmap.mmap(fileno, size, access=mmap.ACCESS_READ) | 116 self.shared_mmap = mmap.mmap(fileno, size, access=mmap.ACCESS_READ) |
104 data_access = SharedDataAccess(self.shared_mmap) | 117 data_access = SharedDataAccess(self.shared_mmap) |
105 if data_access.IntAt(0) == COUNTERS_FILE_MAGIC_NUMBER: | 118 if data_access.IntAt(0) == COUNTERS_FILE_MAGIC_NUMBER: |
106 return CounterCollection(data_access) | 119 return CounterCollection(data_access) |
107 elif data_access.IntAt(0) == CHROME_COUNTERS_FILE_MAGIC_NUMBER: | 120 elif data_access.IntAt(0) == CHROME_COUNTERS_FILE_MAGIC_NUMBER: |
108 return ChromeCounterCollection(data_access) | 121 return ChromeCounterCollection(data_access) |
109 print "File %s is not stats data." % self.data_name | 122 print "File %s is not stats data." % self.data_name |
(...skipping 321 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
431 """Run the stats counter. | 444 """Run the stats counter. |
432 | 445 |
433 Args: | 446 Args: |
434 data_file: The counters file to monitor. | 447 data_file: The counters file to monitor. |
435 """ | 448 """ |
436 StatsViewer(data_file).Run() | 449 StatsViewer(data_file).Run() |
437 | 450 |
438 | 451 |
439 if __name__ == "__main__": | 452 if __name__ == "__main__": |
440 if len(sys.argv) != 2: | 453 if len(sys.argv) != 2: |
441 print "Usage: stats-viewer.py <stats data>" | 454 print "Usage: stats-viewer.py <stats data>|<test_shell pid>" |
442 sys.exit(1) | 455 sys.exit(1) |
443 Main(sys.argv[1]) | 456 Main(sys.argv[1]) |
OLD | NEW |