PageRenderTime 47ms CodeModel.GetById 17ms RepoModel.GetById 0ms app.codeStats 0ms

/html/sites/all/modules/date/date_php4/date_php4_lib.inc

https://github.com/mfb/vozmob
Pascal | 443 lines | 184 code | 12 blank | 247 comment | 40 complexity | cdd51d493a06e993ec5cf3c8ca286cf5 MD5 | raw file
Possible License(s): GPL-2.0
  1. <?php
  2. // $Id: date_php4_lib.inc,v 1.4.4.7 2009/02/24 17:14:06 karens Exp $
  3. /**
  4. * Date Library, extended date functions.
  5. * File is included only when needed.
  6. */
  7. /**
  8. * @ingroup adodb
  9. * @{
  10. */
  11. /**
  12. * The following functions are low level functions that implements pre 1970
  13. * to post 2038 versions of native php date functions. Will handle dates from
  14. * the year 100 to the year 3000. Uses native php date functions when possible,
  15. * alterate methods when native functions won't work.
  16. *
  17. * Altered the original ADODB code to split it between the high level
  18. * functions which are used when pre-1970 and post-2038 dates are not needed
  19. * and this large file which is only parsed for dates that are out of range
  20. * for native php date handling.
  21. *
  22. * Replace native php functions:
  23. * getdate() with date_getdate()
  24. * date() with date_date()
  25. * gmdate() with date_gmdate()
  26. * mktime() with date_mktime()
  27. * gmmktime() with gmdate_mktime()
  28. *
  29. * The following functions were derived from code obtained from
  30. * http://phplens.com/phpeverywhere/adodb_date_library, licensed as follows:
  31. *
  32. * COPYRIGHT(c) 2003-2005 John Lim
  33. * All rights reserved.
  34. *
  35. * Redistribution and use in source and binary forms, with or without
  36. * modification, are permitted under the terms of the BSD License.
  37. *
  38. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  39. * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  40. * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
  41. * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
  42. * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
  43. * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
  44. * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  45. * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  46. * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  47. * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
  48. * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  49. * POSSIBILITY OF SUCH DAMAGE.
  50. */
  51. /**
  52. * Low-level function that returns the getdate() array for pre-1970
  53. * and post-2038 dates.
  54. *
  55. * We have a special$fast flag, which if set to true, will return fewer
  56. * array values, and is much faster as it does not calculate dow, etc.
  57. *
  58. * @param $timestamp a unix timestamp
  59. * @param $timezone name
  60. * Use 'UTC' to avoid timezone conversion.
  61. */
  62. function _date_getdate($timestamp = false, $timezone = false) {
  63. static $YRS;
  64. if ($timezone === FALSE) {
  65. $timezone = date_default_timezone_name();
  66. }
  67. $timestamp_in = $timestamp;
  68. $_day_power = 86400;
  69. $_hour_power = 3600;
  70. $_min_power = 60;
  71. if ($timestamp < -12219321600) $timestamp -= 86400*10; // if 15 Oct 1582 or earlier, gregorian correction
  72. $_month_table_normal = array("", 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
  73. $_month_table_leap = array("", 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
  74. $d366 = $_day_power * 366;
  75. $d365 = $_day_power * 365;
  76. if ($timestamp < 0) {
  77. if (empty($YRS)) $YRS = array(
  78. 1970 => 0,
  79. 1960 => -315619200,
  80. 1950 => -631152000,
  81. 1940 => -946771200,
  82. 1930 => -1262304000,
  83. 1920 => -1577923200,
  84. 1910 => -1893456000,
  85. 1900 => -2208988800,
  86. 1890 => -2524521600,
  87. 1880 => -2840140800,
  88. 1870 => -3155673600,
  89. 1860 => -3471292800,
  90. 1850 => -3786825600,
  91. 1840 => -4102444800,
  92. 1830 => -4417977600,
  93. 1820 => -4733596800,
  94. 1810 => -5049129600,
  95. 1800 => -5364662400,
  96. 1790 => -5680195200,
  97. 1780 => -5995814400,
  98. 1770 => -6311347200,
  99. 1760 => -6626966400,
  100. 1750 => -6942499200,
  101. 1740 => -7258118400,
  102. 1730 => -7573651200,
  103. 1720 => -7889270400,
  104. 1710 => -8204803200,
  105. 1700 => -8520336000,
  106. 1690 => -8835868800,
  107. 1680 => -9151488000,
  108. 1670 => -9467020800,
  109. 1660 => -9782640000,
  110. 1650 => -10098172800,
  111. 1640 => -10413792000,
  112. 1630 => -10729324800,
  113. 1620 => -11044944000,
  114. 1610 => -11360476800,
  115. 1600 => -11676096000);
  116. // The valid range of a 32bit signed timestamp is typically from
  117. // Fri, 13 Dec 1901 20:45:54 GMT to Tue, 19 Jan 2038 03:14:07 GMT
  118. //
  119. $lastsecs = 0;
  120. $lastyear = 1970;
  121. foreach ($YRS as $year => $secs) {
  122. if ($timestamp >= $secs) {
  123. $a = $lastyear;
  124. break;
  125. }
  126. $lastsecs = $secs;
  127. $lastyear = $year;
  128. }
  129. $timestamp -= $lastsecs;
  130. if (!isset($a)) $a = $lastyear;
  131. for (; --$a >= 0;) {
  132. $lastd = $timestamp;
  133. if ($leap = date_is_leap_year($a)) $timestamp += $d366;
  134. else $timestamp += $d365;
  135. if ($timestamp >= 0) {
  136. $year = $a;
  137. break;
  138. }
  139. }
  140. $secs_in_year = 86400 * ($leap ? 366 : 365) + $lastd;
  141. $timestamp = $lastd;
  142. $mtab = ($leap) ? $_month_table_leap : $_month_table_normal;
  143. for ($a = 13 ; --$a > 0;) {
  144. $lastd = $timestamp;
  145. $timestamp += $mtab[$a] * $_day_power;
  146. if ($timestamp >= 0) {
  147. $month = $a;
  148. $ndays = $mtab[$a];
  149. break;
  150. }
  151. }
  152. $timestamp = $lastd;
  153. $day = $ndays + ceil(($timestamp+1) / ($_day_power));
  154. $timestamp += ($ndays - $day+1)* $_day_power;
  155. $hour = floor($timestamp/$_hour_power);
  156. }
  157. else {
  158. if ($timezone != 'UTC') {
  159. $timestamp += date_get_gmt_diff_ts($timestamp, $timezone);
  160. }
  161. for ($a = 1970 ;; $a++) {
  162. $lastd = $timestamp;
  163. if ($leap = date_is_leap_year($a)) $timestamp -= $d366;
  164. else $timestamp -= $d365;
  165. if ($timestamp < 0) {
  166. $year = $a;
  167. break;
  168. }
  169. }
  170. $secs_in_year = $lastd;
  171. $timestamp = $lastd;
  172. $mtab = ($leap) ? $_month_table_leap : $_month_table_normal;
  173. for ($a = 1 ; $a <= 12; $a++) {
  174. $lastd = $timestamp;
  175. $timestamp -= $mtab[$a] * $_day_power;
  176. if ($timestamp < 0) {
  177. $month = $a;
  178. $ndays = $mtab[$a];
  179. break;
  180. }
  181. }
  182. $timestamp = $lastd;
  183. $day = ceil(($timestamp + 1) / $_day_power);
  184. $timestamp = $timestamp - ($day - 1) * $_day_power;
  185. $hour = floor($timestamp / $_hour_power);
  186. }
  187. $timestamp -= $hour * $_hour_power;
  188. $min = floor($timestamp / $_min_power);
  189. $secs = $timestamp - $min * $_min_power;
  190. $dow = date_dow($day, $month, $year);
  191. return array(
  192. 'second' => $secs,
  193. 'minute' => $min,
  194. 'hour' => $hour,
  195. 'day' => $day,
  196. 'wday' => $dow,
  197. 'month' => $month,
  198. 'year' => $year,
  199. 'yday' => floor($secs_in_year / $_day_power),
  200. 'weekday' => gmdate('l', ($_day_power * (3 + $dow))),
  201. 'leap' => $leap,
  202. 'ndays' => $ndays,
  203. 'month_name' => gmdate('F', mktime(0, 0, 0, $month, 2, 1971)),
  204. 0 => $timestamp_in
  205. );
  206. }
  207. /**
  208. * Low level function to create date() for pre-1970 and post-2038 dates.
  209. *
  210. * @param $format a format string for the result
  211. * @param $timestamp a unix timestamp
  212. * @param $timezone name
  213. * Use 'UTC' to avoid timezone conversion.
  214. */
  215. function _date_date($format, $timestamp = false, $timezone = false) {
  216. if ($timezone === FALSE) {
  217. $timezone = date_default_timezone_name();
  218. }
  219. $_day_power = 86400;
  220. $arr = _date_getdate($timestamp, $timezone);
  221. $year = $arr['year'];
  222. $month = $arr['month'];
  223. $day = $arr['day'];
  224. $hour = $arr['hour'];
  225. $min = $arr['minute'];
  226. $secs = $arr['second'];
  227. $max = strlen($format);
  228. $dates = '';
  229. /*
  230. at this point, we have the following integer vars to manipulate:
  231. $year, $month, $day, $hour, $min, $secs
  232. */
  233. for ($i = 0; $i < $max; $i++) {
  234. switch ($format[$i]) {
  235. case 'T': $dates .= date('T');break;
  236. // YEAR
  237. case 'L': $dates .= $arr['leap'] ? '1' : '0'; break;
  238. case 'r': // Thu, 21 Dec 2000 16:01:07 +0200
  239. // 4.3.11 uses '04 Jun 2004'
  240. // 4.3.8 uses ' 4 Jun 2004'
  241. $dates .= gmdate('D', $_day_power*(3 + date_dow($day, $month, $year))) .', '.
  242. ($day < 10 ? '0'. $day : $day) .' '. date('M', mktime(0, 0, 0, $month, 2, 1971)) .' '. $year .' ';
  243. if ($hour < 10) $dates .= '0'. $hour; else $dates .= $hour;
  244. if ($min < 10) $dates .= ':0'. $min; else $dates .= ':'. $min;
  245. if ($secs < 10) $dates .= ':0'. $secs; else $dates .= ':'. $secs;
  246. $gmt = date_get_gmt_diff_ts($timestamp, $timezone);
  247. $dates .= sprintf(' %s%04d', ($gmt >= 0) ? '+' : '-', abs($gmt) / 36); break;
  248. case 'Y': $dates .= date_pad($year, 4); break;
  249. case 'y': $dates .= substr($year, strlen($year)-2, 2); break;
  250. // MONTH
  251. case 'm': if ($month<10) $dates .= '0'. $month; else $dates .= $month; break;
  252. case 'Q': $dates .= ($month + 3)>>2; break;
  253. case 'n': $dates .= $month; break;
  254. case 'M': $dates .= date('M', mktime(0, 0, 0, $month, 2, 1971)); break;
  255. case 'F': $dates .= date('F', mktime(0, 0, 0, $month, 2, 1971)); break;
  256. // DAY
  257. case 't': $dates .= $arr['ndays']; break;
  258. case 'z': $dates .= $arr['yday']; break;
  259. case 'w': $dates .= date_dow($day, $month, $year); break;
  260. case 'l': $dates .= gmdate('l', $_day_power*(3 + date_dow($day, $month, $year))); break;
  261. case 'D': $dates .= gmdate('D', $_day_power*(3 + date_dow($day, $month, $year))); break;
  262. case 'j': $dates .= $day; break;
  263. case 'd': if ($day<10) $dates .= '0'. $day; else $dates .= $day; break;
  264. case 'S':
  265. $d10 = $day % 10;
  266. if ($d10 == 1) $dates .= 'st';
  267. else if ($d10 == 2 && $day != 12) $dates .= 'nd';
  268. else if ($d10 == 3) $dates .= 'rd';
  269. else $dates .= 'th';
  270. break;
  271. // HOUR
  272. case 'Z':
  273. $dates .= -date_get_gmt_diff_ts($timestamp, $timezone);
  274. break;
  275. case 'O':
  276. $gmt = date_get_gmt_diff_ts($timestamp, $timezone);
  277. $dates .= sprintf('%s%04d', ($gmt<0)?'+':'-', abs($gmt)/36);
  278. break;
  279. case 'H':
  280. if ($hour < 10) $dates .= '0'. $hour;
  281. else $dates .= $hour;
  282. break;
  283. case 'h':
  284. if ($hour > 12) $hh = $hour - 12;
  285. else {
  286. if ($hour == 0) $hh = '12';
  287. else $hh = $hour;
  288. }
  289. if ($hh < 10) $dates .= '0'. $hh;
  290. else $dates .= $hh;
  291. break;
  292. case 'G':
  293. $dates .= $hour;
  294. break;
  295. case 'g':
  296. if ($hour > 12) $hh = $hour - 12;
  297. else {
  298. if ($hour == 0) $hh = '12';
  299. else $hh = $hour;
  300. }
  301. $dates .= $hh;
  302. break;
  303. // MINUTES
  304. case 'i': if ($min < 10) $dates .= '0'. $min; else $dates .= $min; break;
  305. // SECONDS
  306. case 'U': $dates .= $timestamp; break;
  307. case 's': if ($secs < 10) $dates .= '0'. $secs; else $dates .= $secs; break;
  308. // AM/PM
  309. // Note 00:00 to 11:59 is AM, while 12:00 to 23:59 is PM
  310. case 'a':
  311. if ($hour>=12) $dates .= 'pm';
  312. else $dates .= 'am';
  313. break;
  314. case 'A':
  315. if ($hour>=12) $dates .= 'PM';
  316. else $dates .= 'AM';
  317. break;
  318. default:
  319. $dates .= $format[$i]; break;
  320. // ESCAPE
  321. case "\\":
  322. $i++;
  323. if ($i < $max) $dates .= $format[$i];
  324. break;
  325. }
  326. }
  327. return $dates;
  328. }
  329. /**
  330. * Low level function to create mktime() for pre-1970 and post 2038 dates.
  331. *
  332. * @param $hr the hour
  333. * @param $min the minute
  334. * @param $sec the second
  335. * @param $mon the month
  336. * @param $day the day
  337. * @param $year the year
  338. * @param $timezone name
  339. * Use 'UTC' to avoid timezone conversion.
  340. */
  341. function _date_mktime($hr, $min, $sec, $mon = false, $day = false, $year = false, $timezone = false) {
  342. if ($timezone === FALSE) {
  343. $timezone = date_default_timezone_name();
  344. }
  345. /*
  346. # disabled because some people place large values in $sec.
  347. # however we need it for $mon because we use an array...
  348. $hr = intval($hr);
  349. $min = intval($min);
  350. $sec = intval($sec);
  351. */
  352. $mon = intval($mon);
  353. $day = intval($day);
  354. $year = intval($year);
  355. $year = date_year_digit_check($year);
  356. if ($mon > 12) {
  357. $y = floor(($mon-1) / 12);
  358. $year += $y;
  359. $mon -= $y * 12;
  360. }
  361. else if ($mon < 1) {
  362. $y = ceil((1-$mon) / 12);
  363. $year -= $y;
  364. $mon += $y * 12;
  365. }
  366. $_day_power = 86400;
  367. $_hour_power = 3600;
  368. $_min_power = 60;
  369. $_month_table_normal = array("", 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
  370. $_month_table_leap = array("", 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
  371. $_total_date = 0;
  372. if ($year >= 1970) {
  373. $year_in = $year;
  374. for ($a = 1970 ; $a <= $year; $a++) {
  375. $leap = date_is_leap_year($a);
  376. if ($leap == true) {
  377. $loop_table = $_month_table_leap;
  378. $_add_date = 366;
  379. }
  380. else {
  381. $loop_table = $_month_table_normal;
  382. $_add_date = 365;
  383. }
  384. if ($a < $year) {
  385. $_total_date += $_add_date;
  386. }
  387. else {
  388. for ($b=1; $b<$mon; $b++) {
  389. $_total_date += $loop_table[$b];
  390. }
  391. }
  392. }
  393. $_total_date +=$day-1;
  394. $ret = ($_total_date * $_day_power) + ($hr * $_hour_power) + ($min * $_min_power) + $sec;
  395. $ret -= date_get_gmt_diff_ts($ret, $timezone);
  396. }
  397. else {
  398. for ($a = 1969 ; $a >= $year; $a--) {
  399. $leap = date_is_leap_year($a);
  400. if ($leap == true) {
  401. $loop_table = $_month_table_leap;
  402. $_add_date = 366;
  403. }
  404. else {
  405. $loop_table = $_month_table_normal;
  406. $_add_date = 365;
  407. }
  408. if ($a > $year) { $_total_date += $_add_date;
  409. }
  410. else {
  411. for ($b = 12;$b>$mon;$b--) {
  412. $_total_date += $loop_table[$b];
  413. }
  414. }
  415. }
  416. $_total_date += $loop_table[$mon] - $day;
  417. $_day_time = $hr * $_hour_power + $min * $_min_power + $sec;
  418. $_day_time = $_day_power - $_day_time;
  419. $ret = -( $_total_date * $_day_power + $_day_time);
  420. if ($ret < -12220185600) $ret += 10*86400; // if earlier than 5 Oct 1582 - gregorian correction
  421. else if ($ret < -12219321600) $ret = -12219321600; // if in limbo, reset to 15 Oct 1582.
  422. }
  423. return $ret;
  424. }
  425. /**
  426. * @} End of ingroup "adodb".
  427. */