1//
2// Base32Encoder.cpp
3//
4// Library: Foundation
5// Package: Streams
6// Module: Base32
7//
8// Copyright (c) 2004-2006, Applied Informatics Software Engineering GmbH.
9// and Contributors.
10//
11// SPDX-License-Identifier: BSL-1.0
12//
13
14
15#include "Poco/Base32Encoder.h"
16
17
18namespace Poco {
19
20
21const unsigned char Base32EncoderBuf::OUT_ENCODING[32] =
22{
23 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H',
24 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P',
25 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X',
26 'Y', 'Z', '2', '3', '4', '5', '6', '7',
27};
28
29
30Base32EncoderBuf::Base32EncoderBuf(std::ostream& ostr, bool padding):
31 _groupLength(0),
32 _buf(*ostr.rdbuf()),
33 _doPadding(padding)
34{
35}
36
37
38Base32EncoderBuf::~Base32EncoderBuf()
39{
40 try
41 {
42 close();
43 }
44 catch (...)
45 {
46 }
47}
48
49
50
51int Base32EncoderBuf::writeToDevice(char c)
52{
53 static const int eof = std::char_traits<char>::eof();
54
55 _group[_groupLength++] = (unsigned char) c;
56 if (_groupLength == 5)
57 {
58 unsigned char idx;
59 idx = _group[0] >> 3;
60 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
61 idx = ((_group[0] & 0x07) << 2) | (_group[1] >> 6);
62 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
63 idx = ((_group[1] & 0x3E) >> 1);
64 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
65 idx = ((_group[1] & 0x01) << 4) | (_group[2] >> 4);
66 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
67 idx = ((_group[2] & 0x0F) << 1) | (_group[3] >> 7);
68 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
69 idx = ((_group[3] & 0x7C) >> 2);
70 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
71 idx = ((_group[3] & 0x03) << 3) | (_group[4] >> 5);
72 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
73 idx = (_group[4] & 0x1F);
74 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
75 _groupLength = 0;
76 }
77 return charToInt(c);
78}
79
80
81int Base32EncoderBuf::close()
82{
83 static const int eof = std::char_traits<char>::eof();
84
85 if (sync() == eof) return eof;
86 if (_groupLength == 1)
87 {
88 _group[1] = 0;
89 unsigned char idx;
90 idx = _group[0] >> 3;
91 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
92 idx = ((_group[0] & 0x07) << 2);
93 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
94 if (_doPadding) {
95 if (_buf.sputc('=') == eof) return eof;
96 if (_buf.sputc('=') == eof) return eof;
97 if (_buf.sputc('=') == eof) return eof;
98 if (_buf.sputc('=') == eof) return eof;
99 if (_buf.sputc('=') == eof) return eof;
100 if (_buf.sputc('=') == eof) return eof;
101 }
102 }
103 else if (_groupLength == 2)
104 {
105 _group[2] = 0;
106 unsigned char idx;
107 idx = _group[0] >> 3;
108 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
109 idx = ((_group[0] & 0x07) << 2) | (_group[1] >> 6);
110 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
111 idx = ((_group[1] & 0x3E) >> 1);
112 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
113 idx = ((_group[1] & 0x01) << 4);
114 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
115 if (_doPadding) {
116 if (_buf.sputc('=') == eof) return eof;
117 if (_buf.sputc('=') == eof) return eof;
118 if (_buf.sputc('=') == eof) return eof;
119 if (_buf.sputc('=') == eof) return eof;
120 }
121 }
122 else if (_groupLength == 3)
123 {
124 _group[3] = 0;
125 unsigned char idx;
126 idx = _group[0] >> 3;
127 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
128 idx = ((_group[0] & 0x07) << 2) | (_group[1] >> 6);
129 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
130 idx = ((_group[1] & 0x3E) >> 1);
131 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
132 idx = ((_group[1] & 0x01) << 4) | (_group[2] >> 4);
133 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
134 idx = ((_group[2] & 0x0F) << 1);
135 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
136 if (_doPadding) {
137 if (_buf.sputc('=') == eof) return eof;
138 if (_buf.sputc('=') == eof) return eof;
139 if (_buf.sputc('=') == eof) return eof;
140 }
141 }
142 else if (_groupLength == 4)
143 {
144 _group[4] = 0;
145 unsigned char idx;
146 idx = _group[0] >> 3;
147 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
148 idx = ((_group[0] & 0x07) << 2) | (_group[1] >> 6);
149 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
150 idx = ((_group[1] & 0x3E) >> 1);
151 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
152 idx = ((_group[1] & 0x01) << 4) | (_group[2] >> 4);
153 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
154 idx = ((_group[2] & 0x0F) << 1) | (_group[3] >> 7);
155 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
156 idx = ((_group[3] & 0x7C) >> 2);
157 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
158 idx = ((_group[3] & 0x03) << 3);
159 if (_buf.sputc(OUT_ENCODING[idx]) == eof) return eof;
160 if (_doPadding && _buf.sputc('=') == eof) return eof;
161 }
162 _groupLength = 0;
163 return _buf.pubsync();
164}
165
166
167Base32EncoderIOS::Base32EncoderIOS(std::ostream& ostr, bool padding):
168 _buf(ostr, padding)
169{
170 poco_ios_init(&_buf);
171}
172
173
174Base32EncoderIOS::~Base32EncoderIOS()
175{
176}
177
178
179int Base32EncoderIOS::close()
180{
181 return _buf.close();
182}
183
184
185Base32EncoderBuf* Base32EncoderIOS::rdbuf()
186{
187 return &_buf;
188}
189
190
191Base32Encoder::Base32Encoder(std::ostream& ostr, bool padding):
192 Base32EncoderIOS(ostr, padding), std::ostream(&_buf)
193{
194}
195
196
197Base32Encoder::~Base32Encoder()
198{
199}
200
201
202} // namespace Poco
203