Thu, 22 Jan 2015 13:21:57 +0100
Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6
michael@0 | 1 | #!/usr/local/bin/perl -w |
michael@0 | 2 | # This Source Code Form is subject to the terms of the Mozilla Public |
michael@0 | 3 | # License, v. 2.0. If a copy of the MPL was not distributed with this |
michael@0 | 4 | # file, You can obtain one at http://mozilla.org/MPL/2.0/. |
michael@0 | 5 | |
michael@0 | 6 | |
michael@0 | 7 | # Perl script to analyze the xpcom output file |
michael@0 | 8 | # |
michael@0 | 9 | # To create xpcom output file : |
michael@0 | 10 | # |
michael@0 | 11 | # setenv NSPR_LOG_MODULES nsComponentManager:5 |
michael@0 | 12 | # setenv NSPR_LOG_FILE xpcom.out |
michael@0 | 13 | # ./mozilla |
michael@0 | 14 | # |
michael@0 | 15 | # Also to try to convert CID -> contractID this program looks for |
michael@0 | 16 | # a file reg.out in the current directory. To generate this file |
michael@0 | 17 | # |
michael@0 | 18 | # $ regExport > reg.out |
michael@0 | 19 | # |
michael@0 | 20 | # Usage: analyze-xpcom-log.pl < xpcom.out |
michael@0 | 21 | # [does better if ./reg.out is available] |
michael@0 | 22 | # |
michael@0 | 23 | # Suresh Duddi <dpsuresh@netscape.net> |
michael@0 | 24 | |
michael@0 | 25 | |
michael@0 | 26 | use strict; |
michael@0 | 27 | |
michael@0 | 28 | # forward declarations |
michael@0 | 29 | sub getContractID($); |
michael@0 | 30 | sub sum($); |
michael@0 | 31 | |
michael@0 | 32 | # Configuration parameters |
michael@0 | 33 | # Print all ? |
michael@0 | 34 | my $all = 0; |
michael@0 | 35 | |
michael@0 | 36 | # hash of cid -> contractid |
michael@0 | 37 | my %contractid; |
michael@0 | 38 | my %contractid_n; |
michael@0 | 39 | my %failedContractid_n; |
michael@0 | 40 | |
michael@0 | 41 | # count of instances of objects created |
michael@0 | 42 | my (%objs, %objs_contractid, %failedObjs) = (); |
michael@0 | 43 | |
michael@0 | 44 | # dlls loaded |
michael@0 | 45 | my @dlls; |
michael@0 | 46 | |
michael@0 | 47 | # temporaries |
michael@0 | 48 | my ($cid, $n, $str); |
michael@0 | 49 | |
michael@0 | 50 | while (<>) { |
michael@0 | 51 | chomp; |
michael@0 | 52 | |
michael@0 | 53 | # dlls loaded |
michael@0 | 54 | if (/loading \"(.*)\"/) { |
michael@0 | 55 | push @dlls, $1; |
michael@0 | 56 | next; |
michael@0 | 57 | } |
michael@0 | 58 | |
michael@0 | 59 | # FAILED ContractIDToClassID |
michael@0 | 60 | if (/ContractIDToClassID\((.*)\).*\[FAILED\]/) { |
michael@0 | 61 | $failedContractid_n{$1}++; |
michael@0 | 62 | next; |
michael@0 | 63 | } |
michael@0 | 64 | |
michael@0 | 65 | # ContractIDToClassID |
michael@0 | 66 | if (/ContractIDToClassID\((.*)\).*\{(.*)\}/) { |
michael@0 | 67 | $contractid{$2} = $1; |
michael@0 | 68 | $contractid_n{$2}++; |
michael@0 | 69 | next; |
michael@0 | 70 | } |
michael@0 | 71 | |
michael@0 | 72 | # CreateInstance() |
michael@0 | 73 | if (/CreateInstance\(\{(.*)\}\) succeeded/) { |
michael@0 | 74 | $objs{$1}++; |
michael@0 | 75 | next; |
michael@0 | 76 | } |
michael@0 | 77 | |
michael@0 | 78 | # CreateInstanceByContractID() |
michael@0 | 79 | if (/CreateInstanceByContractID\((.*)\) succeeded/) { |
michael@0 | 80 | $objs_contractid{$1}++; |
michael@0 | 81 | next; |
michael@0 | 82 | } |
michael@0 | 83 | |
michael@0 | 84 | # FAILED CreateInstance() |
michael@0 | 85 | if (/CreateInstance\(\{(.*)\}\) FAILED/) { |
michael@0 | 86 | $failedObjs{$1}++; |
michael@0 | 87 | next; |
michael@0 | 88 | } |
michael@0 | 89 | } |
michael@0 | 90 | |
michael@0 | 91 | # if there is a file named reg.out in the current dir |
michael@0 | 92 | # then use that to fill in the ContractIDToClassID mapping. |
michael@0 | 93 | my $REG; |
michael@0 | 94 | open REG, "<reg.out"; |
michael@0 | 95 | while (<REG>) { |
michael@0 | 96 | chomp; |
michael@0 | 97 | if (/contractID - (.*)$/) { |
michael@0 | 98 | my $id = $1; |
michael@0 | 99 | $cid = <REG>; |
michael@0 | 100 | chomp($cid); |
michael@0 | 101 | $cid =~ s/^.*\{(.*)\}.*$/$1/; |
michael@0 | 102 | $contractid{$cid} = $id; |
michael@0 | 103 | } |
michael@0 | 104 | } |
michael@0 | 105 | |
michael@0 | 106 | # print results |
michael@0 | 107 | # ---------------------------------------------------------------------- |
michael@0 | 108 | |
michael@0 | 109 | # dlls loaded |
michael@0 | 110 | print "dlls loaded [", scalar @dlls, "]\n"; |
michael@0 | 111 | print "----------------------------------------------------------------------\n"; |
michael@0 | 112 | for ($n = 0; $n < scalar @dlls; $n++) { |
michael@0 | 113 | printf "%2d. %s\n", $n+1, $dlls[$n]; |
michael@0 | 114 | } |
michael@0 | 115 | print "\n"; |
michael@0 | 116 | |
michael@0 | 117 | # Objects created |
michael@0 | 118 | print "Object creations from CID [", sum(\%objs), "]\n"; |
michael@0 | 119 | print "----------------------------------------------------------------------\n"; |
michael@0 | 120 | foreach $cid (sort {$objs{$b} <=> $objs{$a} } keys %objs) { |
michael@0 | 121 | last if (!$all && $objs{$cid} < 50); |
michael@0 | 122 | printf "%5d. %s - %s\n", $objs{$cid}, $cid, getContractID($cid); |
michael@0 | 123 | } |
michael@0 | 124 | print "\n"; |
michael@0 | 125 | |
michael@0 | 126 | print "Object creations from ContractID [", sum(\%objs_contractid), "]\n"; |
michael@0 | 127 | print "----------------------------------------------------------------------\n"; |
michael@0 | 128 | foreach $cid (sort {$objs_contractid{$b} <=> $objs_contractid{$a} } keys %objs_contractid) { |
michael@0 | 129 | last if (!$all && $objs_contractid{$cid} < 50); |
michael@0 | 130 | printf "%5d. %s - %s\n", $objs_contractid{$cid}, $cid, getContractID($cid); |
michael@0 | 131 | } |
michael@0 | 132 | print "\n"; |
michael@0 | 133 | |
michael@0 | 134 | # FAILED Objects created |
michael@0 | 135 | print "FAILED Objects creations [", sum(\%failedObjs), "]\n"; |
michael@0 | 136 | print "----------------------------------------------------------------------\n"; |
michael@0 | 137 | foreach $cid (sort {$failedObjs{$b} <=> $failedObjs{$a} } keys %failedObjs) { |
michael@0 | 138 | last if (!$all && $failedObjs{$cid} < 50); |
michael@0 | 139 | printf "%5d. %s - %s", $failedObjs{$cid}, $cid, getContractID($cid); |
michael@0 | 140 | } |
michael@0 | 141 | print "\n"; |
michael@0 | 142 | |
michael@0 | 143 | # ContractIDToClassID calls |
michael@0 | 144 | print "ContractIDToClassID() calls [", sum(\%contractid_n),"]\n"; |
michael@0 | 145 | print "----------------------------------------------------------------------\n"; |
michael@0 | 146 | foreach $cid (sort {$contractid_n{$b} <=> $contractid_n{$a} } keys %contractid_n) { |
michael@0 | 147 | last if (!$all && $contractid_n{$cid} < 50); |
michael@0 | 148 | printf "%5d. %s - %s\n", $contractid_n{$cid}, $cid, getContractID($cid); |
michael@0 | 149 | } |
michael@0 | 150 | print "\n"; |
michael@0 | 151 | |
michael@0 | 152 | |
michael@0 | 153 | # FAILED ContractIDToClassID calls |
michael@0 | 154 | print "FAILED ContractIDToClassID() calls [", sum(\%failedContractid_n), "]\n"; |
michael@0 | 155 | print "----------------------------------------------------------------------\n"; |
michael@0 | 156 | foreach $cid (sort {$failedContractid_n{$b} <=> $failedContractid_n{$a} } keys %failedContractid_n) { |
michael@0 | 157 | last if (!$all && $failedContractid_n{$cid} < 50); |
michael@0 | 158 | printf "%5d. %s\n", $failedContractid_n{$cid}, $cid; |
michael@0 | 159 | } |
michael@0 | 160 | print "\n"; |
michael@0 | 161 | |
michael@0 | 162 | |
michael@0 | 163 | # Subroutines |
michael@0 | 164 | |
michael@0 | 165 | sub getContractID($) { |
michael@0 | 166 | my $cid = shift; |
michael@0 | 167 | my $ret = ""; |
michael@0 | 168 | $ret = $contractid{$cid} if (exists $contractid{$cid}); |
michael@0 | 169 | return $ret; |
michael@0 | 170 | } |
michael@0 | 171 | |
michael@0 | 172 | sub sum($) { |
michael@0 | 173 | my $hash_ref = shift; |
michael@0 | 174 | my %hash = %$hash_ref; |
michael@0 | 175 | my $total = 0; |
michael@0 | 176 | my $key; |
michael@0 | 177 | foreach $key (keys %hash) { |
michael@0 | 178 | $total += $hash{$key}; |
michael@0 | 179 | } |
michael@0 | 180 | return $total; |
michael@0 | 181 | } |