summaryrefslogtreecommitdiffstats
path: root/src/corelib/io/qiodevice_p.h
diff options
context:
space:
mode:
authorAlex Trotsenko <alex1973tr@gmail.com>2015-04-24 19:02:02 +0300
committerAlex Trotsenko <alex1973tr@gmail.com>2016-01-27 06:32:30 +0000
commit1c0494e63b2750bc4de61ff6f3f07f2d3cab2dbd (patch)
treef0c83d153e17a29f682fc7372fdfc3b9acc160ea /src/corelib/io/qiodevice_p.h
parentacbd79996d7dedd65cda98bd1b0f15690f0271e4 (diff)
QIODevice: add infrastructure for multistreaming
Some sequential devices allow data to be partitioned into several channels that have the property of independently sequenced delivery. Supporting such devices uniformly requires a unified API which provides the user with a uniform concept of multistreaming. This patch is based on QProcess's multiplexing model and introduces the following features: - ability to get the number of channels; - multiple internal read/write buffers; - channel selection functions; - notification signals on channel activity. To keep the source code compatible with single-channel implementations, introduce a private class that references the current read buffer and hides multistreaming internals from the user. Bump the TypeInformationVersion field in qtHookData, to notify the Qt Creator developers that the offset of QFilePrivate::fileName was changed and dumpers should be adapted. [ChangeLog][QtCore] Added multistreaming to QIODevice. Change-Id: Idcaa6a618927c101c4c7284d2a633913be6a6ee2 Reviewed-by: Allan Sandfeld Jensen <allan.jensen@theqtcompany.com> Reviewed-by: Oswald Buddenhagen <oswald.buddenhagen@theqtcompany.com>
Diffstat (limited to 'src/corelib/io/qiodevice_p.h')
-rw-r--r--src/corelib/io/qiodevice_p.h55
1 files changed, 54 insertions, 1 deletions
diff --git a/src/corelib/io/qiodevice_p.h b/src/corelib/io/qiodevice_p.h
index b84190e6e5..1bb569532b 100644
--- a/src/corelib/io/qiodevice_p.h
+++ b/src/corelib/io/qiodevice_p.h
@@ -56,6 +56,7 @@
#include "QtCore/qobjectdefs.h"
#include "QtCore/qstring.h"
#include "private/qringbuffer_p.h"
+#include "QtCore/qvector.h"
#ifndef QT_NO_QOBJECT
#include "private/qobject_p.h"
#endif
@@ -82,9 +83,48 @@ public:
QIODevice::OpenMode openMode;
QString errorString;
- QRingBuffer buffer;
+ QVector<QRingBuffer> readBuffers;
+ QVector<QRingBuffer> writeBuffers;
+
+ class QRingBufferRef {
+ QRingBuffer *m_buf;
+ inline QRingBufferRef() : m_buf(Q_NULLPTR) { }
+ friend class QIODevicePrivate;
+ public:
+ // wrap functions from QRingBuffer
+ inline qint64 nextDataBlockSize() const { return (m_buf ? m_buf->nextDataBlockSize() : Q_INT64_C(0)); }
+ inline const char *readPointer() const { return (m_buf ? m_buf->readPointer() : Q_NULLPTR); }
+ inline const char *readPointerAtPosition(qint64 pos, qint64 &length) const { Q_ASSERT(m_buf); return m_buf->readPointerAtPosition(pos, length); }
+ inline void free(qint64 bytes) { Q_ASSERT(m_buf); m_buf->free(bytes); }
+ inline char *reserve(qint64 bytes) { Q_ASSERT(m_buf); return m_buf->reserve(bytes); }
+ inline char *reserveFront(qint64 bytes) { Q_ASSERT(m_buf); return m_buf->reserveFront(bytes); }
+ inline void truncate(qint64 pos) { Q_ASSERT(m_buf); m_buf->truncate(pos); }
+ inline void chop(qint64 bytes) { Q_ASSERT(m_buf); m_buf->chop(bytes); }
+ inline bool isEmpty() const { return !m_buf || m_buf->isEmpty(); }
+ inline int getChar() { return (m_buf ? m_buf->getChar() : -1); }
+ inline void putChar(char c) { Q_ASSERT(m_buf); m_buf->putChar(c); }
+ inline void ungetChar(char c) { Q_ASSERT(m_buf); m_buf->ungetChar(c); }
+ inline qint64 size() const { return (m_buf ? m_buf->size() : Q_INT64_C(0)); }
+ inline void clear() { if (m_buf) m_buf->clear(); }
+ inline qint64 indexOf(char c) const { return (m_buf ? m_buf->indexOf(c, m_buf->size()) : Q_INT64_C(-1)); }
+ inline qint64 indexOf(char c, qint64 maxLength, qint64 pos = 0) const { return (m_buf ? m_buf->indexOf(c, maxLength, pos) : Q_INT64_C(-1)); }
+ inline qint64 read(char *data, qint64 maxLength) { return (m_buf ? m_buf->read(data, maxLength) : Q_INT64_C(0)); }
+ inline QByteArray read() { return (m_buf ? m_buf->read() : QByteArray()); }
+ inline qint64 peek(char *data, qint64 maxLength, qint64 pos = 0) const { return (m_buf ? m_buf->peek(data, maxLength, pos) : Q_INT64_C(0)); }
+ inline void append(const QByteArray &qba) { Q_ASSERT(m_buf); m_buf->append(qba); }
+ inline qint64 skip(qint64 length) { return (m_buf ? m_buf->skip(length) : Q_INT64_C(0)); }
+ inline qint64 readLine(char *data, qint64 maxLength) { return (m_buf ? m_buf->readLine(data, maxLength) : Q_INT64_C(-1)); }
+ inline bool canReadLine() const { return m_buf && m_buf->canReadLine(); }
+ };
+
+ QRingBufferRef buffer;
+ QRingBufferRef writeBuffer;
qint64 pos;
qint64 devicePos;
+ int readChannelCount;
+ int writeChannelCount;
+ int currentReadChannel;
+ int currentWriteChannel;
qint64 transactionPos;
bool transactionStarted;
bool baseReadLineDataCalled;
@@ -111,6 +151,19 @@ public:
}
void seekBuffer(qint64 newPos);
+ inline void setCurrentReadChannel(int channel)
+ {
+ buffer.m_buf = (channel < readBuffers.size() ? &readBuffers[channel] : nullptr);
+ currentReadChannel = channel;
+ }
+ inline void setCurrentWriteChannel(int channel)
+ {
+ writeBuffer.m_buf = (channel < writeBuffers.size() ? &writeBuffers[channel] : nullptr);
+ currentWriteChannel = channel;
+ }
+ void setReadChannelCount(int count);
+ void setWriteChannelCount(int count);
+
virtual qint64 peek(char *data, qint64 maxSize);
virtual QByteArray peek(qint64 maxSize);