Optimizations and refactoring.
More optimization
Limit size of sending-frames queue.

* Context.MaxSendQueueCount sets the limit of the number of messages that
  can simultaneously be sending frames. (The default of 0 means unlimited.)
* Sender.Send will block if the queue is full.

This not only limits memory usage, it also seems to improve performance a
lot when sending a lot of messages, as it reduces the overhead of
maintaining the queue.