← Index
NYTProf Performance Profile   « block view • line view • sub view »
For script/nytprof.pl
  Run on Thu May 31 16:49:15 2012
Reported on Thu May 31 16:53:43 2012

Filename/Users/edenc/perl5/lib/perl5/KiokuDB/TypeMap/Entry/Closure.pm
StatementsExecuted 15 statements in 1.03ms
Subroutines
Calls P F Exclusive
Time
Inclusive
Time
Subroutine
11118µs4.31msKiokuDB::TypeMap::Entry::Closure::::BEGIN@2KiokuDB::TypeMap::Entry::Closure::BEGIN@2
11111µs46µsKiokuDB::TypeMap::Entry::Closure::::BEGIN@4KiokuDB::TypeMap::Entry::Closure::BEGIN@4
11110µs25µsKiokuDB::TypeMap::Entry::Closure::::BEGIN@122KiokuDB::TypeMap::Entry::Closure::BEGIN@122
11110µs305µsKiokuDB::TypeMap::Entry::Closure::::BEGIN@9KiokuDB::TypeMap::Entry::Closure::BEGIN@9
1118µs30µsKiokuDB::TypeMap::Entry::Closure::::BEGIN@5KiokuDB::TypeMap::Entry::Closure::BEGIN@5
1118µs23µsKiokuDB::TypeMap::Entry::Closure::::BEGIN@7KiokuDB::TypeMap::Entry::Closure::BEGIN@7
0000s0sKiokuDB::TypeMap::Entry::Closure::::__ANON__[:142]KiokuDB::TypeMap::Entry::Closure::__ANON__[:142]
0000s0sKiokuDB::TypeMap::Entry::Closure::::__ANON__[:150]KiokuDB::TypeMap::Entry::Closure::__ANON__[:150]
0000s0sKiokuDB::TypeMap::Entry::Closure::::__ANON__[:172]KiokuDB::TypeMap::Entry::Closure::__ANON__[:172]
0000s0sKiokuDB::TypeMap::Entry::Closure::::__ANON__[:90]KiokuDB::TypeMap::Entry::Closure::__ANON__[:90]
0000s0sKiokuDB::TypeMap::Entry::Closure::::_deparseKiokuDB::TypeMap::Entry::Closure::_deparse
0000s0sKiokuDB::TypeMap::Entry::Closure::::_eval_bodyKiokuDB::TypeMap::Entry::Closure::_eval_body
0000s0sKiokuDB::TypeMap::Entry::Closure::::compile_collapse_bodyKiokuDB::TypeMap::Entry::Closure::compile_collapse_body
0000s0sKiokuDB::TypeMap::Entry::Closure::::compile_expandKiokuDB::TypeMap::Entry::Closure::compile_expand
0000s0sKiokuDB::TypeMap::Entry::Closure::::compile_refreshKiokuDB::TypeMap::Entry::Closure::compile_refresh
Call graph for these subroutines as a Graphviz dot language file.
Line State
ments
Time
on line
Calls Time
in subs
Code
1package KiokuDB::TypeMap::Entry::Closure;
2249µs28.60ms
# spent 4.31ms (18µs+4.29) within KiokuDB::TypeMap::Entry::Closure::BEGIN@2 which was called: # once (18µs+4.29ms) by Module::Runtime::require_module at line 2
use Moose;
# spent 4.31ms making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@2 # spent 4.29ms making 1 call to Moose::Exporter::__ANON__[Moose/Exporter.pm:492]
3
4229µs280µs
# spent 46µs (11+34) within KiokuDB::TypeMap::Entry::Closure::BEGIN@4 which was called: # once (11µs+34µs) by Module::Runtime::require_module at line 4
use Carp qw(croak);
# spent 46µs making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@4 # spent 34µs making 1 call to Exporter::import
5227µs251µs
# spent 30µs (8+21) within KiokuDB::TypeMap::Entry::Closure::BEGIN@5 which was called: # once (8µs+21µs) by Module::Runtime::require_module at line 5
use Scalar::Util qw(refaddr);
# spent 30µs making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@5 # spent 21µs making 1 call to Exporter::import
6
7229µs238µs
# spent 23µs (8+15) within KiokuDB::TypeMap::Entry::Closure::BEGIN@7 which was called: # once (8µs+15µs) by Module::Runtime::require_module at line 7
no warnings 'recursion';
# spent 23µs making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@7 # spent 15µs making 1 call to warnings::unimport
8
92535µs2600µs
# spent 305µs (10+295) within KiokuDB::TypeMap::Entry::Closure::BEGIN@9 which was called: # once (10µs+295µs) by Module::Runtime::require_module at line 9
use namespace::clean -except => 'meta';
# spent 305µs making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@9 # spent 295µs making 1 call to namespace::clean::import
10
1113µs14.56mswith qw(KiokuDB::TypeMap::Entry::Std);
# spent 4.56ms making 1 call to Moose::with
12
13sub compile_collapse_body {
14 my $self = shift;
15
16 require B;
17 require B::Deparse;
18 require PadWalker;
19
20 return sub {
21 my ( $collapser, %args ) = @_;
22
23 my $sub = $args{object};
24
25 my ( $pkg, $name ) = Class::MOP::get_code_info($sub);
26
27 my %data;
28
29 # FIXME make this customizable on a per sub and per typemap level
30 if ( $name eq '__ANON__' ) {
31 my $pad = PadWalker::closed_over($sub);
32
33 if ( keys %$pad ) {
34 my $collapsed_pad = $collapser->visit($pad);
35
36 $data{pad} = $collapsed_pad;
37
38 my $buffer = $collapser->_buffer;
39 my $pad_entry_data = blessed $collapsed_pad ? $buffer->id_to_entry( $collapsed_pad->id )->data : $collapsed_pad;
40
41 $buffer->first_class->insert(map { $_->id } values %$pad_entry_data ); # maybe only if entry($_->id)->object's refcount is > 1 (only shared closure vars) ?
42 }
43
44 # FIXME find all GVs in the optree and insert refs to them?
45 # i suppose they should be handled like named...
46 $data{body} = $self->_deparse($sub);
47 } else {
48 ( my $pkg_file = "${pkg}.pm" ) =~ s{::}{/}g;
49
50 my $file;
51
52 if ( my $meta = Class::MOP::get_metaclass_by_name($pkg) ) {
53 if ( my $method = $meta->get_method($name) ) {
54 if ( refaddr($method->body) == refaddr($sub)
55 and
56 $method->isa("Class::MOP::Method::Generated")
57 and
58 $method->can("definition_context")
59 ) {
60 $file = $method->definition_context->{file};
61 }
62 }
63 }
64
65 unless ( defined $file ) {
66 my $cv = B::svref_2object($sub);
67 $file = $cv->FILE unless $cv->XSUB; # Can't really tell who called newXS or even bootstrap, so we assume the package .pm did
68 }
69
70 my $inc_key;
71
72 if ( defined $file ) {
73 my %rev_inc = reverse %INC;
74 $inc_key = $rev_inc{$file};
75 $inc_key = $file unless defined $inc_key;
76 }
77
78 if ( defined($inc_key) and $pkg_file ne $inc_key ) {
79 $data{file} = $inc_key;
80 }
81
82 @data{qw(package name)} = ( $pkg, $name );
83 }
84
85 return $collapser->make_entry(
86 %args,
87 object => $sub,
88 data => \%data,
89 );
90 };
91}
92
93sub _deparse {
94 my ( $self, $cv ) = @_;
95
96 B::Deparse->new->coderef2text($cv);
97}
98
99sub compile_expand {
100 my $self = shift;
101
102 require PadWalker;
103
104 return sub {
105 my ( $linker, $entry ) = @_;
106
107 my $data = $entry->data;
108
109 if ( exists $data->{body} ) {
110 my ( $body, $pad ) = @{ $data }{qw(body pad)};
111
112 my $inflated_pad;
113 $linker->inflate_data( $pad, \$inflated_pad );
114
115 my $sub = $self->_eval_body( $linker, $body, $inflated_pad );
116
117 $linker->register_object( $entry => $sub );
118
119 return $sub;
120 } else {
121 my $fq = join("::", @{ $data }{qw(package name)});
1222334µs240µs
# spent 25µs (10+15) within KiokuDB::TypeMap::Entry::Closure::BEGIN@122 which was called: # once (10µs+15µs) by Module::Runtime::require_module at line 122
my $glob = do { no strict 'refs'; *$fq };
# spent 25µs making 1 call to KiokuDB::TypeMap::Entry::Closure::BEGIN@122 # spent 15µs making 1 call to strict::unimport
123
124 unless ( defined(*{$glob}{CODE}) ) {
125 if ( defined(my $file = $data->{file}) ) {
126 require $file unless exists $INC{$file};
127 } else {
128 Class::MOP::load_class($data->{package});
129 }
130
131 unless ( defined(*{$glob}{CODE}) ) {
132 croak "The subroutine &$data->{name} is no longer defined, but is referred to in the database";
133 }
134 }
135
136 my $sub = *{$glob}{CODE};
137
138 $linker->register_object( $entry => $sub );
139
140 return $sub;
141 }
142 };
143}
144
145sub compile_refresh {
146 my $self = shift;
147
148 return sub {
149 croak "refreshing of closures is not yet supported";
150 };
151}
152
153sub _eval_body {
154 my ( $self, $linker, $body, $pad ) = @_;
155
156 my ( $sub, $e ) = do {
157 local $@;
158
159 if ( my @vars = keys %$pad ) {
160 my $vars = join ", ", @vars;
161
162 # FIXME Parse::Perl
163 my $sub = eval "
164 my ( $vars );
165 sub $body;
166 ";
167
168 my $e = $@;
169
170 $linker->queue_finalizer(sub {
171 PadWalker::set_closed_over($sub, $pad);
172 }) if $sub;
173
174 ( $sub, $e );
175 } else {
176 eval "sub $body", $@;
177 }
178 };
179
180 die $e unless $sub;
181
182 return $sub;
183}
184
185
18614µs22.87ms__PACKAGE__->meta->make_immutable;
# spent 2.85ms making 1 call to Class::MOP::Class::make_immutable # spent 15µs making 1 call to KiokuDB::TypeMap::Entry::Closure::meta
187
188110µs__PACKAGE__
189
190110µs1995µs__END__