php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #73837 "new DateTime()" sometimes returns 1 second ago value on PHP 7.1.0
Submitted: 2016-12-29 19:25 UTC Modified: 2017-01-01 12:29 UTC
Votes:1
Avg. Score:4.0 ± 0.0
Reproduced:1 of 1 (100.0%)
Same Version:1 (100.0%)
Same OS:0 (0.0%)
From: for-bugs at hnw dot jp Assigned: derick (profile)
Status: Closed Package: Date/time related
PHP Version: 7.1.0 OS: macOS
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: for-bugs at hnw dot jp
New email:
PHP Version: OS:

 

 [2016-12-29 19:25 UTC] for-bugs at hnw dot jp
Description:
------------
From PHP 7.1, DateTime constructor fills microseconds. However, setting seconds and setting microseconds are in different function, so sometimes DateTime instance has 1 second ago value from actual time.

Test script:
---------------
<?php
$prev_dt = new DateTime();
while (true) {
    $dt = new DateTime();
    if ($prev_dt > $dt) {
        var_dump($prev_dt->format("Y-m-d H:i:s.u"));
        var_dump($dt->format("Y-m-d H:i:s.u"));
        break;
    }
    $prev_dt = $dt;
}


Expected result:
----------------
infinite loop

Actual result:
--------------
soon ends and outputs like this:

string(26) "2016-12-29 18:35:54.999998"
string(26) "2016-12-29 18:35:54.000000"

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2016-12-29 19:43 UTC] requinix@php.net
-Status: Open +Status: Verified -Assigned To: +Assigned To: derick
 [2016-12-29 19:43 UTC] requinix@php.net
Same on Windows.

Looks like the problem is in timelib.
 [2017-01-01 12:29 UTC] derick@php.net
-Status: Verified +Status: Assigned
 [2017-01-01 12:29 UTC] derick@php.net
That's curious... will investigate.
 [2017-01-10 12:28 UTC] for-bug at hnw dot jp
There's nothing curious. The current code uses different time-source against seconds and microseconds for the current time. They should be unified.

In php_date_initialize(), timelib_unixtime2local() is called with time(NULL) as 2nd argument. In this function, unixtime is set to "now". Then php_date_set_current_time_fraction() is executed and the value from gettimeofday() is set as microsecond of "now".

Suppose the accurate time is "2016-12-29 18:35:54.999999+00:00" when time(NULL) is called. Then time(NULL) returns 1483036554. 1 microsecond after, gettimeofday() is called and returns {1483036555, 0}. Then the value of "now" gets "148303654.000000" (Of course, it should be "1483036554.999999" or "1483036555.000000").
 [2017-02-11 11:10 UTC] derick@php.net
Automatic comment on behalf of github@derickrethans.nl
Revision: http://git.php.net/?p=php-src.git;a=commit;h=5113909259f897c9c69f23cf5f8f7ab8972d5eba
Log: Fixed bug #73837 (&quot;new DateTime()&quot; sometimes returns 1 second ago value).
 [2017-02-11 11:10 UTC] derick@php.net
-Status: Assigned +Status: Closed
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Nov 21 15:01:30 2024 UTC