OLD | NEW |
1 #!/usr/bin/perl | 1 #!/usr/bin/perl |
2 | 2 |
3 # Copyright (C) 2007 Apple Inc. All rights reserved. | 3 # Copyright (C) 2007 Apple Inc. All rights reserved. |
4 # | 4 # |
5 # Redistribution and use in source and binary forms, with or without | 5 # Redistribution and use in source and binary forms, with or without |
6 # modification, are permitted provided that the following conditions | 6 # modification, are permitted provided that the following conditions |
7 # are met: | 7 # are met: |
8 # | 8 # |
9 # 1. Redistributions of source code must retain the above copyright | 9 # 1. Redistributions of source code must retain the above copyright |
10 # notice, this list of conditions and the following disclaimer. | 10 # notice, this list of conditions and the following disclaimer. |
11 # 2. Redistributions in binary form must reproduce the above copyright | 11 # 2. Redistributions in binary form must reproduce the above copyright |
12 # notice, this list of conditions and the following disclaimer in the | 12 # notice, this list of conditions and the following disclaimer in the |
13 # documentation and/or other materials provided with the distribution. | 13 # documentation and/or other materials provided with the distribution. |
14 # 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of | 14 # 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of |
15 # its contributors may be used to endorse or promote products derived | 15 # its contributors may be used to endorse or promote products derived |
16 # from this software without specific prior written permission. | 16 # from this software without specific prior written permission. |
17 # | 17 # |
18 # THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY | 18 # THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY |
19 # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | 19 # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
20 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | 20 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
21 # DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY | 21 # DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY |
22 # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | 22 # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
23 # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | 23 # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
24 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | 24 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
25 # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 25 # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
26 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF | 26 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
69 my %callstacks = (); | 69 my %callstacks = (); |
70 my $byteCountTotal = 0; | 70 my $byteCountTotal = 0; |
71 | 71 |
72 for (my $i = 0; $i < @lines; $i++) { | 72 for (my $i = 0; $i < @lines; $i++) { |
73 my $line = $lines[$i]; | 73 my $line = $lines[$i]; |
74 my ($callCount, $byteCount); | 74 my ($callCount, $byteCount); |
75 | 75 |
76 # First try malloc_history format | 76 # First try malloc_history format |
77 # 6 calls for 664 bytes thread_ffffffff |0x0 | start | 77 # 6 calls for 664 bytes thread_ffffffff |0x0 | start |
78 ($callCount, $byteCount) = ($line =~ /(\d+) calls for (\d+) bytes/); | 78 ($callCount, $byteCount) = ($line =~ /(\d+) calls for (\d+) bytes/); |
79 | 79 |
80 # Then try leaks format | 80 # Then try leaks format |
81 # Leak: 0x0ac3ca40 size=48 | 81 # Leak: 0x0ac3ca40 size=48 |
82 # 0x00020001 0x00000001 0x00000000 0x00000000 ................ | 82 # 0x00020001 0x00000001 0x00000000 0x00000000 ................ |
83 # Call stack: [thread ffffffff]: | 0x0 | start | 83 # Call stack: [thread ffffffff]: | 0x0 | start |
84 if (!$callCount || !$byteCount) { | 84 if (!$callCount || !$byteCount) { |
85 $callCount = 1; | 85 $callCount = 1; |
86 ($byteCount) = ($line =~ /Leak: [x[:xdigit:]]* size=(\d+)/); | 86 ($byteCount) = ($line =~ /Leak: [x[:xdigit:]]* size=(\d+)/); |
87 | 87 |
88 if ($byteCount) { | 88 if ($byteCount) { |
89 while (!($line =~ "Call stack: ")) { | 89 while (!($line =~ "Call stack: ")) { |
90 $i++; | 90 $i++; |
91 $line = $lines[$i]; | 91 $line = $lines[$i]; |
92 } | 92 } |
93 } | 93 } |
94 } | 94 } |
95 | 95 |
96 # Then try LeakFinder format | 96 # Then try LeakFinder format |
97 # --------------- Key: 213813, 84 bytes --------- | 97 # --------------- Key: 213813, 84 bytes --------- |
98 # c:\cygwin\home\buildbot\webkit\opensource\webcore\rendering\renderaren
a.cpp(78): WebCore::RenderArena::allocate | 98 # c:\cygwin\home\buildbot\webkit\opensource\webcore\rendering\renderaren
a.cpp(78): WebCore::RenderArena::allocate |
99 # c:\cygwin\home\buildbot\webkit\opensource\webcore\rendering\renderobje
ct.cpp(82): WebCore::RenderObject::operator new | 99 # c:\cygwin\home\buildbot\webkit\opensource\webcore\rendering\renderobje
ct.cpp(82): WebCore::RenderObject::operator new |
100 if (!$callCount || !$byteCount) { | 100 if (!$callCount || !$byteCount) { |
101 $callCount = 1; | 101 $callCount = 1; |
102 ($byteCount) = ($line =~ /Key: (?:\d+), (\d+) bytes/); | 102 ($byteCount) = ($line =~ /Key: (?:\d+), (\d+) bytes/); |
103 if ($byteCount) { | 103 if ($byteCount) { |
104 $line = $lines[++$i]; | 104 $line = $lines[++$i]; |
105 my @tempStack; | 105 my @tempStack; |
106 while ($lines[$i+1] !~ /^(?:-|\d)/) { | 106 while ($lines[$i+1] !~ /^(?:-|\d)/) { |
107 if ($line =~ /\): (.*)$/) { | 107 if ($line =~ /\): (.*)$/) { |
108 my $call = $1; | 108 my $call = $1; |
109 $call =~ s/\r$//; | 109 $call =~ s/\r$//; |
110 unshift(@tempStack, $call); | 110 unshift(@tempStack, $call); |
111 } | 111 } |
112 $line = $lines[++$i]; | 112 $line = $lines[++$i]; |
113 } | 113 } |
114 $line = join(" | ", @tempStack); | 114 $line = join(" | ", @tempStack); |
115 } | 115 } |
116 } | 116 } |
117 | 117 |
118 # Then give up | 118 # Then give up |
119 next if (!$callCount || !$byteCount); | 119 next if (!$callCount || !$byteCount); |
120 | 120 |
121 $byteCountTotal += $byteCount; | 121 $byteCountTotal += $byteCount; |
122 | 122 |
123 next if ($grepRegexp && !($line =~ $grepRegexp)); | 123 next if ($grepRegexp && !($line =~ $grepRegexp)); |
124 | 124 |
125 my $callstackBegin = 0; | 125 my $callstackBegin = 0; |
126 if ($mergeDepth) { | 126 if ($mergeDepth) { |
127 # count stack frames backwards from end of callstack | 127 # count stack frames backwards from end of callstack |
128 $callstackBegin = length($line); | 128 $callstackBegin = length($line); |
129 for (my $pipeCount = 0; $pipeCount < $mergeDepth; $pipeCount++) { | 129 for (my $pipeCount = 0; $pipeCount < $mergeDepth; $pipeCount++) { |
130 my $rindexResult = rindex($line, "|", $callstackBegin - 1); | 130 my $rindexResult = rindex($line, "|", $callstackBegin - 1); |
131 last if $rindexResult == -1; | 131 last if $rindexResult == -1; |
132 $callstackBegin = $rindexResult; | 132 $callstackBegin = $rindexResult; |
133 } | 133 } |
134 } else { | 134 } else { |
135 # start at beginning of callstack | 135 # start at beginning of callstack |
136 $callstackBegin = index($line, "|"); | 136 $callstackBegin = index($line, "|"); |
137 } | 137 } |
138 | 138 |
139 my $callstack = substr($line, $callstackBegin + 2); # + 2 skips "| " | 139 my $callstack = substr($line, $callstackBegin + 2); # + 2 skips "| " |
140 for my $regexp (@mergeRegexps) { | 140 for my $regexp (@mergeRegexps) { |
141 if ($callstack =~ $regexp) { | 141 if ($callstack =~ $regexp) { |
142 $callstack = $regexp . "\n"; | 142 $callstack = $regexp . "\n"; |
143 last; | 143 last; |
144 } | 144 } |
145 } | 145 } |
146 | 146 |
147 if (!$callstacks{$callstack}) { | 147 if (!$callstacks{$callstack}) { |
148 $callstacks{$callstack} = {"callCount" => 0, "byteCount" => 0}; | 148 $callstacks{$callstack} = {"callCount" => 0, "byteCount" => 0}; |
149 } | 149 } |
150 | 150 |
151 $callstacks{$callstack}{"callCount"} += $callCount; | 151 $callstacks{$callstack}{"callCount"} += $callCount; |
152 $callstacks{$callstack}{"byteCount"} += $byteCount; | 152 $callstacks{$callstack}{"byteCount"} += $byteCount; |
153 } | 153 } |
154 | 154 |
155 my $byteCountTotalReported = 0; | 155 my $byteCountTotalReported = 0; |
156 for my $callstack (sort { $callstacks{$b}{"byteCount"} <=> $callstacks{$a}{"
byteCount"} } keys %callstacks) { | 156 for my $callstack (sort { $callstacks{$b}{"byteCount"} <=> $callstacks{$a}{"
byteCount"} } keys %callstacks) { |
(...skipping 11 matching lines...) Expand all Loading... |
168 | 168 |
169 exit(main()); | 169 exit(main()); |
170 | 170 |
171 # Copied from perldoc -- please excuse the style | 171 # Copied from perldoc -- please excuse the style |
172 sub commify($) | 172 sub commify($) |
173 { | 173 { |
174 local $_ = shift; | 174 local $_ = shift; |
175 1 while s/^([-+]?\d+)(\d{3})/$1,$2/; | 175 1 while s/^([-+]?\d+)(\d{3})/$1,$2/; |
176 return $_; | 176 return $_; |
177 } | 177 } |
OLD | NEW |