One perk for being in school is that you have the chance to dig very deeply in certain concept for the sake of understanding. I am currently doing some research work on concurrency and I decided to implement a simple producer-consumer problem, just for fun. Then, I decided to dig into this problem until I couldn't go further.

The problem

The producer-consumer problem is a classical concurrency scenario where you have 1 or more producer and 1 to more consumer. A producer produce a good while a consumer consume the good. The concurrent part is the limited space where goods are stored, called the buffer. At some point, a producer will have to wait for a consumer to consume. In reverse, a consumer will have to wait for a producer to produce.

1-to-1 producer-consumer problem

The simple implementation

Multi-threading solutions (those on Wikipedia) are the easier to implement. You will need concurrency control system like semaphores or monitor. There is even a lock-free solution when having a single consumer and producer.

Java semaphores solution on GitHub

What about distributed implementation?

Previous solutions imply implementation in a multi-threading environment. My research is in distributed environment so I decided to implement a simple distributed producer-consumer using a message queue as the buffer.

Basic distributed producer-consumer solution

So basically, distributed solutions will use message passing. Message could be send over network or using any IPC technologies. In this solution, the underlying network layer is the buffer. The producer send (see produce) message to the consumer who then read (see consume) it.

In this solution the communication pattern is R (request). Optionally, the consumer could response to the producer went an item has been consumed. That would bring the communication pattern to RR (request-reply).

This solution could also work using multiple producers. The consumer would be the server and producers are clients. What if I want more consumers?

Java message passing solution on GitHub

The distributed n-to-n producer-consumer with a broker

The biggest challenge with the producer-consumer problem is the buffer. For the distributed n-to-n producer-consumer problem I will need an addition, a broker. The broker will act as the buffer manager.

n-to-n producer-consumer solution

This solution use a RR (request-reply) communication pattern. When a producer send a produced item, it need to wait for the broker confirmation before producing the next one. Same for consumer, if the broker has no item to consume, the consumer will have to wait.

The RR communication pattern also mean this is a synchronous solution. The asynchronous solution would need a RARA (request-answer reply-answer) communication pattern for maximum concurrency level.

If order on consumer or producer is not important, the broker could scale on multiple nodes. A load balancer could then balance consume and produce requests to all brokers. Remember, that the buffer has a limited size and the load balance should respect the buffer size.

Can we got further? Of course!

No broker solution

If you are in a sensor network we may not have the possibility to use a broker. You could solve this problem by using multicast and consensus. A consumer request an item to all producers, producers, using a distributed consensus algorithm, determine who is going to send the item, then the selected one reply to the consumer. When the buffer is distributed to all producers, we need a production consensus to ensure that the buffer limit is not broken.

Ordered solution

Ordering stuff in a distributed environment is always a huge problem. If we use a broker, produced item could be ordered when received by the broker. If we need to order them by the time it was produced on producer, then we will need a central clock. If we can’t have a distributed clock, we could use a logical clock coupled with a distributed mutex so that only one producer can produce at the time.

No broker, ordered producer and consumer

All in. From this point, it get complex and fast. I am not even sure that we can still say a producer-consumer problem.

Can we still go further? I am pretty sure, but I will stop here, by head hurt. Do we need all of this in real life, yes. You can easily find example in video game.

So, that the end for today, but, what about the dining philosopher?

GitHub