mirror of https://github.com/qt/qtgrpc.git
170 lines
4.9 KiB
C++
170 lines
4.9 KiB
C++
// Copyright (C) 2022 The Qt Company Ltd.
|
|
// Copyright (C) 2019 Alexey Edelev <semlanik@gmail.com>
|
|
// SPDX-License-Identifier: LicenseRef-Qt-Commercial
|
|
|
|
#ifndef QPROTOBUFSELFCHECKITERATOR_H
|
|
#define QPROTOBUFSELFCHECKITERATOR_H
|
|
|
|
#include <QtProtobuf/qtprotobufglobal.h>
|
|
#include <QtCore/qnumeric.h>
|
|
|
|
#include <QtCore/QByteArray>
|
|
|
|
#include <iterator>
|
|
|
|
QT_BEGIN_NAMESPACE
|
|
|
|
namespace QtProtobufPrivate {
|
|
class QProtobufSelfcheckIterator
|
|
{
|
|
public:
|
|
using difference_type = QByteArray::difference_type;
|
|
using iterator_category = std::random_access_iterator_tag;
|
|
using value_type = QByteArray::value_type;
|
|
using pointer = QByteArray::pointer;
|
|
using reference = QByteArray::reference;
|
|
|
|
static QProtobufSelfcheckIterator fromView(QByteArrayView container)
|
|
{
|
|
QProtobufSelfcheckIterator iter(container);
|
|
return iter;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator(const QProtobufSelfcheckIterator &other) = default;
|
|
QProtobufSelfcheckIterator &operator=(const QProtobufSelfcheckIterator &other) = default;
|
|
|
|
explicit operator QByteArray::const_iterator &() { return m_it; }
|
|
explicit operator QByteArray::const_iterator() const { return m_it; }
|
|
|
|
char operator*()
|
|
{
|
|
Q_ASSERT(isValid());
|
|
return *m_it;
|
|
}
|
|
|
|
bool isValid() const noexcept { return m_containerBegin <= m_it && m_it <= m_containerEnd; }
|
|
|
|
QProtobufSelfcheckIterator &operator++() noexcept
|
|
{
|
|
if (!isValid()) {
|
|
qWarning("Deserialization failed: Unexpected end of data.");
|
|
return *this;
|
|
}
|
|
++m_it;
|
|
return *this;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator operator++(int) noexcept
|
|
{
|
|
QProtobufSelfcheckIterator old(*this);
|
|
operator++();
|
|
return old;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator &operator--() noexcept
|
|
{
|
|
if (!isValid()) {
|
|
qWarning("Deserialization failed: Unexpected end of data.");
|
|
return *this;
|
|
}
|
|
|
|
--m_it;
|
|
return *this;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator operator--(int) noexcept
|
|
{
|
|
QProtobufSelfcheckIterator old(*this);
|
|
operator--();
|
|
return old;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator &operator+=(qsizetype count) noexcept
|
|
{
|
|
if (!isValid()) {
|
|
qWarning("Deserialization failed: Unexpected end of data.");
|
|
return *this;
|
|
}
|
|
m_it += count;
|
|
return *this;
|
|
}
|
|
|
|
QProtobufSelfcheckIterator &operator-=(qsizetype count) noexcept
|
|
{
|
|
if (!isValid()) {
|
|
qWarning("Deserialization failed: Unexpected end of data.");
|
|
return *this;
|
|
}
|
|
m_it -= count;
|
|
return *this;
|
|
}
|
|
|
|
const char *data() const { return m_it; }
|
|
qsizetype bytesLeft() const { return isValid() ? std::distance(m_it, m_containerEnd) : 0; }
|
|
|
|
private:
|
|
explicit QProtobufSelfcheckIterator(QByteArrayView container)
|
|
: m_containerBegin(container.begin()),
|
|
m_containerEnd(container.end()),
|
|
m_it(container.begin())
|
|
{
|
|
}
|
|
|
|
friend bool operator==(const QProtobufSelfcheckIterator &lhs,
|
|
const QProtobufSelfcheckIterator &rhs) noexcept
|
|
{
|
|
Q_ASSERT(lhs.m_containerBegin == rhs.m_containerBegin);
|
|
Q_ASSERT(lhs.m_containerEnd == rhs.m_containerEnd);
|
|
return lhs.m_it == rhs.m_it;
|
|
}
|
|
friend bool operator!=(const QProtobufSelfcheckIterator &lhs,
|
|
const QProtobufSelfcheckIterator &rhs) noexcept
|
|
{
|
|
Q_ASSERT(lhs.m_containerBegin == rhs.m_containerBegin);
|
|
Q_ASSERT(lhs.m_containerEnd == rhs.m_containerEnd);
|
|
return lhs.m_it != rhs.m_it;
|
|
}
|
|
friend bool operator==(const QProtobufSelfcheckIterator &lhs,
|
|
const QByteArray::const_iterator &other) noexcept
|
|
{
|
|
Q_ASSERT(lhs.m_containerBegin <= other && other <= lhs.m_containerEnd);
|
|
return lhs.m_it == other;
|
|
}
|
|
friend bool operator!=(const QProtobufSelfcheckIterator &lhs,
|
|
const QByteArray::const_iterator &other) noexcept
|
|
{
|
|
Q_ASSERT(lhs.m_containerBegin <= other && other <= lhs.m_containerEnd);
|
|
return lhs.m_it != other;
|
|
}
|
|
|
|
friend qint64 operator-(const QProtobufSelfcheckIterator &lhs,
|
|
const QProtobufSelfcheckIterator &rhs) noexcept
|
|
{
|
|
Q_ASSERT(lhs.m_containerBegin == rhs.m_containerBegin);
|
|
return lhs.m_it - rhs.m_it;
|
|
}
|
|
|
|
QByteArrayView::const_iterator m_containerBegin;
|
|
QByteArrayView::const_iterator m_containerEnd;
|
|
QByteArrayView::const_iterator m_it;
|
|
};
|
|
|
|
inline QProtobufSelfcheckIterator operator+(const QProtobufSelfcheckIterator &it, qsizetype length)
|
|
{
|
|
QProtobufSelfcheckIterator copy = it;
|
|
copy += length;
|
|
return copy;
|
|
}
|
|
|
|
inline QProtobufSelfcheckIterator operator-(const QProtobufSelfcheckIterator &it, qsizetype length)
|
|
{
|
|
QProtobufSelfcheckIterator copy = it;
|
|
copy -= length;
|
|
return copy;
|
|
}
|
|
} // namespace QtProtobufPrivate
|
|
|
|
QT_END_NAMESPACE
|
|
|
|
#endif // QPROTOBUFSELFCHECKITERATOR_H
|