1//
2// TextBufferIterator.cpp
3//
4// Library: Foundation
5// Package: Text
6// Module: TextBufferIterator
7//
8// Copyright (c) 2010, Applied Informatics Software Engineering GmbH.
9// and Contributors.
10//
11// SPDX-License-Identifier: BSL-1.0
12//
13
14
15#include "Poco/TextBufferIterator.h"
16#include "Poco/TextEncoding.h"
17#include <algorithm>
18#include <cstring>
19
20
21namespace Poco {
22
23
24TextBufferIterator::TextBufferIterator():
25 _pEncoding(0),
26 _it(0),
27 _end(0)
28{
29}
30
31
32TextBufferIterator::TextBufferIterator(const char* begin, const TextEncoding& encoding):
33 _pEncoding(&encoding),
34 _it(begin),
35 _end(begin + std::strlen(begin))
36{
37}
38
39
40TextBufferIterator::TextBufferIterator(const char* begin, std::size_t size, const TextEncoding& encoding):
41 _pEncoding(&encoding),
42 _it(begin),
43 _end(begin + size)
44{
45}
46
47
48TextBufferIterator::TextBufferIterator(const char* begin, const char* pEnd, const TextEncoding& encoding):
49 _pEncoding(&encoding),
50 _it(begin),
51 _end(pEnd)
52{
53}
54
55
56TextBufferIterator::TextBufferIterator(const char* pEnd):
57 _pEncoding(0),
58 _it(pEnd),
59 _end(pEnd)
60{
61}
62
63
64TextBufferIterator::~TextBufferIterator()
65{
66}
67
68
69TextBufferIterator::TextBufferIterator(const TextBufferIterator& it):
70 _pEncoding(it._pEncoding),
71 _it(it._it),
72 _end(it._end)
73{
74}
75
76
77TextBufferIterator& TextBufferIterator::operator = (const TextBufferIterator& it)
78{
79 if (&it != this)
80 {
81 _pEncoding = it._pEncoding;
82 _it = it._it;
83 _end = it._end;
84 }
85 return *this;
86}
87
88
89void TextBufferIterator::swap(TextBufferIterator& it)
90{
91 std::swap(_pEncoding, it._pEncoding);
92 std::swap(_it, it._it);
93 std::swap(_end, it._end);
94}
95
96
97int TextBufferIterator::operator * () const
98{
99 poco_check_ptr (_pEncoding);
100 poco_assert (_it != _end);
101 const char* it = _it;
102
103 unsigned char buffer[TextEncoding::MAX_SEQUENCE_LENGTH];
104 unsigned char* p = buffer;
105
106 if (it != _end)
107 *p++ = *it++;
108 else
109 *p++ = 0;
110
111 int read = 1;
112 int n = _pEncoding->queryConvert(buffer, 1);
113
114 while (-1 > n && (_end - it) >= -n - read)
115 {
116 while (read < -n && it != _end)
117 {
118 *p++ = *it++;
119 read++;
120 }
121 n = _pEncoding->queryConvert(buffer, read);
122 }
123
124 if (-1 > n)
125 {
126 return -1;
127 }
128 else
129 {
130 return n;
131 }
132}
133
134
135TextBufferIterator& TextBufferIterator::operator ++ ()
136{
137 poco_check_ptr (_pEncoding);
138 poco_assert (_it != _end);
139
140 unsigned char buffer[TextEncoding::MAX_SEQUENCE_LENGTH];
141 unsigned char* p = buffer;
142
143 if (_it != _end)
144 *p++ = *_it++;
145 else
146 *p++ = 0;
147
148 int read = 1;
149 int n = _pEncoding->sequenceLength(buffer, 1);
150
151 while (-1 > n && (_end - _it) >= -n - read)
152 {
153 while (read < -n && _it != _end)
154 {
155 *p++ = *_it++;
156 read++;
157 }
158 n = _pEncoding->sequenceLength(buffer, read);
159 }
160 while (read < n && _it != _end)
161 {
162 _it++;
163 read++;
164 }
165
166 return *this;
167}
168
169
170TextBufferIterator TextBufferIterator::operator ++ (int)
171{
172 TextBufferIterator prev(*this);
173 operator ++ ();
174 return prev;
175}
176
177
178} // namespace Poco
179