1
/* Copyright 2000-2005 The Apache Software Foundation or its licensors, as
4
* Licensed under the Apache License, Version 2.0 (the "License");
5
* you may not use this file except in compliance with the License.
6
* You may obtain a copy of the License at
8
* http://www.apache.org/licenses/LICENSE-2.0
10
* Unless required by applicable law or agreed to in writing, software
11
* distributed under the License is distributed on an "AS IS" BASIS,
12
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
* See the License for the specific language governing permissions and
14
* limitations under the License.
17
/* base64 encoder/decoder. Originally part of main/util.c
18
* but moved here so that support/ab and apr_sha1.c could
19
* use it. This meant removing the apr_palloc()s and adding
20
* ugly 'len' functions, which is quite a nasty cost.
23
#include "apr_base64.h"
24
#if APR_CHARSET_EBCDIC
25
#include "apr_xlate.h"
26
#endif /* APR_CHARSET_EBCDIC */
28
/* aaaack but it's fast and const should make it shared text page. */
29
static const unsigned char pr2six[256] =
31
#if !APR_CHARSET_EBCDIC
33
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
34
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
35
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 62, 64, 64, 64, 63,
36
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 64, 64, 64, 64, 64, 64,
37
64, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
38
15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 64, 64, 64, 64, 64,
39
64, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
40
41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 64, 64, 64, 64, 64,
41
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
42
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
43
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
44
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
45
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
46
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
47
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
48
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64
49
#else /*APR_CHARSET_EBCDIC*/
51
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
52
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
53
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
54
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
55
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 62, 64,
56
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
57
64, 63, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
58
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
59
64, 26, 27, 28, 29, 30, 31, 32, 33, 34, 64, 64, 64, 64, 64, 64,
60
64, 35, 36, 37, 38, 39, 40, 41, 42, 43, 64, 64, 64, 64, 64, 64,
61
64, 64, 44, 45, 46, 47, 48, 49, 50, 51, 64, 64, 64, 64, 64, 64,
62
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64,
63
64, 0, 1, 2, 3, 4, 5, 6, 7, 8, 64, 64, 64, 64, 64, 64,
64
64, 9, 10, 11, 12, 13, 14, 15, 16, 17, 64, 64, 64, 64, 64, 64,
65
64, 64, 18, 19, 20, 21, 22, 23, 24, 25, 64, 64, 64, 64, 64, 64,
66
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 64, 64, 64, 64, 64, 64
67
#endif /*APR_CHARSET_EBCDIC*/
70
#if APR_CHARSET_EBCDIC
71
static apr_xlate_t *xlate_to_ebcdic;
72
static unsigned char os_toascii[256];
74
APU_DECLARE(apr_status_t) apr_base64init_ebcdic(apr_xlate_t *to_ascii,
75
apr_xlate_t *to_ebcdic)
78
apr_size_t inbytes_left, outbytes_left;
82
/* Only single-byte conversion is supported.
84
rv = apr_xlate_sb_get(to_ascii, &onoff);
88
if (!onoff) { /* If conversion is not single-byte-only */
91
rv = apr_xlate_sb_get(to_ebcdic, &onoff);
95
if (!onoff) { /* If conversion is not single-byte-only */
98
xlate_to_ebcdic = to_ebcdic;
99
for (i = 0; i < sizeof(os_toascii); i++) {
102
inbytes_left = outbytes_left = sizeof(os_toascii);
103
apr_xlate_conv_buffer(to_ascii, os_toascii, &inbytes_left,
104
os_toascii, &outbytes_left);
108
#endif /*APR_CHARSET_EBCDIC*/
110
APU_DECLARE(int) apr_base64_decode_len(const char *bufcoded)
113
register const unsigned char *bufin;
114
register int nprbytes;
116
bufin = (const unsigned char *) bufcoded;
117
while (pr2six[*(bufin++)] <= 63);
119
nprbytes = (bufin - (const unsigned char *) bufcoded) - 1;
120
nbytesdecoded = ((nprbytes + 3) / 4) * 3;
122
return nbytesdecoded + 1;
125
APU_DECLARE(int) apr_base64_decode(char *bufplain, const char *bufcoded)
127
#if APR_CHARSET_EBCDIC
128
apr_size_t inbytes_left, outbytes_left;
129
#endif /* APR_CHARSET_EBCDIC */
132
len = apr_base64_decode_binary((unsigned char *) bufplain, bufcoded);
133
#if APR_CHARSET_EBCDIC
134
inbytes_left = outbytes_left = len;
135
apr_xlate_conv_buffer(xlate_to_ebcdic, bufplain, &inbytes_left,
136
bufplain, &outbytes_left);
137
#endif /* APR_CHARSET_EBCDIC */
138
bufplain[len] = '\0';
142
/* This is the same as apr_base64_decode() except on EBCDIC machines, where
143
* the conversion of the output to ebcdic is left out.
145
APU_DECLARE(int) apr_base64_decode_binary(unsigned char *bufplain,
146
const char *bufcoded)
149
register const unsigned char *bufin;
150
register unsigned char *bufout;
151
register int nprbytes;
153
bufin = (const unsigned char *) bufcoded;
154
while (pr2six[*(bufin++)] <= 63);
155
nprbytes = (bufin - (const unsigned char *) bufcoded) - 1;
156
nbytesdecoded = ((nprbytes + 3) / 4) * 3;
158
bufout = (unsigned char *) bufplain;
159
bufin = (const unsigned char *) bufcoded;
161
while (nprbytes > 4) {
163
(unsigned char) (pr2six[*bufin] << 2 | pr2six[bufin[1]] >> 4);
165
(unsigned char) (pr2six[bufin[1]] << 4 | pr2six[bufin[2]] >> 2);
167
(unsigned char) (pr2six[bufin[2]] << 6 | pr2six[bufin[3]]);
172
/* Note: (nprbytes == 1) would be an error, so just ingore that case */
175
(unsigned char) (pr2six[*bufin] << 2 | pr2six[bufin[1]] >> 4);
179
(unsigned char) (pr2six[bufin[1]] << 4 | pr2six[bufin[2]] >> 2);
183
(unsigned char) (pr2six[bufin[2]] << 6 | pr2six[bufin[3]]);
186
nbytesdecoded -= (4 - nprbytes) & 3;
187
return nbytesdecoded;
190
static const char basis_64[] =
191
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
193
APU_DECLARE(int) apr_base64_encode_len(int len)
195
return ((len + 2) / 3 * 4) + 1;
198
APU_DECLARE(int) apr_base64_encode(char *encoded, const char *string, int len)
200
#if !APR_CHARSET_EBCDIC
201
return apr_base64_encode_binary(encoded, (const unsigned char *) string, len);
202
#else /* APR_CHARSET_EBCDIC */
207
for (i = 0; i < len - 2; i += 3) {
208
*p++ = basis_64[(os_toascii[string[i]] >> 2) & 0x3F];
209
*p++ = basis_64[((os_toascii[string[i]] & 0x3) << 4) |
210
((int) (os_toascii[string[i + 1]] & 0xF0) >> 4)];
211
*p++ = basis_64[((os_toascii[string[i + 1]] & 0xF) << 2) |
212
((int) (os_toascii[string[i + 2]] & 0xC0) >> 6)];
213
*p++ = basis_64[os_toascii[string[i + 2]] & 0x3F];
216
*p++ = basis_64[(os_toascii[string[i]] >> 2) & 0x3F];
217
if (i == (len - 1)) {
218
*p++ = basis_64[((os_toascii[string[i]] & 0x3) << 4)];
222
*p++ = basis_64[((os_toascii[string[i]] & 0x3) << 4) |
223
((int) (os_toascii[string[i + 1]] & 0xF0) >> 4)];
224
*p++ = basis_64[((os_toascii[string[i + 1]] & 0xF) << 2)];
231
#endif /* APR_CHARSET_EBCDIC */
234
/* This is the same as apr_base64_encode() except on EBCDIC machines, where
235
* the conversion of the input to ascii is left out.
237
APU_DECLARE(int) apr_base64_encode_binary(char *encoded,
238
const unsigned char *string, int len)
244
for (i = 0; i < len - 2; i += 3) {
245
*p++ = basis_64[(string[i] >> 2) & 0x3F];
246
*p++ = basis_64[((string[i] & 0x3) << 4) |
247
((int) (string[i + 1] & 0xF0) >> 4)];
248
*p++ = basis_64[((string[i + 1] & 0xF) << 2) |
249
((int) (string[i + 2] & 0xC0) >> 6)];
250
*p++ = basis_64[string[i + 2] & 0x3F];
253
*p++ = basis_64[(string[i] >> 2) & 0x3F];
254
if (i == (len - 1)) {
255
*p++ = basis_64[((string[i] & 0x3) << 4)];
259
*p++ = basis_64[((string[i] & 0x3) << 4) |
260
((int) (string[i + 1] & 0xF0) >> 4)];
261
*p++ = basis_64[((string[i + 1] & 0xF) << 2)];