"TYPO3 4.0.1: typo3_src-4.0.1/typo3/sysext/adodb/adodb/adodb-time.inc.php Source File", "datetime" => "Sat Dec 2 19:22:24 2006", "date" => "2 Dec 2006", "doxygenversion" => "1.4.6", "projectname" => "TYPO3 4.0.1", "projectnumber" => "4.0.1" ); get_header($doxygen_vars); ?>

adodb-time.inc.php

00001 <?php
00366 /* Initialization */
00367 
00368 /*
00369         Version Number
00370 */
00371 define('ADODB_DATE_VERSION',0.24);
00372 
00373 /*
00374         This code was originally for windows. But apparently this problem happens 
00375         also with Linux, RH 7.3 and later!
00376         
00377         glibc-2.2.5-34 and greater has been changed to return -1 for dates <
00378         1970.  This used to work.  The problem exists with RedHat 7.3 and 8.0
00379         echo (mktime(0, 0, 0, 1, 1, 1960));  // prints -1
00380         
00381         References:
00382          http://bugs.php.net/bug.php?id=20048&edit=2
00383          http://lists.debian.org/debian-glibc/2002/debian-glibc-200205/msg00010.html
00384 */
00385 
00386 if (!defined('ADODB_ALLOW_NEGATIVE_TS')) define('ADODB_NO_NEGATIVE_TS',1);
00387 
00388 function adodb_date_test_date($y1,$m,$d=13)
00389 {
00390         $t = adodb_mktime(0,0,0,$m,$d,$y1);
00391         $rez = adodb_date('Y-n-j H:i:s',$t);
00392         if ("$y1-$m-$d 00:00:00" != $rez) {
00393                 print "<b>$y1 error, expected=$y1-$m-$d 00:00:00, adodb=$rez</b><br>";
00394                 return false;
00395         }
00396         return true;
00397 }
00398 
00399 function adodb_date_test_strftime($fmt)
00400 {
00401         $s1 = strftime($fmt);
00402         $s2 = adodb_strftime($fmt);
00403         
00404         if ($s1 == $s2) return true;
00405         
00406         echo "error for $fmt,  strftime=$s1, $adodb=$s2<br>";
00407         return false;
00408 }
00409 
00413 function adodb_date_test()
00414 {
00415         
00416         error_reporting(E_ALL);
00417         print "<h4>Testing adodb_date and adodb_mktime. version=".ADODB_DATE_VERSION.' PHP='.PHP_VERSION."</h4>";
00418         @set_time_limit(0);
00419         $fail = false;
00420         
00421         // This flag disables calling of PHP native functions, so we can properly test the code
00422         if (!defined('ADODB_TEST_DATES')) define('ADODB_TEST_DATES',1);
00423         
00424         adodb_date_test_strftime('%Y %m %x %X');
00425         adodb_date_test_strftime("%A %d %B %Y");
00426         adodb_date_test_strftime("%H %M S");
00427         
00428         $t = adodb_mktime(0,0,0);
00429         if (!(adodb_date('Y-m-d') == date('Y-m-d'))) print 'Error in '.adodb_mktime(0,0,0).'<br>';
00430         
00431         $t = adodb_mktime(0,0,0,6,1,2102);
00432         if (!(adodb_date('Y-m-d',$t) == '2102-06-01')) print 'Error in '.adodb_date('Y-m-d',$t).'<br>';
00433         
00434         $t = adodb_mktime(0,0,0,2,1,2102);
00435         if (!(adodb_date('Y-m-d',$t) == '2102-02-01')) print 'Error in '.adodb_date('Y-m-d',$t).'<br>';
00436         
00437         
00438         print "<p>Testing gregorian <=> julian conversion<p>";
00439         $t = adodb_mktime(0,0,0,10,11,1492);
00440         //http://www.holidayorigins.com/html/columbus_day.html - Friday check
00441         if (!(adodb_date('D Y-m-d',$t) == 'Fri 1492-10-11')) print 'Error in Columbus landing<br>';
00442         
00443         $t = adodb_mktime(0,0,0,2,29,1500);
00444         if (!(adodb_date('Y-m-d',$t) == '1500-02-29')) print 'Error in julian leap years<br>';
00445         
00446         $t = adodb_mktime(0,0,0,2,29,1700);
00447         if (!(adodb_date('Y-m-d',$t) == '1700-03-01')) print 'Error in gregorian leap years<br>';
00448         
00449         print  adodb_mktime(0,0,0,10,4,1582).' ';
00450         print adodb_mktime(0,0,0,10,15,1582);
00451         $diff = (adodb_mktime(0,0,0,10,15,1582) - adodb_mktime(0,0,0,10,4,1582));
00452         if ($diff != 3600*24) print " <b>Error in gregorian correction = ".($diff/3600/24)." days </b><br>";
00453                 
00454         print " 15 Oct 1582, Fri=".(adodb_dow(1582,10,15) == 5 ? 'Fri' : '<b>Error</b>')."<br>";
00455         print " 4 Oct 1582, Thu=".(adodb_dow(1582,10,4) == 4 ? 'Thu' : '<b>Error</b>')."<br>";
00456         
00457         print "<p>Testing overflow<p>";
00458         
00459         $t = adodb_mktime(0,0,0,3,33,1965);
00460         if (!(adodb_date('Y-m-d',$t) == '1965-04-02')) print 'Error in day overflow 1 <br>';
00461         $t = adodb_mktime(0,0,0,4,33,1971);
00462         if (!(adodb_date('Y-m-d',$t) == '1971-05-03')) print 'Error in day overflow 2 <br>';
00463         $t = adodb_mktime(0,0,0,1,60,1965);
00464         if (!(adodb_date('Y-m-d',$t) == '1965-03-01')) print 'Error in day overflow 3 '.adodb_date('Y-m-d',$t).' <br>';
00465         $t = adodb_mktime(0,0,0,12,32,1965);
00466         if (!(adodb_date('Y-m-d',$t) == '1966-01-01')) print 'Error in day overflow 4 '.adodb_date('Y-m-d',$t).' <br>';
00467         $t = adodb_mktime(0,0,0,12,63,1965);
00468         if (!(adodb_date('Y-m-d',$t) == '1966-02-01')) print 'Error in day overflow 5 '.adodb_date('Y-m-d',$t).' <br>';
00469         $t = adodb_mktime(0,0,0,13,3,1965);
00470         if (!(adodb_date('Y-m-d',$t) == '1966-01-03')) print 'Error in mth overflow 1 <br>';
00471         
00472         print "Testing 2-digit => 4-digit year conversion<p>";
00473         if (adodb_year_digit_check(00) != 2000) print "Err 2-digit 2000<br>";
00474         if (adodb_year_digit_check(10) != 2010) print "Err 2-digit 2010<br>";
00475         if (adodb_year_digit_check(20) != 2020) print "Err 2-digit 2020<br>";
00476         if (adodb_year_digit_check(30) != 2030) print "Err 2-digit 2030<br>";
00477         if (adodb_year_digit_check(40) != 1940) print "Err 2-digit 1940<br>";
00478         if (adodb_year_digit_check(50) != 1950) print "Err 2-digit 1950<br>";
00479         if (adodb_year_digit_check(90) != 1990) print "Err 2-digit 1990<br>";
00480         
00481         // Test string formating
00482         print "<p>Testing date formating</p>";
00483         $fmt = '\d\a\t\e T Y-m-d H:i:s a A d D F g G h H i j l L m M n O \R\F\C2822 r s t U w y Y z Z 2003';
00484         $s1 = date($fmt,0);
00485         $s2 = adodb_date($fmt,0);
00486         if ($s1 != $s2) {
00487                 print " date() 0 failed<br>$s1<br>$s2<br>";
00488         }
00489         flush();
00490         for ($i=100; --$i > 0; ) {
00491 
00492                 $ts = 3600.0*((rand()%60000)+(rand()%60000))+(rand()%60000);
00493                 $s1 = date($fmt,$ts);
00494                 $s2 = adodb_date($fmt,$ts);
00495                 //print "$s1 <br>$s2 <p>";
00496                 $pos = strcmp($s1,$s2);
00497 
00498                 if (($s1) != ($s2)) {
00499                         for ($j=0,$k=strlen($s1); $j < $k; $j++) {
00500                                 if ($s1[$j] != $s2[$j]) {
00501                                         print substr($s1,$j).' ';
00502                                         break;
00503                                 }
00504                         }
00505                         print "<b>Error date(): $ts<br><pre> 
00506 &nbsp; \"$s1\" (date len=".strlen($s1).")
00507 &nbsp; \"$s2\" (adodb_date len=".strlen($s2).")</b></pre><br>";
00508                         $fail = true;
00509                 }
00510                 
00511                 $a1 = getdate($ts);
00512                 $a2 = adodb_getdate($ts);
00513                 $rez = array_diff($a1,$a2);
00514                 if (sizeof($rez)>0) {
00515                         print "<b>Error getdate() $ts</b><br>";
00516                                 print_r($a1);
00517                         print "<br>";
00518                                 print_r($a2);
00519                         print "<p>";
00520                         $fail = true;
00521                 }
00522         }
00523         
00524         // Test generation of dates outside 1901-2038
00525         print "<p>Testing random dates between 100 and 4000</p>";
00526         adodb_date_test_date(100,1);
00527         for ($i=100; --$i >= 0;) {
00528                 $y1 = 100+rand(0,1970-100);
00529                 $m = rand(1,12);
00530                 adodb_date_test_date($y1,$m);
00531                 
00532                 $y1 = 3000-rand(0,3000-1970);
00533                 adodb_date_test_date($y1,$m);
00534         }
00535         print '<p>';
00536         $start = 1960+rand(0,10);
00537         $yrs = 12;
00538         $i = 365.25*86400*($start-1970);
00539         $offset = 36000+rand(10000,60000);
00540         $max = 365*$yrs*86400;
00541         $lastyear = 0;
00542         
00543         // we generate a timestamp, convert it to a date, and convert it back to a timestamp
00544         // and check if the roundtrip broke the original timestamp value.
00545         print "Testing $start to ".($start+$yrs).", or $max seconds, offset=$offset: ";
00546         $cnt = 0;
00547         for ($max += $i; $i < $max; $i += $offset) {
00548                 $ret = adodb_date('m,d,Y,H,i,s',$i);
00549                 $arr = explode(',',$ret);
00550                 if ($lastyear != $arr[2]) {
00551                         $lastyear = $arr[2];
00552                         print " $lastyear ";
00553                         flush();
00554                 }
00555                 $newi = adodb_mktime($arr[3],$arr[4],$arr[5],$arr[0],$arr[1],$arr[2]);
00556                 if ($i != $newi) {
00557                         print "Error at $i, adodb_mktime returned $newi ($ret)";
00558                         $fail = true;
00559                         break;
00560                 }
00561                 $cnt += 1;
00562         }
00563         echo "Tested $cnt dates<br>";
00564         if (!$fail) print "<p>Passed !</p>";
00565         else print "<p><b>Failed</b> :-(</p>";
00566 }
00567 
00572 function adodb_dow($year, $month, $day)
00573 {
00574 /*
00575 Pope Gregory removed 10 days - October 5 to October 14 - from the year 1582 and 
00576 proclaimed that from that time onwards 3 days would be dropped from the calendar 
00577 every 400 years.
00578 
00579 Thursday, October 4, 1582 (Julian) was followed immediately by Friday, October 15, 1582 (Gregorian). 
00580 */
00581         if ($year <= 1582) {
00582                 if ($year < 1582 || 
00583                         ($year == 1582 && ($month < 10 || ($month == 10 && $day < 15)))) $greg_correction = 3;
00584                  else
00585                         $greg_correction = 0;
00586         } else
00587                 $greg_correction = 0;
00588         
00589         if($month > 2)
00590             $month -= 2;
00591         else {
00592             $month += 10;
00593             $year--;
00594         }
00595         
00596         $day =  floor((13 * $month - 1) / 5) +
00597                 $day + ($year % 100) +
00598                 floor(($year % 100) / 4) +
00599                 floor(($year / 100) / 4) - 2 *
00600                 floor($year / 100) + 77 + $greg_correction;
00601         
00602         return $day - 7 * floor($day / 7);
00603 }
00604 
00605 
00610 function _adodb_is_leap_year($year) 
00611 {
00612         if ($year % 4 != 0) return false;
00613         
00614         if ($year % 400 == 0) {
00615                 return true;
00616         // if gregorian calendar (>1582), century not-divisible by 400 is not leap
00617         } else if ($year > 1582 && $year % 100 == 0 ) {
00618                 return false;
00619         } 
00620         
00621         return true;
00622 }
00623 
00624 
00628 function adodb_is_leap_year($year) 
00629 {
00630         return  _adodb_is_leap_year(adodb_year_digit_check($year));
00631 }
00632 
00637 function adodb_year_digit_check($y) 
00638 {
00639         if ($y < 100) {
00640         
00641                 $yr = (integer) date("Y");
00642                 $century = (integer) ($yr /100);
00643                 
00644                 if ($yr%100 > 50) {
00645                         $c1 = $century + 1;
00646                         $c0 = $century;
00647                 } else {
00648                         $c1 = $century;
00649                         $c0 = $century - 1;
00650                 }
00651                 $c1 *= 100;
00652                 // if 2-digit year is less than 30 years in future, set it to this century
00653                 // otherwise if more than 30 years in future, then we set 2-digit year to the prev century.
00654                 if (($y + $c1) < $yr+30) $y = $y + $c1;
00655                 else $y = $y + $c0*100;
00656         }
00657         return $y;
00658 }
00659 
00663 function adodb_get_gmt_diff() 
00664 {
00665 static $TZ;
00666         if (isset($TZ)) return $TZ;
00667         
00668         $TZ = mktime(0,0,0,1,2,1970,0) - gmmktime(0,0,0,1,2,1970,0);
00669         return $TZ;
00670 }
00671 
00675 function adodb_getdate($d=false,$fast=false)
00676 {
00677         if ($d === false) return getdate();
00678         if (!defined('ADODB_TEST_DATES')) {
00679                 if ((abs($d) <= 0x7FFFFFFF)) { // check if number in 32-bit signed range
00680                         if (!defined('ADODB_NO_NEGATIVE_TS') || $d >= 0) // if windows, must be +ve integer
00681                                 return @getdate($d);
00682                 }
00683         }
00684         return _adodb_getdate($d);
00685 }
00686 
00687 /*
00688 // generate $YRS table for _adodb_getdate()
00689 function adodb_date_gentable($out=true)
00690 {
00691 
00692         for ($i=1970; $i >= 1600; $i-=10) {
00693                 $s = adodb_gmmktime(0,0,0,1,1,$i);
00694                 echo "$i => $s,<br>";   
00695         }
00696 }
00697 adodb_date_gentable();
00698 
00699 for ($i=1970; $i > 1500; $i--) {
00700 
00701 echo "<hr />$i ";
00702         adodb_date_test_date($i,1,1);
00703 }
00704 
00705 */
00706 
00707 
00708 $_month_table_normal = array("",31,28,31,30,31,30,31,31,30,31,30,31);
00709 $_month_table_leaf = array("",31,29,31,30,31,30,31,31,30,31,30,31);
00710         
00711 function adodb_validdate($y,$m,$d)
00712 {
00713 global $_month_table_normal,$_month_table_leaf;
00714 
00715         if (_adodb_is_leap_year($y)) $marr =& $_month_table_leaf;
00716         else $marr =& $_month_table_normal;
00717         
00718         if ($m > 12 || $m < 1) return false;
00719         
00720         if ($d > 31 || $d < 1) return false;
00721         
00722         if ($marr[$m] < $d) return false;
00723         
00724         if ($y < 1000 && $y > 3000) return false;
00725         
00726         return true;
00727 }
00728 
00734 function _adodb_getdate($origd=false,$fast=false,$is_gmt=false)
00735 {
00736 static $YRS;
00737 global $_month_table_normal,$_month_table_leaf;
00738 
00739         $d =  $origd - ($is_gmt ? 0 : adodb_get_gmt_diff());
00740         
00741         $_day_power = 86400;
00742         $_hour_power = 3600;
00743         $_min_power = 60;
00744         
00745         if ($d < -12219321600) $d -= 86400*10; // if 15 Oct 1582 or earlier, gregorian correction 
00746         
00747         $_month_table_normal = array("",31,28,31,30,31,30,31,31,30,31,30,31);
00748         $_month_table_leaf = array("",31,29,31,30,31,30,31,31,30,31,30,31);
00749         
00750         $d366 = $_day_power * 366;
00751         $d365 = $_day_power * 365;
00752         
00753         if ($d < 0) {
00754                 
00755                 if (empty($YRS)) $YRS = array(
00756                         1970 => 0,
00757                         1960 => -315619200,
00758                         1950 => -631152000,
00759                         1940 => -946771200,
00760                         1930 => -1262304000,
00761                         1920 => -1577923200,
00762                         1910 => -1893456000,
00763                         1900 => -2208988800,
00764                         1890 => -2524521600,
00765                         1880 => -2840140800,
00766                         1870 => -3155673600,
00767                         1860 => -3471292800,
00768                         1850 => -3786825600,
00769                         1840 => -4102444800,
00770                         1830 => -4417977600,
00771                         1820 => -4733596800,
00772                         1810 => -5049129600,
00773                         1800 => -5364662400,
00774                         1790 => -5680195200,
00775                         1780 => -5995814400,
00776                         1770 => -6311347200,
00777                         1760 => -6626966400,
00778                         1750 => -6942499200,
00779                         1740 => -7258118400,
00780                         1730 => -7573651200,
00781                         1720 => -7889270400,
00782                         1710 => -8204803200,
00783                         1700 => -8520336000,
00784                         1690 => -8835868800,
00785                         1680 => -9151488000,
00786                         1670 => -9467020800,
00787                         1660 => -9782640000,
00788                         1650 => -10098172800,
00789                         1640 => -10413792000,
00790                         1630 => -10729324800,
00791                         1620 => -11044944000,
00792                         1610 => -11360476800,
00793                         1600 => -11676096000);
00794 
00795                 if ($is_gmt) $origd = $d;
00796                 // The valid range of a 32bit signed timestamp is typically from 
00797                 // Fri, 13 Dec 1901 20:45:54 GMT to Tue, 19 Jan 2038 03:14:07 GMT
00798                 //
00799                 
00800                 # old algorithm iterates through all years. new algorithm does it in
00801                 # 10 year blocks
00802                 
00803                 /*
00804                 # old algo
00805                 for ($a = 1970 ; --$a >= 0;) {
00806                         $lastd = $d;
00807                         
00808                         if ($leaf = _adodb_is_leap_year($a)) $d += $d366;
00809                         else $d += $d365;
00810                         
00811                         if ($d >= 0) {
00812                                 $year = $a;
00813                                 break;
00814                         }
00815                 }
00816                 */
00817                 
00818                 $lastsecs = 0;
00819                 $lastyear = 1970;
00820                 foreach($YRS as $year => $secs) {
00821                         if ($d >= $secs) {
00822                                 $a = $lastyear;
00823                                 break;
00824                         }
00825                         $lastsecs = $secs;
00826                         $lastyear = $year;
00827                 }
00828                 
00829                 $d -= $lastsecs;
00830                 if (!isset($a)) $a = $lastyear;
00831                 
00832                 //echo ' yr=',$a,' ', $d,'.';
00833                 
00834                 for (; --$a >= 0;) {
00835                         $lastd = $d;
00836                         
00837                         if ($leaf = _adodb_is_leap_year($a)) $d += $d366;
00838                         else $d += $d365;
00839                         
00840                         if ($d >= 0) {
00841                                 $year = $a;
00842                                 break;
00843                         }
00844                 }
00845                 
00846                 
00847                 $secsInYear = 86400 * ($leaf ? 366 : 365) + $lastd;
00848                 
00849                 $d = $lastd;
00850                 $mtab = ($leaf) ? $_month_table_leaf : $_month_table_normal;
00851                 for ($a = 13 ; --$a > 0;) {
00852                         $lastd = $d;
00853                         $d += $mtab[$a] * $_day_power;
00854                         if ($d >= 0) {
00855                                 $month = $a;
00856                                 $ndays = $mtab[$a];
00857                                 break;
00858                         }
00859                 }
00860                 
00861                 $d = $lastd;
00862                 $day = $ndays + ceil(($d+1) / ($_day_power));
00863 
00864                 $d += ($ndays - $day+1)* $_day_power;
00865                 $hour = floor($d/$_hour_power);
00866         
00867         } else {
00868                 for ($a = 1970 ;; $a++) {
00869                         $lastd = $d;
00870                         
00871                         if ($leaf = _adodb_is_leap_year($a)) $d -= $d366;
00872                         else $d -= $d365;
00873                         if ($d < 0) {
00874                                 $year = $a;
00875                                 break;
00876                         }
00877                 }
00878                 $secsInYear = $lastd;
00879                 $d = $lastd;
00880                 $mtab = ($leaf) ? $_month_table_leaf : $_month_table_normal;
00881                 for ($a = 1 ; $a <= 12; $a++) {
00882                         $lastd = $d;
00883                         $d -= $mtab[$a] * $_day_power;
00884                         if ($d < 0) {
00885                                 $month = $a;
00886                                 $ndays = $mtab[$a];
00887                                 break;
00888                         }
00889                 }
00890                 $d = $lastd;
00891                 $day = ceil(($d+1) / $_day_power);
00892                 $d = $d - ($day-1) * $_day_power;
00893                 $hour = floor($d /$_hour_power);
00894         }
00895         
00896         $d -= $hour * $_hour_power;
00897         $min = floor($d/$_min_power);
00898         $secs = $d - $min * $_min_power;
00899         if ($fast) {
00900                 return array(
00901                 'seconds' => $secs,
00902                 'minutes' => $min,
00903                 'hours' => $hour,
00904                 'mday' => $day,
00905                 'mon' => $month,
00906                 'year' => $year,
00907                 'yday' => floor($secsInYear/$_day_power),
00908                 'leap' => $leaf,
00909                 'ndays' => $ndays
00910                 );
00911         }
00912         
00913         
00914         $dow = adodb_dow($year,$month,$day);
00915 
00916         return array(
00917                 'seconds' => $secs,
00918                 'minutes' => $min,
00919                 'hours' => $hour,
00920                 'mday' => $day,
00921                 'wday' => $dow,
00922                 'mon' => $month,
00923                 'year' => $year,
00924                 'yday' => floor($secsInYear/$_day_power),
00925                 'weekday' => gmdate('l',$_day_power*(3+$dow)),
00926                 'month' => gmdate('F',mktime(0,0,0,$month,2,1971)),
00927                 0 => $origd
00928         );
00929 }
00930 
00931 function adodb_gmdate($fmt,$d=false)
00932 {
00933         return adodb_date($fmt,$d,true);
00934 }
00935 
00936 // accepts unix timestamp and iso date format in $d
00937 function adodb_date2($fmt, $d=false, $is_gmt=false)
00938 {
00939         if ($d !== false) {
00940                 if (!preg_match( 
00941                         "|^([0-9]{4})[-/\.]?([0-9]{1,2})[-/\.]?([0-9]{1,2})[ -]?(([0-9]{1,2}):?([0-9]{1,2}):?([0-9\.]{1,4}))?|", 
00942                         ($d), $rr)) return adodb_date($fmt,false,$is_gmt);
00943 
00944                 if ($rr[1] <= 100 && $rr[2]<= 1) return adodb_date($fmt,false,$is_gmt);
00945         
00946                 // h-m-s-MM-DD-YY
00947                 if (!isset($rr[5])) $d = adodb_mktime(0,0,0,$rr[2],$rr[3],$rr[1],false,$is_gmt);
00948                 else $d = @adodb_mktime($rr[5],$rr[6],$rr[7],$rr[2],$rr[3],$rr[1],false,$is_gmt);
00949         }
00950         
00951         return adodb_date($fmt,$d,$is_gmt);
00952 }
00953 
00954 
00958 function adodb_date($fmt,$d=false,$is_gmt=false)
00959 {
00960 static $daylight;
00961 
00962         if ($d === false) return ($is_gmt)? @gmdate($fmt): @date($fmt);
00963         if (!defined('ADODB_TEST_DATES')) {
00964                 if ((abs($d) <= 0x7FFFFFFF)) { // check if number in 32-bit signed range
00965                         if (!defined('ADODB_NO_NEGATIVE_TS') || $d >= 0) // if windows, must be +ve integer
00966                                 return ($is_gmt)? @gmdate($fmt,$d): @date($fmt,$d);
00967 
00968                 }
00969         }
00970         $_day_power = 86400;
00971         
00972         $arr = _adodb_getdate($d,true,$is_gmt);
00973         
00974         if (!isset($daylight)) $daylight = function_exists('adodb_daylight_sv');
00975         if ($daylight) adodb_daylight_sv($arr, $is_gmt);
00976         
00977         $year = $arr['year'];
00978         $month = $arr['mon'];
00979         $day = $arr['mday'];
00980         $hour = $arr['hours'];
00981         $min = $arr['minutes'];
00982         $secs = $arr['seconds'];
00983         
00984         $max = strlen($fmt);
00985         $dates = '';
00986         
00987         $isphp5 = PHP_VERSION >= 5;
00988         
00989         /*
00990                 at this point, we have the following integer vars to manipulate:
00991                 $year, $month, $day, $hour, $min, $secs
00992         */
00993         for ($i=0; $i < $max; $i++) {
00994                 switch($fmt[$i]) {
00995                 case 'T': $dates .= date('T');break;
00996                 // YEAR
00997                 case 'L': $dates .= $arr['leap'] ? '1' : '0'; break;
00998                 case 'r': // Thu, 21 Dec 2000 16:01:07 +0200
00999                 
01000                         // 4.3.11 uses '04 Jun 2004'
01001                         // 4.3.8 uses  ' 4 Jun 2004'
01002                         $dates .= gmdate('D',$_day_power*(3+adodb_dow($year,$month,$day))).', '         
01003                                 . ($day<10?'0'.$day:$day) . ' '.date('M',mktime(0,0,0,$month,2,1971)).' '.$year.' ';
01004                         
01005                         if ($hour < 10) $dates .= '0'.$hour; else $dates .= $hour; 
01006                         
01007                         if ($min < 10) $dates .= ':0'.$min; else $dates .= ':'.$min;
01008                         
01009                         if ($secs < 10) $dates .= ':0'.$secs; else $dates .= ':'.$secs;
01010                         
01011                         $gmt = adodb_get_gmt_diff();
01012                         if ($isphp5) 
01013                                 $dates .= sprintf(' %s%04d',($gmt<=0)?'+':'-',abs($gmt)/36); 
01014                         else
01015                                 $dates .= sprintf(' %s%04d',($gmt<0)?'+':'-',abs($gmt)/36); 
01016                         break;
01017                                 
01018                 case 'Y': $dates .= $year; break;
01019                 case 'y': $dates .= substr($year,strlen($year)-2,2); break;
01020                 // MONTH
01021                 case 'm': if ($month<10) $dates .= '0'.$month; else $dates .= $month; break;
01022                 case 'Q': $dates .= ($month+3)>>2; break;
01023                 case 'n': $dates .= $month; break;
01024                 case 'M': $dates .= date('M',mktime(0,0,0,$month,2,1971)); break;
01025                 case 'F': $dates .= date('F',mktime(0,0,0,$month,2,1971)); break;
01026                 // DAY
01027                 case 't': $dates .= $arr['ndays']; break;
01028                 case 'z': $dates .= $arr['yday']; break;
01029                 case 'w': $dates .= adodb_dow($year,$month,$day); break;
01030                 case 'l': $dates .= gmdate('l',$_day_power*(3+adodb_dow($year,$month,$day))); break;
01031                 case 'D': $dates .= gmdate('D',$_day_power*(3+adodb_dow($year,$month,$day))); break;
01032                 case 'j': $dates .= $day; break;
01033                 case 'd': if ($day<10) $dates .= '0'.$day; else $dates .= $day; break;
01034                 case 'S': 
01035                         $d10 = $day % 10;
01036                         if ($d10 == 1) $dates .= 'st';
01037                         else if ($d10 == 2 && $day != 12) $dates .= 'nd';
01038                         else if ($d10 == 3) $dates .= 'rd';
01039                         else $dates .= 'th';
01040                         break;
01041                         
01042                 // HOUR
01043                 case 'Z':
01044                         $dates .= ($is_gmt) ? 0 : -adodb_get_gmt_diff(); break;
01045                 case 'O': 
01046                         $gmt = ($is_gmt) ? 0 : adodb_get_gmt_diff();
01047                         
01048                         if ($isphp5)
01049                                 $dates .= sprintf('%s%04d',($gmt<=0)?'+':'-',abs($gmt)/36); 
01050                         else
01051                                 $dates .= sprintf('%s%04d',($gmt<0)?'+':'-',abs($gmt)/36); 
01052                         break;
01053                         
01054                 case 'H': 
01055                         if ($hour < 10) $dates .= '0'.$hour; 
01056                         else $dates .= $hour; 
01057                         break;
01058                 case 'h': 
01059                         if ($hour > 12) $hh = $hour - 12; 
01060                         else {
01061                                 if ($hour == 0) $hh = '12'; 
01062                                 else $hh = $hour;
01063                         }
01064                         
01065                         if ($hh < 10) $dates .= '0'.$hh;
01066                         else $dates .= $hh;
01067                         break;
01068                         
01069                 case 'G': 
01070                         $dates .= $hour;
01071                         break;
01072                         
01073                 case 'g':
01074                         if ($hour > 12) $hh = $hour - 12; 
01075                         else {
01076                                 if ($hour == 0) $hh = '12'; 
01077                                 else $hh = $hour; 
01078                         }
01079                         $dates .= $hh;
01080                         break;
01081                 // MINUTES
01082                 case 'i': if ($min < 10) $dates .= '0'.$min; else $dates .= $min; break;
01083                 // SECONDS
01084                 case 'U': $dates .= $d; break;
01085                 case 's': if ($secs < 10) $dates .= '0'.$secs; else $dates .= $secs; break;
01086                 // AM/PM
01087                 // Note 00:00 to 11:59 is AM, while 12:00 to 23:59 is PM
01088                 case 'a':
01089                         if ($hour>=12) $dates .= 'pm';
01090                         else $dates .= 'am';
01091                         break;
01092                 case 'A':
01093                         if ($hour>=12) $dates .= 'PM';
01094                         else $dates .= 'AM';
01095                         break;
01096                 default:
01097                         $dates .= $fmt[$i]; break;
01098                 // ESCAPE
01099                 case "\\": 
01100                         $i++;
01101                         if ($i < $max) $dates .= $fmt[$i];
01102                         break;
01103                 }
01104         }
01105         return $dates;
01106 }
01107 
01112 function adodb_gmmktime($hr,$min,$sec,$mon=false,$day=false,$year=false,$is_dst=false)
01113 {
01114         return adodb_mktime($hr,$min,$sec,$mon,$day,$year,$is_dst,true);
01115 }
01116 
01123 function adodb_mktime($hr,$min,$sec,$mon=false,$day=false,$year=false,$is_dst=false,$is_gmt=false) 
01124 {
01125         if (!defined('ADODB_TEST_DATES')) {
01126 
01127                 if ($mon === false) {
01128                         return $is_gmt? @gmmktime($hr,$min,$sec): @mktime($hr,$min,$sec);
01129                 }
01130                 
01131                 // for windows, we don't check 1970 because with timezone differences, 
01132                 // 1 Jan 1970 could generate negative timestamp, which is illegal
01133                 if (1971 < $year && $year < 2038
01134                         || !defined('ADODB_NO_NEGATIVE_TS') && (1901 < $year && $year < 2038)
01135                         ) {
01136                                 return $is_gmt ?
01137                                         @gmmktime($hr,$min,$sec,$mon,$day,$year):
01138                                         @mktime($hr,$min,$sec,$mon,$day,$year);
01139                         }
01140         }
01141         
01142         $gmt_different = ($is_gmt) ? 0 : adodb_get_gmt_diff();
01143 
01144         /*
01145         # disabled because some people place large values in $sec.
01146         # however we need it for $mon because we use an array...
01147         $hr = intval($hr);
01148         $min = intval($min);
01149         $sec = intval($sec);
01150         */
01151         $mon = intval($mon);
01152         $day = intval($day);
01153         $year = intval($year);
01154         
01155         
01156         $year = adodb_year_digit_check($year);
01157 
01158         if ($mon > 12) {
01159                 $y = floor($mon / 12);
01160                 $year += $y;
01161                 $mon -= $y*12;
01162         } else if ($mon < 1) {
01163                 $y = ceil((1-$mon) / 12);
01164                 $year -= $y;
01165                 $mon += $y*12;
01166         }
01167         
01168         $_day_power = 86400;
01169         $_hour_power = 3600;
01170         $_min_power = 60;
01171         
01172         $_month_table_normal = array("",31,28,31,30,31,30,31,31,30,31,30,31);
01173         $_month_table_leaf = array("",31,29,31,30,31,30,31,31,30,31,30,31);
01174         
01175         $_total_date = 0;
01176         if ($year >= 1970) {
01177                 for ($a = 1970 ; $a <= $year; $a++) {
01178                         $leaf = _adodb_is_leap_year($a);
01179                         if ($leaf == true) {
01180                                 $loop_table = $_month_table_leaf;
01181                                 $_add_date = 366;
01182                         } else {
01183                                 $loop_table = $_month_table_normal;
01184                                 $_add_date = 365;
01185                         }
01186                         if ($a < $year) { 
01187                                 $_total_date += $_add_date;
01188                         } else {
01189                                 for($b=1;$b<$mon;$b++) {
01190                                         $_total_date += $loop_table[$b];
01191                                 }
01192                         }
01193                 }
01194                 $_total_date +=$day-1;
01195                 $ret = $_total_date * $_day_power + $hr * $_hour_power + $min * $_min_power + $sec + $gmt_different;
01196         
01197         } else {
01198                 for ($a = 1969 ; $a >= $year; $a--) {
01199                         $leaf = _adodb_is_leap_year($a);
01200                         if ($leaf == true) {
01201                                 $loop_table = $_month_table_leaf;
01202                                 $_add_date = 366;
01203                         } else {
01204                                 $loop_table = $_month_table_normal;
01205                                 $_add_date = 365;
01206                         }
01207                         if ($a > $year) { $_total_date += $_add_date;
01208                         } else {
01209                                 for($b=12;$b>$mon;$b--) {
01210                                         $_total_date += $loop_table[$b];
01211                                 }
01212                         }
01213                 }
01214                 $_total_date += $loop_table[$mon] - $day;
01215                 
01216                 $_day_time = $hr * $_hour_power + $min * $_min_power + $sec;
01217                 $_day_time = $_day_power - $_day_time;
01218                 $ret = -( $_total_date * $_day_power + $_day_time - $gmt_different);
01219                 if ($ret < -12220185600) $ret += 10*86400; // if earlier than 5 Oct 1582 - gregorian correction
01220                 else if ($ret < -12219321600) $ret = -12219321600; // if in limbo, reset to 15 Oct 1582.
01221         } 
01222         //print " dmy=$day/$mon/$year $hr:$min:$sec => " .$ret;
01223         return $ret;
01224 }
01225 
01226 function adodb_gmstrftime($fmt, $ts=false)
01227 {
01228         return adodb_strftime($fmt,$ts,true);
01229 }
01230 
01231 // hack - convert to adodb_date
01232 function adodb_strftime($fmt, $ts=false,$is_gmt=false)
01233 {
01234 global $ADODB_DATE_LOCALE;
01235 
01236         if (!defined('ADODB_TEST_DATES')) {
01237                 if ((abs($ts) <= 0x7FFFFFFF)) { // check if number in 32-bit signed range
01238                         if (!defined('ADODB_NO_NEGATIVE_TS') || $ts >= 0) // if windows, must be +ve integer
01239                                 return ($is_gmt)? @gmstrftime($fmt,$ts): @strftime($fmt,$ts);
01240 
01241                 }
01242         }
01243         
01244         if (empty($ADODB_DATE_LOCALE)) {
01245         /*
01246                 $tstr = strtoupper(gmstrftime('%c',31366800)); // 30 Dec 1970, 1 am
01247                 $sep = substr($tstr,2,1);
01248                 $hasAM = strrpos($tstr,'M') !== false;
01249         */
01250                 # see http://phplens.com/lens/lensforum/msgs.php?id=14865 for reasoning, and changelog for version 0.24
01251                 $dstr = gmstrftime('%x',31366800); // 30 Dec 1970, 1 am
01252                 $sep = substr($dstr,2,1);
01253                 $tstr = strtoupper(gmstrftime('%X',31366800)); // 30 Dec 1970, 1 am
01254                 $hasAM = strrpos($tstr,'M') !== false;
01255                 
01256                 $ADODB_DATE_LOCALE = array();
01257                 $ADODB_DATE_LOCALE[] =  strncmp($tstr,'30',2) == 0 ? 'd'.$sep.'m'.$sep.'y' : 'm'.$sep.'d'.$sep.'y';     
01258                 $ADODB_DATE_LOCALE[]  = ($hasAM) ? 'h:i:s a' : 'H:i:s';
01259                         
01260         }
01261         $inpct = false;
01262         $fmtdate = '';
01263         for ($i=0,$max = strlen($fmt); $i < $max; $i++) {
01264                 $ch = $fmt[$i];
01265                 if ($ch == '%') {
01266                         if ($inpct) {
01267                                 $fmtdate .= '%';
01268                                 $inpct = false;
01269                         } else
01270                                 $inpct = true;
01271                 } else if ($inpct) {
01272                 
01273                         $inpct = false;
01274                         switch($ch) {
01275                         case '0':
01276                         case '1':
01277                         case '2':
01278                         case '3':
01279                         case '4':
01280                         case '5':
01281                         case '6':
01282                         case '7':
01283                         case '8':
01284                         case '9':
01285                         case 'E':
01286                         case 'O':
01287                                 /* ignore format modifiers */
01288                                 $inpct = true; 
01289                                 break;
01290                                 
01291                         case 'a': $fmtdate .= 'D'; break;
01292                         case 'A': $fmtdate .= 'l'; break;
01293                         case 'h':
01294                         case 'b': $fmtdate .= 'M'; break;
01295                         case 'B': $fmtdate .= 'F'; break;
01296                         case 'c': $fmtdate .= $ADODB_DATE_LOCALE[0].$ADODB_DATE_LOCALE[1]; break;
01297                         case 'C': $fmtdate .= '\C?'; break; // century
01298                         case 'd': $fmtdate .= 'd'; break;
01299                         case 'D': $fmtdate .= 'm/d/y'; break;
01300                         case 'e': $fmtdate .= 'j'; break;
01301                         case 'g': $fmtdate .= '\g?'; break; //?
01302                         case 'G': $fmtdate .= '\G?'; break; //?
01303                         case 'H': $fmtdate .= 'H'; break;
01304                         case 'I': $fmtdate .= 'h'; break;
01305                         case 'j': $fmtdate .= '?z'; $parsej = true; break; // wrong as j=1-based, z=0-basd
01306                         case 'm': $fmtdate .= 'm'; break;
01307                         case 'M': $fmtdate .= 'i'; break;
01308                         case 'n': $fmtdate .= "\n"; break;
01309                         case 'p': $fmtdate .= 'a'; break;
01310                         case 'r': $fmtdate .= 'h:i:s a'; break;
01311                         case 'R': $fmtdate .= 'H:i:s'; break;
01312                         case 'S': $fmtdate .= 's'; break;
01313                         case 't': $fmtdate .= "\t"; break;
01314                         case 'T': $fmtdate .= 'H:i:s'; break;
01315                         case 'u': $fmtdate .= '?u'; $parseu = true; break; // wrong strftime=1-based, date=0-based
01316                         case 'U': $fmtdate .= '?U'; $parseU = true; break;// wrong strftime=1-based, date=0-based
01317                         case 'x': $fmtdate .= $ADODB_DATE_LOCALE[0]; break;
01318                         case 'X': $fmtdate .= $ADODB_DATE_LOCALE[1]; break;
01319                         case 'w': $fmtdate .= '?w'; $parseu = true; break; // wrong strftime=1-based, date=0-based
01320                         case 'W': $fmtdate .= '?W'; $parseU = true; break;// wrong strftime=1-based, date=0-based
01321                         case 'y': $fmtdate .= 'y'; break;
01322                         case 'Y': $fmtdate .= 'Y'; break;
01323                         case 'Z': $fmtdate .= 'T'; break;
01324                         }
01325                 } else if (('A' <= ($ch) && ($ch) <= 'Z' ) || ('a' <= ($ch) && ($ch) <= 'z' ))
01326                         $fmtdate .= "\\".$ch;
01327                 else
01328                         $fmtdate .= $ch;
01329         }
01330         //echo "fmt=",$fmtdate,"<br>";
01331         if ($ts === false) $ts = time();
01332         $ret = adodb_date($fmtdate, $ts, $is_gmt);
01333         return $ret;
01334 }
01335 
01336 
01337 ?>