Ring buffer, implemented with a circular array. Designed for multiple producers (add()) and a single consumer (remove()).
Note that the remove() methods are not reentrant, so multiple consumers won't work correctly ! The buffer has a fixed capacity, and a low (LOW), highest delivered (HD) and highest received (HR) seqno.
An element with a sequence number (seqno) > low + capacity or < HD will get discarded.
Elements are added after HD, but cannot wrap around beyond LOW. Addition doesn't need to be sequential, e.g. adding 5, 6, 8 is OK (as long as a seqno doesn't pass LOW). Addition may advance HR. Addition of elements that are already present is a no-op, and will not set the element again.
Removal of elements starts at HD+1; any non-null element is removed and HD is advanced accordingly. If a remove method is called with nullify=true, then removed elements are nulled and LOW is advanced as well (LOW=HD). Note that
all removals in a given RingBuffer must either have nullify=true, or all must be false. It is not permitted to do some removals with nullify=true, and others with nullify=false, in the same RingBuffer.
The {@link #stable(long)} method is called periodically; it nulls all elements between LOW and HD and advances LOWto HD.
The design of RingBuffer is discussed in doc/design/RingBuffer.txt.
@author Bela Ban
@since 3.1