Some additional comments for DatagramSequencer.

This commit is contained in:
Andrzej Kapolka 2014-06-18 14:44:11 -07:00
parent 530852a756
commit 6ec562931f

View file

@ -23,18 +23,50 @@
class ReliableChannel;
/// Performs simple datagram sequencing, packet fragmentation and reassembly.
/// Performs datagram sequencing, packet fragmentation and reassembly. Works with Bitstream to provide methods to send and
/// receive data over UDP with varying reliability and latency characteristics. To use, create a DatagramSequencer with the
/// fixed-size header that will be included with all outgoing datagrams and expected in all incoming ones (the contents of the
/// header are not checked on receive, only skipped over, and may be modified by the party that actually send the
/// datagram--this means that the header may include dynamically generated data, as long as its size remains fixed). Connect
/// the readyToWrite signal to a slot that will actually transmit the datagram to the remote party. When a datagram is
/// received from that party, call receivedDatagram with its contents.
///
/// A "packet" represents a batch of data sent at one time (split into one or more datagrams sized below the MTU). Packets are
/// received in full and in order or not at all (that is, a packet being assembled is dropped as soon as a fragment from the
/// next packet is received). Packets can be any size, but the larger a packet is, the more likely it is to be dropped--so,
/// it's better to keep packet sizes close to the MTU. To write a packet, call startPacket, write data to the returned
/// Bitstream, then call endPacket (which will result in one or more firings of readyToWrite). Data written in this way is not
/// guaranteed to be received, but if it is received, it will arrive in order. This is a good way to transmit delta state:
/// state that represents the change between the last acknowledged state and the current state (which, if not received, will
/// not be resent as-is; instead, it will be replaced by up-to-date new deltas).
///
/// There are two methods for sending reliable data. The first, for small messages that require minimum-latency processing, is
/// the high priority messaging system. When you call sendHighPriorityMessage, the message that you send will be included with
/// every outgoing packet until it is acknowledged. When the receiving party first sees the message, it will fire a
/// receivedHighPriorityMessage signal.
///
/// The second method employs a set of independent reliable channels multiplexed onto the packet stream. These channels are
/// created lazily through the getReliableOutputChannel/getReliableInputChannel functions. Output channels contain buffers
/// to which one may write either arbitrary data (as a QIODevice) or messages (as QVariants), or switch between the two.
/// Each time a packet is sent, data pending for reliable output channels is added, in proportion to their relative priorities,
/// until the packet size limit set by setMaxPacketSize is reached. On the receive side, the streams are reconstructed and
/// (again, depending on whether messages are enabled) either the QIODevice reports that data is available, or, when a complete
/// message is decoded, the receivedMessage signal is fired.
class DatagramSequencer : public QObject {
Q_OBJECT
public:
/// Contains the content of a high-priority message along with the number of the first packet in which it was sent.
class HighPriorityMessage {
public:
QVariant data;
int firstPacketNumber;
};
/// Creates a new datagram sequencer.
/// \param datagramHeader the content of the header that will be prepended to each outgoing datagram and whose length
/// will be skipped over in each incoming datagram
DatagramSequencer(const QByteArray& datagramHeader = QByteArray(), QObject* parent = NULL);
/// Returns a reference to the weak hash mapping remote ids to shared objects.
@ -267,15 +299,24 @@ class ReliableChannel : public QObject {
public:
/// Returns the channel's index in the sequencer's channel map.
int getIndex() const { return _index; }
/// Returns a reference to the buffer used to write/read data to/from this channel.
CircularBuffer& getBuffer() { return _buffer; }
/// Returns a reference to the data stream created on this channel's buffer.
QDataStream& getDataStream() { return _dataStream; }
/// Returns a reference to the bitstream created on this channel's data stream.
Bitstream& getBitstream() { return _bitstream; }
/// Sets the channel priority, which determines how much of this channel's data (in proportion to the other channels) to
/// include in each outgoing packet.
void setPriority(float priority) { _priority = priority; }
float getPriority() const { return _priority; }
/// Returns the number of bytes available to read from this channel.
int getBytesAvailable() const;
/// Sets whether we expect to write/read framed messages.
@ -287,6 +328,7 @@ public:
signals:
/// Fired when a framed message has been received on this channel.
void receivedMessage(const QVariant& message);
private slots: