← Index
NYTProf Performance Profile   « block view • line view • sub view »
For 01.HTTP.t
  Run on Tue May 4 15:25:55 2010
Reported on Tue May 4 15:26:06 2010

File /usr/local/lib/perl5/5.10.1/Time/Local.pm
Statements Executed 50
Statement Execution Time 21.1ms
Subroutines — ordered by exclusive time
Calls P F Exclusive
Time
Inclusive
Time
Subroutine
11124µs29µsTime::Local::::_daygmTime::Local::_daygm
11120µs73µsTime::Local::::BEGIN@4Time::Local::BEGIN@4
11111µs27µsTime::Local::::BEGIN@5Time::Local::BEGIN@5
1119µs60µsTime::Local::::BEGIN@28Time::Local::BEGIN@28
1118µs10µsTime::Local::::BEGIN@7Time::Local::BEGIN@7
1116µs30µsTime::Local::::BEGIN@30Time::Local::BEGIN@30
1116µs62µsTime::Local::::BEGIN@9Time::Local::BEGIN@9
1116µs8µsTime::Local::::BEGIN@6Time::Local::BEGIN@6
1115µs30µsTime::Local::::BEGIN@29Time::Local::BEGIN@29
1125µs5µsTime::Local::::CORE:packTime::Local::CORE:pack (opcode)
0000s0sTime::Local::::_is_leap_yearTime::Local::_is_leap_year
0000s0sTime::Local::::_timegmTime::Local::_timegm
0000s0sTime::Local::::timegmTime::Local::timegm
0000s0sTime::Local::::timegm_nocheckTime::Local::timegm_nocheck
0000s0sTime::Local::::timelocalTime::Local::timelocal
0000s0sTime::Local::::timelocal_nocheckTime::Local::timelocal_nocheck
Call graph for these subroutines as a Graphviz dot language file.
Line State
ments
Time
on line
Calls Time
in subs
Code
1package Time::Local;
2
312µsrequire Exporter;
4326µs2127µs
# spent 73µs (20+54) within Time::Local::BEGIN@4 which was called # once (20µs+54µs) by LWP::UserAgent::BEGIN@12 at line 4
use Carp;
# spent 73µs making 1 call to Time::Local::BEGIN@4 # spent 54µs making 1 call to Exporter::import
5322µs242µs
# spent 27µs (11+16) within Time::Local::BEGIN@5 which was called # once (11µs+16µs) by LWP::UserAgent::BEGIN@12 at line 5
use Config;
# spent 27µs making 1 call to Time::Local::BEGIN@5 # spent 16µs making 1 call to Config::import
6317µs211µs
# spent 8µs (6+2) within Time::Local::BEGIN@6 which was called # once (6µs+2µs) by LWP::UserAgent::BEGIN@12 at line 6
use strict;
# spent 8µs making 1 call to Time::Local::BEGIN@6 # spent 2µs making 1 call to strict::import
7324µs213µs
# spent 10µs (8+3) within Time::Local::BEGIN@7 which was called # once (8µs+3µs) by LWP::UserAgent::BEGIN@12 at line 7
use integer;
# spent 10µs making 1 call to Time::Local::BEGIN@7 # spent 2µs making 1 call to integer::import
8
9382µs2119µs
# spent 62µs (6+56) within Time::Local::BEGIN@9 which was called # once (6µs+56µs) by LWP::UserAgent::BEGIN@12 at line 9
use vars qw( $VERSION @ISA @EXPORT @EXPORT_OK );
# spent 62µs making 1 call to Time::Local::BEGIN@9 # spent 56µs making 1 call to vars::import
1012µs$VERSION = '1.1901';
11
12121µs@ISA = qw( Exporter );
1312µs@EXPORT = qw( timegm timelocal );
1411µs@EXPORT_OK = qw( timegm_nocheck timelocal_nocheck );
15
1613µsmy @MonthDays = ( 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 );
17
18# Determine breakpoint for rolling century
19134µsmy $ThisYear = ( localtime() )[5];
2011µsmy $Breakpoint = ( $ThisYear + 50 ) % 100;
211600nsmy $NextCentury = $ThisYear - $ThisYear % 100;
221400ns$NextCentury += 100 if $Breakpoint < 50;
231100nsmy $Century = $NextCentury - 100;
241100nsmy $SecOff = 0;
25
261300nsmy ( %Options, %Cheat );
27
28326µs2111µs
# spent 60µs (9+51) within Time::Local::BEGIN@28 which was called # once (9µs+51µs) by LWP::UserAgent::BEGIN@12 at line 28
use constant SECS_PER_MINUTE => 60;
# spent 60µs making 1 call to Time::Local::BEGIN@28 # spent 51µs making 1 call to constant::import
29322µs254µs
# spent 30µs (5+24) within Time::Local::BEGIN@29 which was called # once (5µs+24µs) by LWP::UserAgent::BEGIN@12 at line 29
use constant SECS_PER_HOUR => 3600;
# spent 30µs making 1 call to Time::Local::BEGIN@29 # spent 24µs making 1 call to constant::import
3031.78ms253µs
# spent 30µs (6+23) within Time::Local::BEGIN@30 which was called # once (6µs+23µs) by LWP::UserAgent::BEGIN@12 at line 30
use constant SECS_PER_DAY => 86400;
# spent 30µs making 1 call to Time::Local::BEGIN@30 # spent 23µs making 1 call to constant::import
31
321100nsmy $MaxInt;
3313µsif ( $^O eq 'MacOS' ) {
34 # time_t is unsigned...
35 $MaxInt = ( 1 << ( 8 * $Config{ivsize} ) ) - 1;
36}
37else {
38112µs141µs $MaxInt = ( ( 1 << ( 8 * $Config{ivsize} - 2 ) ) - 1 ) * 2 + 1;
# spent 41µs making 1 call to Config::FETCH
39}
40
411600nsmy $MaxDay = int( ( $MaxInt - ( SECS_PER_DAY / 2 ) ) / SECS_PER_DAY ) - 1;
42
43# Determine the EPOC day for this machine
441100nsmy $Epoc = 0;
4512µsif ( $^O eq 'vos' ) {
46 # work around posix-977 -- VOS doesn't handle dates in the range
47 # 1970-1980.
48 $Epoc = _daygm( 0, 0, 0, 1, 0, 70, 4, 0 );
49}
50elsif ( $^O eq 'MacOS' ) {
51 $MaxDay *=2 if $^O eq 'MacOS'; # time_t unsigned ... quick hack?
52 # MacOS time() is seconds since 1 Jan 1904, localtime
53 # so we need to calculate an offset to apply later
54 $Epoc = 693901;
55 $SecOff = timelocal( localtime(0)) - timelocal( gmtime(0) ) ;
56 $Epoc += _daygm( gmtime(0) );
57}
58else {
59118.9ms129µs $Epoc = _daygm( gmtime(0) );
# spent 29µs making 1 call to Time::Local::_daygm
60}
61
6212µs%Cheat = (); # clear the cache as epoc has changed
63
64
# spent 29µs (24+5) within Time::Local::_daygm which was called # once (24µs+5µs) by LWP::UserAgent::BEGIN@12 at line 59
sub _daygm {
65
66 # This is written in such a byzantine way in order to avoid
67 # lexical variables and sub calls, for speed
68 return $_[3] + (
69428µs15µs $Cheat{ pack( 'ss', @_[ 4, 5 ] ) } ||= do {
# spent 5µs making 1 call to Time::Local::CORE:pack
70 my $month = ( $_[4] + 10 ) % 12;
71 my $year = ( $_[5] + 1900 ) - ( $month / 10 );
72
73 ( ( 365 * $year )
74 + ( $year / 4 )
75 - ( $year / 100 )
76 + ( $year / 400 )
77 + ( ( ( $month * 306 ) + 5 ) / 10 )
78 )
79 - $Epoc;
80 }
81 );
82}
83
84sub _timegm {
85 my $sec =
86 $SecOff + $_[0] + ( SECS_PER_MINUTE * $_[1] ) + ( SECS_PER_HOUR * $_[2] );
87
88 return $sec + ( SECS_PER_DAY * &_daygm );
89}
90
91sub timegm {
92 my ( $sec, $min, $hour, $mday, $month, $year ) = @_;
93
94 if ( $year >= 1000 ) {
95 $year -= 1900;
96 }
97 elsif ( $year < 100 and $year >= 0 ) {
98 $year += ( $year > $Breakpoint ) ? $Century : $NextCentury;
99 }
100
101 unless ( $Options{no_range_check} ) {
102 croak "Month '$month' out of range 0..11"
103 if $month > 11
104 or $month < 0;
105
106 my $md = $MonthDays[$month];
107 ++$md
108 if $month == 1 && _is_leap_year( $year + 1900 );
109
110 croak "Day '$mday' out of range 1..$md" if $mday > $md or $mday < 1;
111 croak "Hour '$hour' out of range 0..23" if $hour > 23 or $hour < 0;
112 croak "Minute '$min' out of range 0..59" if $min > 59 or $min < 0;
113 croak "Second '$sec' out of range 0..59" if $sec > 59 or $sec < 0;
114 }
115
116 my $days = _daygm( undef, undef, undef, $mday, $month, $year );
117
118 unless ($Options{no_range_check} or abs($days) < $MaxDay) {
119 my $msg = '';
120 $msg .= "Day too big - $days > $MaxDay\n" if $days > $MaxDay;
121
122 $year += 1900;
123 $msg .= "Cannot handle date ($sec, $min, $hour, $mday, $month, $year)";
124
125 croak $msg;
126 }
127
128 return $sec
129 + $SecOff
130 + ( SECS_PER_MINUTE * $min )
131 + ( SECS_PER_HOUR * $hour )
132 + ( SECS_PER_DAY * $days );
133}
134
135sub _is_leap_year {
136 return 0 if $_[0] % 4;
137 return 1 if $_[0] % 100;
138 return 0 if $_[0] % 400;
139
140 return 1;
141}
142
143sub timegm_nocheck {
144 local $Options{no_range_check} = 1;
145 return &timegm;
146}
147
148sub timelocal {
149 my $ref_t = &timegm;
150 my $loc_for_ref_t = _timegm( localtime($ref_t) );
151
152 my $zone_off = $loc_for_ref_t - $ref_t
153 or return $loc_for_ref_t;
154
155 # Adjust for timezone
156 my $loc_t = $ref_t - $zone_off;
157
158 # Are we close to a DST change or are we done
159 my $dst_off = $ref_t - _timegm( localtime($loc_t) );
160
161 # If this evaluates to true, it means that the value in $loc_t is
162 # the _second_ hour after a DST change where the local time moves
163 # backward.
164 if ( ! $dst_off &&
165 ( ( $ref_t - SECS_PER_HOUR ) - _timegm( localtime( $loc_t - SECS_PER_HOUR ) ) < 0 )
166 ) {
167 return $loc_t - SECS_PER_HOUR;
168 }
169
170 # Adjust for DST change
171 $loc_t += $dst_off;
172
173 return $loc_t if $dst_off > 0;
174
175 # If the original date was a non-extent gap in a forward DST jump,
176 # we should now have the wrong answer - undo the DST adjustment
177 my ( $s, $m, $h ) = localtime($loc_t);
178 $loc_t -= $dst_off if $s != $_[0] || $m != $_[1] || $h != $_[2];
179
180 return $loc_t;
181}
182
183sub timelocal_nocheck {
184 local $Options{no_range_check} = 1;
185 return &timelocal;
186}
187
188156µs1;
189
190__END__
191
192=head1 NAME
193
194Time::Local - efficiently compute time from local and GMT time
195
196=head1 SYNOPSIS
197
198 $time = timelocal($sec,$min,$hour,$mday,$mon,$year);
199 $time = timegm($sec,$min,$hour,$mday,$mon,$year);
200
201=head1 DESCRIPTION
202
203This module provides functions that are the inverse of built-in perl
204functions C<localtime()> and C<gmtime()>. They accept a date as a
205six-element array, and return the corresponding C<time(2)> value in
206seconds since the system epoch (Midnight, January 1, 1970 GMT on Unix,
207for example). This value can be positive or negative, though POSIX
208only requires support for positive values, so dates before the
209system's epoch may not work on all operating systems.
210
211It is worth drawing particular attention to the expected ranges for
212the values provided. The value for the day of the month is the actual
213day (ie 1..31), while the month is the number of months since January
214(0..11). This is consistent with the values returned from
215C<localtime()> and C<gmtime()>.
216
217=head1 FUNCTIONS
218
219=head2 C<timelocal()> and C<timegm()>
220
221This module exports two functions by default, C<timelocal()> and
222C<timegm()>.
223
224The C<timelocal()> and C<timegm()> functions perform range checking on
225the input $sec, $min, $hour, $mday, and $mon values by default.
226
227=head2 C<timelocal_nocheck()> and C<timegm_nocheck()>
228
229If you are working with data you know to be valid, you can speed your
230code up by using the "nocheck" variants, C<timelocal_nocheck()> and
231C<timegm_nocheck()>. These variants must be explicitly imported.
232
233 use Time::Local 'timelocal_nocheck';
234
235 # The 365th day of 1999
236 print scalar localtime timelocal_nocheck 0,0,0,365,0,99;
237
238If you supply data which is not valid (month 27, second 1,000) the
239results will be unpredictable (so don't do that).
240
241=head2 Year Value Interpretation
242
243Strictly speaking, the year should be specified in a form consistent
244with C<localtime()>, i.e. the offset from 1900. In order to make the
245interpretation of the year easier for humans, however, who are more
246accustomed to seeing years as two-digit or four-digit values, the
247following conventions are followed:
248
249=over 4
250
251=item *
252
253Years greater than 999 are interpreted as being the actual year,
254rather than the offset from 1900. Thus, 1964 would indicate the year
255Martin Luther King won the Nobel prize, not the year 3864.
256
257=item *
258
259Years in the range 100..999 are interpreted as offset from 1900, so
260that 112 indicates 2012. This rule also applies to years less than
261zero (but see note below regarding date range).
262
263=item *
264
265Years in the range 0..99 are interpreted as shorthand for years in the
266rolling "current century," defined as 50 years on either side of the
267current year. Thus, today, in 1999, 0 would refer to 2000, and 45 to
2682045, but 55 would refer to 1955. Twenty years from now, 55 would
269instead refer to 2055. This is messy, but matches the way people
270currently think about two digit dates. Whenever possible, use an
271absolute four digit year instead.
272
273=back
274
275The scheme above allows interpretation of a wide range of dates,
276particularly if 4-digit years are used.
277
278=head2 Limits of time_t
279
280The range of dates that can be actually be handled depends on the size
281of C<time_t> (usually a signed integer) on the given
282platform. Currently, this is 32 bits for most systems, yielding an
283approximate range from Dec 1901 to Jan 2038.
284
285Both C<timelocal()> and C<timegm()> croak if given dates outside the
286supported range.
287
288=head2 Ambiguous Local Times (DST)
289
290Because of DST changes, there are many time zones where the same local
291time occurs for two different GMT times on the same day. For example,
292in the "Europe/Paris" time zone, the local time of 2001-10-28 02:30:00
293can represent either 2001-10-28 00:30:00 GMT, B<or> 2001-10-28
29401:30:00 GMT.
295
296When given an ambiguous local time, the timelocal() function should
297always return the epoch for the I<earlier> of the two possible GMT
298times.
299
300=head2 Non-Existent Local Times (DST)
301
302When a DST change causes a locale clock to skip one hour forward,
303there will be an hour's worth of local times that don't exist. Again,
304for the "Europe/Paris" time zone, the local clock jumped from
3052001-03-25 01:59:59 to 2001-03-25 03:00:00.
306
307If the C<timelocal()> function is given a non-existent local time, it
308will simply return an epoch value for the time one hour later.
309
310=head2 Negative Epoch Values
311
312Negative epoch (C<time_t>) values are not officially supported by the
313POSIX standards, so this module's tests do not test them. On some
314systems, they are known not to work. These include MacOS (pre-OSX) and
315Win32.
316
317On systems which do support negative epoch values, this module should
318be able to cope with dates before the start of the epoch, down the
319minimum value of time_t for the system.
320
321=head1 IMPLEMENTATION
322
323These routines are quite efficient and yet are always guaranteed to
324agree with C<localtime()> and C<gmtime()>. We manage this by caching
325the start times of any months we've seen before. If we know the start
326time of the month, we can always calculate any time within the month.
327The start times are calculated using a mathematical formula. Unlike
328other algorithms that do multiple calls to C<gmtime()>.
329
330The C<timelocal()> function is implemented using the same cache. We
331just assume that we're translating a GMT time, and then fudge it when
332we're done for the timezone and daylight savings arguments. Note that
333the timezone is evaluated for each date because countries occasionally
334change their official timezones. Assuming that C<localtime()> corrects
335for these changes, this routine will also be correct.
336
337=head1 BUGS
338
339The whole scheme for interpreting two-digit years can be considered a
340bug.
341
342=head1 SUPPORT
343
344Support for this module is provided via the datetime@perl.org email
345list. See http://lists.perl.org/ for more details.
346
347Please submit bugs to the CPAN RT system at
348http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Time-Local or via email
349at bug-time-local@rt.cpan.org.
350
351=head1 COPYRIGHT
352
353Copyright (c) 1997-2003 Graham Barr, 2003-2007 David Rolsky. All
354rights reserved. This program is free software; you can redistribute
355it and/or modify it under the same terms as Perl itself.
356
357The full text of the license can be found in the LICENSE file included
358with this module.
359
360=head1 AUTHOR
361
362This module is based on a Perl 4 library, timelocal.pl, that was
363included with Perl 4.036, and was most likely written by Tom
364Christiansen.
365
366The current version was written by Graham Barr.
367
368It is now being maintained separately from the Perl core by Dave
369Rolsky, <autarch@urth.org>.
370
371=cut
# spent 5µs within Time::Local::CORE:pack which was called # once (5µs+0s) by Time::Local::_daygm at line 69 of Time/Local.pm
sub Time::Local::CORE:pack; # xsub