
Disruptor: High performance alternative to bounded queues (2011) [pdf] - cjg
http://lmax-exchange.github.io/disruptor/files/Disruptor-1.0.pdf
======
lomnakkus
See also Aeron[1] which is basically a networked superset of the Disruptor,
featuring (IIRC) a just-as-fast machine-local implementation. Made by some of
the same people as the LMAX Disruptor. It's not _quite_ ready for general use
AFAICT, but it's quickly getting there...

There's also a really informative presentation[2] by Martin Thompson on some
of the ideas that they're using to get really low latency and high throughput.

[1] [https://github.com/real-logic/Aeron](https://github.com/real-logic/Aeron)

[2] [https://www.infoq.com/presentations/aeron-
messaging](https://www.infoq.com/presentations/aeron-messaging)

~~~
lomnakkus
Actually, I thought this might be of sufficient general interest that I
submitted it as a story:
[https://news.ycombinator.com/item?id=12059565](https://news.ycombinator.com/item?id=12059565)

(Not really sure about how the whole submit-a-thing works around here, so I
just thought I'd mention it.)

------
vog
I really don't want to put this down. This looks very interesting and is
nicely presented. But I have trouble recognizing the main idea(s) behind the
"LMAX Disruptor". To me, this all boils down to:

"You get better performance if you implement your event queue via a pre-
allocated ring buffer instead of (dynamically allocated) linked-lists or
arrays."

Is it really just that? If so, this is nothing new, but quite common in game
programming and related fields. For example, see:
[https://fgiesen.wordpress.com/2010/12/14/ring-buffers-and-
qu...](https://fgiesen.wordpress.com/2010/12/14/ring-buffers-and-queues/)

What am I missing?

~~~
shahbazac
Its been many years since I saw the presentation but I believe they made a
point of mentioning that ring buffers are not a new technology. They mentioned
how such data structures are used all the time in network devices, such as
switches.

The disruptor is an actual library based on ring buffers (other have already
pointed out some other features).

In practical terms, this library has been immensely popular. Within a couple
years of disruptor's release, practically every (java based) trading firm was
using them. I've even seen c++ implementations, only vaguely resembling this
library, being referred to as 'disruptors.'

Beyond the library, the original (and subsequent) presentations by the authors
popularized the concepts of "mechanical sympathy" (understand the abstraction
layer beneath what you are currently working in) and introduced a whole new
set of developers to modern CPUs, thinking about cache lines, etc.

~~~
delibes
You might want to also see Martin Thompson's old blog called Mechanical
Sympathy, and in particular his post on 'false sharing'

[http://mechanical-sympathy.blogspot.co.uk/2011/07/false-
shar...](http://mechanical-sympathy.blogspot.co.uk/2011/07/false-sharing.html)

------
eelan
That is an old presentation. The most up to date info can be found at
[https://github.com/LMAX-
Exchange/disruptor/wiki/Introduction](https://github.com/LMAX-
Exchange/disruptor/wiki/Introduction)

------
danbruc
ArrayBlockingQueue [1] uses a ring buffer backed by a fixed-size array, too.
It is really hard to say where the speed-up comes from without seeing the
code, but it is certainly not from using a ring buffer because both of the
compared implementations do so. I guess they just were more careful when they
designed the auxiliary state and the operation on it, for example
ArrayBlockingQueue explicitly tracks the number of elements in the queue with
a separate field - instead of deriving it from the insert and remove pointers
- and therefore this field is contented by readers and writers. Also
preallocating entries for all slots to work around Java's lack of support for
arrays of value types certainly removes some overhead from the allocator.

EDIT: Just realized that the code is on GitHub - will have a look.

[1]
[http://grepcode.com/file/repository.grepcode.com/java/root/j...](http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/util/concurrent/ArrayBlockingQueue.java)

~~~
delibes
ArrayBlockingQueue is compared in the performance test results

[https://github.com/LMAX-
Exchange/disruptor/wiki/Performance-...](https://github.com/LMAX-
Exchange/disruptor/wiki/Performance-Results)

~~~
danbruc
That is why I mentioned it in the first place. The paper reads very much like
they think using a ring buffer provides a performance advantage over other
queue implementations but then they compare two implementations using ring
buffers. So their improved performance stems definitely not from using a ring
buffer but from implementations details like the synchronization mechanisms
used or preallocating and reusing queue entries.

------
lmb
There is a podcast at [1] where the author of the disruptor is interviewed.

1: [http://www.se-radio.net/2016/04/se-radio-episode-254-mike-
ba...](http://www.se-radio.net/2016/04/se-radio-episode-254-mike-barker-on-
the-lmax-architecture/)

------
dintech
Also take a look at:

[http://chronicle.software/products/chronicle-
queue/](http://chronicle.software/products/chronicle-queue/)

------
irishjohnnie
It's been a while, but didn't the performance turn out to be similar to other
data structures in multi-socket scenarios because it requires interlocked
-type instructions?

