Filename | /usr/local/lib/perl5/site_perl/Mail/SpamAssassin/Util/TieOneStringHash.pm |
Statements | Executed 11453 statements in 330ms |
Calls | P | F | Exclusive Time |
Inclusive Time |
Subroutine |
---|---|---|---|---|---|
1715 | 2 | 1 | 94.0ms | 94.0ms | CORE:match (opcode) | Mail::SpamAssassin::Util::TieOneStringHash::
2615 | 3 | 1 | 57.1ms | 57.1ms | CORE:regcomp (opcode) | Mail::SpamAssassin::Util::TieOneStringHash::
900 | 2 | 2 | 55.2ms | 128ms | STORE | Mail::SpamAssassin::Util::TieOneStringHash::
900 | 1 | 1 | 48.7ms | 48.7ms | CORE:subst (opcode) | Mail::SpamAssassin::Util::TieOneStringHash::
815 | 1 | 1 | 34.2ms | 90.0ms | EXISTS | Mail::SpamAssassin::Util::TieOneStringHash::
900 | 2 | 2 | 28.5ms | 100ms | FETCH | Mail::SpamAssassin::Util::TieOneStringHash::
12 | 1 | 1 | 196µs | 196µs | CORE:substcont (opcode) | Mail::SpamAssassin::Util::TieOneStringHash::
1 | 1 | 1 | 45µs | 55µs | BEGIN@22 | Mail::SpamAssassin::Util::TieOneStringHash::
1 | 1 | 1 | 22µs | 53µs | BEGIN@23 | Mail::SpamAssassin::Util::TieOneStringHash::
1 | 1 | 1 | 21µs | 119µs | BEGIN@25 | Mail::SpamAssassin::Util::TieOneStringHash::
1 | 1 | 1 | 21µs | 79µs | BEGIN@24 | Mail::SpamAssassin::Util::TieOneStringHash::
1 | 1 | 1 | 15µs | 15µs | TIEHASH | Mail::SpamAssassin::Util::TieOneStringHash::
0 | 0 | 0 | 0s | 0s | CLEAR | Mail::SpamAssassin::Util::TieOneStringHash::
0 | 0 | 0 | 0s | 0s | DELETE | Mail::SpamAssassin::Util::TieOneStringHash::
0 | 0 | 0 | 0s | 0s | FIRSTKEY | Mail::SpamAssassin::Util::TieOneStringHash::
0 | 0 | 0 | 0s | 0s | NEXTKEY | Mail::SpamAssassin::Util::TieOneStringHash::
0 | 0 | 0 | 0s | 0s | SCALAR | Mail::SpamAssassin::Util::TieOneStringHash::
Line | State ments |
Time on line |
Calls | Time in subs |
Code |
---|---|---|---|---|---|
1 | # A memory-efficient, but slow, single-string structure with a hash interface. | ||||
2 | |||||
3 | # <@LICENSE> | ||||
4 | # Licensed to the Apache Software Foundation (ASF) under one or more | ||||
5 | # contributor license agreements. See the NOTICE file distributed with | ||||
6 | # this work for additional information regarding copyright ownership. | ||||
7 | # The ASF licenses this file to you under the Apache License, Version 2.0 | ||||
8 | # (the "License"); you may not use this file except in compliance with | ||||
9 | # the License. You may obtain a copy of the License at: | ||||
10 | # | ||||
11 | # http://www.apache.org/licenses/LICENSE-2.0 | ||||
12 | # | ||||
13 | # Unless required by applicable law or agreed to in writing, software | ||||
14 | # distributed under the License is distributed on an "AS IS" BASIS, | ||||
15 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||||
16 | # See the License for the specific language governing permissions and | ||||
17 | # limitations under the License. | ||||
18 | # </@LICENSE> | ||||
19 | |||||
20 | package Mail::SpamAssassin::Util::TieOneStringHash; | ||||
21 | |||||
22 | 2 | 58µs | 2 | 65µs | # spent 55µs (45+10) within Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@22 which was called:
# once (45µs+10µs) by Mail::SpamAssassin::Conf::BEGIN@90 at line 22 # spent 55µs making 1 call to Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@22
# spent 10µs making 1 call to strict::import |
23 | 2 | 62µs | 2 | 85µs | # spent 53µs (22+32) within Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@23 which was called:
# once (22µs+32µs) by Mail::SpamAssassin::Conf::BEGIN@90 at line 23 # spent 53µs making 1 call to Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@23
# spent 32µs making 1 call to warnings::import |
24 | 2 | 63µs | 2 | 138µs | # spent 79µs (21+58) within Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@24 which was called:
# once (21µs+58µs) by Mail::SpamAssassin::Conf::BEGIN@90 at line 24 # spent 79µs making 1 call to Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@24
# spent 58µs making 1 call to re::import |
25 | 2 | 906µs | 2 | 216µs | # spent 119µs (21+97) within Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@25 which was called:
# once (21µs+97µs) by Mail::SpamAssassin::Conf::BEGIN@90 at line 25 # spent 119µs making 1 call to Mail::SpamAssassin::Util::TieOneStringHash::BEGIN@25
# spent 97µs making 1 call to Exporter::import |
26 | |||||
27 | 1 | 8µs | our @ISA = qw(); | ||
28 | |||||
29 | # the structure is pretty simple: it's a single string, containing | ||||
30 | # items like so: | ||||
31 | # | ||||
32 | # \n KEY 0x00 VALUE 0x00 \n | ||||
33 | # \n KEY2 0x00 VALUE2 0x00 \n | ||||
34 | # ... | ||||
35 | # | ||||
36 | # undef values are represented using $UNDEF_VALUE, a hacky magic string. | ||||
37 | # Only simple scalars can be stored; refs of any kind produce a croak(). | ||||
38 | # | ||||
39 | # writes are slowest, reads are slow, but memory usage is very low | ||||
40 | # compared to a "real" hash table -- in other words, this is perfect | ||||
41 | # for infrequently-read data that has to be kept around but should | ||||
42 | # affect memory usage as little as possible. | ||||
43 | |||||
44 | 1 | 6µs | my $UNDEF_VALUE = "_UNDEF_\001"; | ||
45 | |||||
46 | ########################################################################### | ||||
47 | |||||
48 | # spent 15µs within Mail::SpamAssassin::Util::TieOneStringHash::TIEHASH which was called:
# once (15µs+0s) by Mail::SpamAssassin::Conf::new at line 4531 of Mail/SpamAssassin/Conf.pm | ||||
49 | 1 | 4µs | my $class = shift; | ||
50 | 1 | 3µs | my $str = ''; | ||
51 | 1 | 12µs | return bless \$str, $class; | ||
52 | } | ||||
53 | |||||
54 | # spent 128ms (55.2+72.5) within Mail::SpamAssassin::Util::TieOneStringHash::STORE which was called 900 times, avg 142µs/call:
# 842 times (52.0ms+68.9ms) by Mail::SpamAssassin::Conf::Parser::set_hash_key_value at line 809 of Mail/SpamAssassin/Conf/Parser.pm, avg 144µs/call
# 58 times (3.16ms+3.57ms) by Mail::SpamAssassin::Conf::__ANON__[/usr/local/lib/perl5/site_perl/Mail/SpamAssassin/Conf.pm:2981] at line 2972 of Mail/SpamAssassin/Conf.pm, avg 116µs/call | ||||
55 | 900 | 4.17ms | my ($store, $k, $v) = @_; | ||
56 | 900 | 1.62ms | $v = $UNDEF_VALUE unless defined($v); | ||
57 | |||||
58 | 900 | 1.56ms | if (ref $v) { | ||
59 | croak "oops! only simple scalars can be stored in a TieOneStringHash"; | ||||
60 | } | ||||
61 | 900 | 1.57ms | if (!defined $k) { | ||
62 | croak "oops! TieOneStringHash requires defined keys"; | ||||
63 | } | ||||
64 | |||||
65 | 900 | 90.7ms | 1812 | 72.5ms | if ($$store !~ s{\n\Q$k\E\000.*?\000\n} # spent 48.7ms making 900 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:subst, avg 54µs/call
# spent 23.6ms making 900 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:regcomp, avg 26µs/call
# spent 196µs making 12 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:substcont, avg 16µs/call |
66 | {\n$k\000$v\000\n}xgs) | ||||
67 | { | ||||
68 | 894 | 21.1ms | $$store .= "\n$k\000$v\000\n"; | ||
69 | } | ||||
70 | 900 | 10.8ms | 1; | ||
71 | } | ||||
72 | |||||
73 | # spent 100ms (28.5+71.7) within Mail::SpamAssassin::Util::TieOneStringHash::FETCH which was called 900 times, avg 111µs/call:
# 842 times (26.7ms+68.0ms) by Mail::SpamAssassin::Conf::Parser::set_hash_key_value at line 809 of Mail/SpamAssassin/Conf/Parser.pm, avg 112µs/call
# 58 times (1.74ms+3.67ms) by Mail::SpamAssassin::Conf::__ANON__[/usr/local/lib/perl5/site_perl/Mail/SpamAssassin/Conf.pm:2981] at line 2972 of Mail/SpamAssassin/Conf.pm, avg 93µs/call | ||||
74 | 900 | 3.43ms | my ($store, $k) = @_; | ||
75 | 900 | 85.9ms | 1800 | 71.7ms | if ($$store =~ m{\n\Q$k\E\000(.*?)\000\n}xs) # spent 50.0ms making 900 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:match, avg 56µs/call
# spent 21.6ms making 900 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:regcomp, avg 24µs/call |
76 | { | ||||
77 | 900 | 13.4ms | return $1 eq $UNDEF_VALUE ? undef : $1; | ||
78 | } | ||||
79 | return; | ||||
80 | } | ||||
81 | |||||
82 | # spent 90.0ms (34.2+55.8) within Mail::SpamAssassin::Util::TieOneStringHash::EXISTS which was called 815 times, avg 110µs/call:
# 815 times (34.2ms+55.8ms) by Mail::SpamAssassin::Conf::Parser::check_for_missing_descriptions at line 658 of Mail/SpamAssassin/Conf/Parser.pm, avg 110µs/call | ||||
83 | 815 | 1.63ms | my ($store, $k) = @_; | ||
84 | 815 | 83.8ms | 1630 | 55.8ms | if ($$store =~ m{\n\Q$k\E\000}xs) # spent 44.0ms making 815 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:match, avg 54µs/call
# spent 11.8ms making 815 calls to Mail::SpamAssassin::Util::TieOneStringHash::CORE:regcomp, avg 15µs/call |
85 | { | ||||
86 | 746 | 8.95ms | return 1; | ||
87 | } | ||||
88 | 69 | 718µs | return; | ||
89 | } | ||||
90 | |||||
91 | sub DELETE { | ||||
92 | my ($store, $k) = @_; | ||||
93 | if ($$store =~ s{\n\Q$k\E\000(.*?)\000\n} | ||||
94 | {}xgs) | ||||
95 | { | ||||
96 | return $1 eq $UNDEF_VALUE ? undef : $1; | ||||
97 | } | ||||
98 | return; | ||||
99 | } | ||||
100 | |||||
101 | sub FIRSTKEY { | ||||
102 | my ($store) = @_; | ||||
103 | if ($$store =~ m{^\n(.*?)\000}s) | ||||
104 | { | ||||
105 | return $1; | ||||
106 | } | ||||
107 | return; | ||||
108 | } | ||||
109 | |||||
110 | sub NEXTKEY { | ||||
111 | my ($store, $lastk) = @_; | ||||
112 | if ($$store =~ m{\n\Q$lastk\E\000.*?\000\n | ||||
113 | \n(.*?)\000}xs) | ||||
114 | { | ||||
115 | return $1; | ||||
116 | } | ||||
117 | return; | ||||
118 | } | ||||
119 | |||||
120 | sub CLEAR { | ||||
121 | my ($store) = @_; | ||||
122 | $$store = ''; | ||||
123 | } | ||||
124 | |||||
125 | sub SCALAR { | ||||
126 | my ($store) = @_; | ||||
127 | return $$store; # as a string! | ||||
128 | } | ||||
129 | |||||
130 | 1 | 8µs | 1; | ||
# spent 94.0ms within Mail::SpamAssassin::Util::TieOneStringHash::CORE:match which was called 1715 times, avg 55µs/call:
# 900 times (50.0ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::FETCH at line 75, avg 56µs/call
# 815 times (44.0ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::EXISTS at line 84, avg 54µs/call | |||||
# spent 57.1ms within Mail::SpamAssassin::Util::TieOneStringHash::CORE:regcomp which was called 2615 times, avg 22µs/call:
# 900 times (23.6ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::STORE at line 65, avg 26µs/call
# 900 times (21.6ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::FETCH at line 75, avg 24µs/call
# 815 times (11.8ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::EXISTS at line 84, avg 15µs/call | |||||
# spent 48.7ms within Mail::SpamAssassin::Util::TieOneStringHash::CORE:subst which was called 900 times, avg 54µs/call:
# 900 times (48.7ms+0s) by Mail::SpamAssassin::Util::TieOneStringHash::STORE at line 65, avg 54µs/call | |||||
# spent 196µs within Mail::SpamAssassin::Util::TieOneStringHash::CORE:substcont which was called 12 times, avg 16µs/call:
# 12 times (196µs+0s) by Mail::SpamAssassin::Util::TieOneStringHash::STORE at line 65, avg 16µs/call |