class SequentialSubscription implements Subscription, Cancellable {

    @Override
    public void request(long n) {
        final long currRequested;
        if (isRequestNValid(n)) {
            currRequested = requestedUpdater.accumulateAndGet(this, n,
                    FlowControlUtils::addWithOverflowProtectionIfNotNegative);
        } else {
            currRequested = sanitizeInvalidRequestN(n);
            requested = currRequested;
        }

        for (;;) {
            final long currSourceRequested = sourceRequested;
            if (currSourceRequested == CANCELLED) {
                break;
            } else if (currSourceRequested < 0) {
                assert currSourceRequested == SWITCHING || currSourceRequested == REQUESTED;
                if (sourceRequestedUpdater.compareAndSet(this, currSourceRequested, REQUESTED)) {
                    break;
                }
            } else {
                // We must read the subscription BEFORE the CAS (which involves a read barrier). This ensures if the
                // sourceRequested value is visible then the subscription (which may have been switched by
                // another thread) is also visible.
                final Subscription currSubscription = subscription;
                if (isRequestNValid(currRequested)) {
                    // sourceRequested ...[delta]... requested
                    final long delta = currRequested - currSourceRequested;
                    if (sourceRequestedUpdater.compareAndSet(this, currSourceRequested, currSourceRequested + delta)) {
                        // sourceRequested is either monotonically increasing, or set to an invalid value
                        // (e.g. negative) if a Subscription switch is on going and atomically set to requestN to
                        // preserve the monotonic increasing property. If the CAS worked that means the value of
                        // subscription before will be visible if there was previously a switch. We also know there is
                        // no concurrent interaction on the subscription because currSourceRequested is known not to be
                        // SWITCHING, and the value would have increased.
                        if (delta != 0) {
                            currSubscription.request(delta);
                        }
                        break;
                    }
                } else if (sourceRequestedUpdater.compareAndSet(this, currSourceRequested, CANCELLED)) {
                    currSubscription.request(currRequested);
                    break;
                }
            }
        }
    }

      SequentialSubscription();
      SequentialSubscription(Subscription delegate);

}