Skip to content

Commit ac65e2a

Browse files
committed
More unique uniqid (no BC)
1 parent 7b3e68f commit ac65e2a

File tree

1 file changed

+23
-11
lines changed

1 file changed

+23
-11
lines changed

ext/standard/uniqid.c

Lines changed: 23 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -53,20 +53,32 @@ PHP_FUNCTION(uniqid)
5353
Z_PARAM_BOOL(more_entropy)
5454
ZEND_PARSE_PARAMETERS_END();
5555

56-
/* This implementation needs current microsecond to change,
57-
* hence we poll time until it does. This is much faster than
58-
* calling usleep(1) which may cause the kernel to schedule
59-
* another process, causing a pause of around 10ms.
56+
/* This implementation needs current microsecond to change.
57+
* We will manually move the time forward if needed. This is
58+
* more stable as polling or sleeping as it will not be
59+
* effected by time changes (like ntp) and this is much faster
60+
* than calling usleep(1) which may cause the kernel to
61+
* schedule another process, causing a pause of around 10ms.
6062
*/
61-
do {
62-
(void)gettimeofday((struct timeval *) &tv, (struct timezone *) NULL);
63-
} while (tv.tv_sec == prev_tv.tv_sec && tv.tv_usec == prev_tv.tv_usec);
63+
(void)gettimeofday((struct timeval *) &tv, (struct timezone *) NULL);
64+
if (UNEXPECTED((tv.tv_sec == prev_tv.tv_sec && tv.tv_usec <= prev_tv.tv_usec)
65+
|| tv.tv_sec < prev_tv.tv_sec
66+
)) {
67+
prev_tv.tv_usec += 1;
68+
if (UNEXPECTED(prev_tv.tv_usec > 999999)) {
69+
prev_tv.tv_sec += prev_tv.tv_usec / 1000000;
70+
prev_tv.tv_usec = prev_tv.tv_usec % 1000000;
71+
}
6472

65-
prev_tv.tv_sec = tv.tv_sec;
66-
prev_tv.tv_usec = tv.tv_usec;
73+
sec = (int) prev_tv.tv_sec;
74+
usec = (int) prev_tv.tv_usec;
75+
} else {
76+
prev_tv.tv_sec = tv.tv_sec;
77+
prev_tv.tv_usec = tv.tv_usec;
6778

68-
sec = (int) tv.tv_sec;
69-
usec = (int) (tv.tv_usec % 0x100000);
79+
sec = (int) tv.tv_sec;
80+
usec = (int) (tv.tv_usec % 0x100000);
81+
}
7082

7183
/* The max value usec can have is 0xF423F, so we use only five hex
7284
* digits for usecs.

0 commit comments

Comments
 (0)