class DefaultVersionService implements VersionService {

  @Override
  public HybridLogicalTimestamp nextVersion() {

    final long physicalNow = this.clock.timestampMicros();

    if (localTime.get() >= physicalNow) {
      //physical clock hasn't moved forward relative to local, keep the logicalTime, bump counter
      localCounter.incrementAndGet();
      traceBackwardDrift(physicalNow, localTime.get());
    } else {
      // the physical clock is ahead

      /*
       a hack to handle the 2051 problem; if our system clock is "too" far ahead of our local
       logicalTime then all future versions get dragged forward to keep up with it and we have
       to wait for "reality" to catch up with that logicalTime to reset things.

       todo: this misses the case where the clock is borked on construction;
       in the ctor we set the initial local to the physical clock, so this only catches drift
       when updating the local. it also needs some thought such that if multiple nodes are stuck
       on fwd/back physical times and just bumping counters they don't clash.
        */
      if (physicalNowTooFarAhead(physicalNow, localTime)) {
        localCounter.incrementAndGet();
        traceForwardDrift(physicalNow, localTime.get());
      } else {
        // things look sane, take the physical logicalTime and reset the counter
        localTime.set(physicalNow);
        localCounter.set(INITIAL_COUNTER);
      }
    }

    return new HybridLogicalTimestamp(localTime.get(), localCounter.get());
  }

    DefaultVersionService(Clock clock);
    DefaultVersionService();

}