@@ -429,7 +429,7 @@ protected function getSequentialPerNodeIDs( $bucket, $bits, $count ) {
429429 /**
430430 * Get a (time,counter,clock sequence) where (time,counter) is higher
431431 * than any previous (time,counter) value for the given clock sequence.
432- * This is useful for making UIDs sequential on a per-node bases .
432+ * This is useful for making UIDs sequential on a per-node basis .
433433 *
434434 * @param string $lockFile Name of a local lock file
435435 * @param int $clockSeqSize The number of possible clock sequence values
@@ -490,7 +490,7 @@ protected function getTimeAndDelay( $lockFile, $clockSeqSize, $counterSize, $off
490490 // - For any drift above 10ms, we pretend that the clock went backwards, and treat
491491 // it the same way as after an NTP sync, by incrementing clock sequence instead.
492492 // Given the sequence rolls over automatically, and silently, and is meant to be
493- // rare, this is essentially sacrifices a reasonable guarantee of uniqueness.
493+ // rare, this essentially sacrifices a reasonable guarantee of uniqueness.
494494 // - For long running processes (e.g. longer than a few seconds) the drift can
495495 // easily be more than 2 seconds. Because we only have a single lock file
496496 // and don't want to keep too many counters and deal with clearing those,
@@ -513,33 +513,31 @@ protected function getTimeAndDelay( $lockFile, $clockSeqSize, $counterSize, $off
513513 // The UID lock file was already initialized
514514 $ clkSeq = (int )$ data [0 ] % $ clockSeqSize ;
515515 $ prevSec = (int )$ data [1 ];
516- // Counter for UIDs with the same timestamp,
517- $ msecCounter = 0 ;
516+ $ prevMsecCounter = (int )$ data [2 ] % $ msecCounterSize ;
518517 $ randOffset = (int )$ data [3 ] % $ counterSize ;
519-
520- // If the system clock moved backwards by an NTP sync,
521- // or if the last writer process had its clock drift ahead,
522- // Try to catch up if the gap is small, so that we can keep a single
523- // monotonic logic file.
518+ // If the system clock moved back or inter-process clock drift caused the last
519+ // writer process to record a higher time than the current process time, then
520+ // briefly wait for the current process clock to catch up.
524521 $ sec = $ this ->timeWaitUntil ( $ prevSec );
525522 if ( $ sec === false ) {
526- // Gap is too big. Looks like the clock got moved back significantly.
527- // Start a new clock sequence, and re-randomize the extra offset,
528- // which is useful for UIDs that do not include the clock sequence number.
523+ // There was too much clock drift to wait. Bump the clock sequence number to
524+ // avoid collisions between new and already-generated IDs with the same time.
529525 $ clkSeq = ( $ clkSeq + 1 ) % $ clockSeqSize ;
530526 $ sec = time ();
527+ $ msecCounter = 0 ;
531528 $ randOffset = mt_rand ( 0 , $ offsetSize - 1 );
532529 trigger_error ( "Clock was set back; sequence number incremented. " );
533530 } elseif ( $ sec === $ prevSec ) {
534- // Double check, only keep remainder if a previous writer wrote
535- // something here that we don't accept.
536- $ msecCounter = (int )$ data [2 ] % $ msecCounterSize ;
537- // Bump the counter if the time has not changed yet
538- if ( ++$ msecCounter >= $ msecCounterSize ) {
531+ // The time matches the last ID. Bump the tie-breaking counter.
532+ $ msecCounter = $ prevMsecCounter + 1 ;
533+ if ( $ msecCounter >= $ msecCounterSize ) {
539534 // More IDs generated with the same time than counterSize can accommodate
540535 flock ( $ handle , LOCK_UN );
541536 throw new RuntimeException ( "Counter overflow for timestamp value. " );
542537 }
538+ } else {
539+ // The time is higher than the last ID. Reset the tie-breaking counter.
540+ $ msecCounter = 0 ;
543541 }
544542 } else {
545543 // Initialize UID lock file information
0 commit comments