public void sendCall(final Call call) throws IOException {
      if (callsToWrite.size() >= maxQueueSize) {
        throw new IOException("Can't add " + call.toShortString()
          + " to the write queue. callsToWrite.size()=" + callsToWrite.size());
      }
      callsToWrite.offer(call);
      BlockingRpcConnection.this.notifyAll();
    }
If the client wants to interrupt its calls easily (i.e. call Thread#interrupt), it gets into a
java issue: an interruption during a write closes the socket/channel. A way to avoid this is to
use a different thread for writing. This way, on interruptions, we either cancel the writes or
ignore the answer if the write is already done, but we don't stop the write in the middle. This
adds a thread per region server in the client, so it's kept as an option.
<p>
The implementation is simple: the client threads adds their call to the queue, and then wait
for an answer. The CallSender blocks on the queue, and writes the calls one after the other. On
interruption, the client cancels its call. The CallSender checks that the call has not been
canceled before writing it.
</p>
When the connection closes, all the calls not yet sent are dismissed. The client thread is
notified with an appropriate exception, as if the call was already sent but the answer not yet
received.
</p>
hbase-client/src/main/java/org/apache/hadoop/hbase/ipc/BlockingRpcConnection.java