tizen beta release
[framework/web/wrt-plugins-common.git] / src / Commons / Base64.cpp
1 /*
2  * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
3  *
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
7  *
8  *        http://www.apache.org/licenses/LICENSE-2.0
9  *
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.
15  */
16 /*
17  * Copyright (c) 2003-2007, Bicom Systems Ltd.
18  *
19  * All rights reserved.
20  *
21  * Redistribution and use in source and binary forms, with or without
22  * modification, are permitted provided that the following conditions are met:
23  *
24  *   - Redistributions of source code must retain the above copyright notice,
25  *         this list of conditions and the following disclaimer.
26  *   - Redistributions in binary form must reproduce the above copyright
27  *         notice, this list of conditions and the following disclaimer in the
28  *         documentation and/or other materials provided with the distribution.
29  *   - Neither the name of the Bicom Systems Ltd nor the names of its
30  *         contributors may be used to endorse or promote products derived from
31  *         this software without specific prior written permission.
32  *
33  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
34  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
35  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
36  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
37  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
38  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
39  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
40  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
41  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
42  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
43  * POSSIBILITY OF SUCH DAMAGE.
44  *
45  * Denis Komadaric,
46  * Bicom Systems Ltd.
47  */
48 #include <ctype.h>
49 #include "Exception.h"
50 #include "Base64.h"
51
52 namespace WrtDeviceApis {
53 namespace Commons {
54
55 const std::string Base64::chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
56     "abcdefghijklmnopqrstuvwxyz"
57     "0123456789+/";
58
59 bool Base64::is_base64(unsigned char c)
60 {
61     return (isalnum(c) || (c == '+') || (c == '/'));
62 }
63
64 std::string Base64::encode(unsigned char* data,
65         std::size_t num)
66 {
67     std::string ret;
68     int i = 0;
69     int j = 0;
70     unsigned char char_array_3[3];
71     unsigned char char_array_4[4];
72
73     while (num--) {
74         char_array_3[i++] = *(data++);
75         if (i == 3) {
76             char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
77             char_array_4[1] =
78                 ((char_array_3[0] &
79                   0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
80             char_array_4[2] =
81                 ((char_array_3[1] &
82                   0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
83             char_array_4[3] = char_array_3[2] & 0x3f;
84
85             for (i = 0; i < 4; ++i) {
86                 ret += chars[char_array_4[i]];
87             }
88             i = 0;
89         }
90     }
91
92     if (i != 0) {
93         for (j = i; j < 3; ++j) {
94             char_array_3[j] = '\0';
95         }
96
97         char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
98         char_array_4[1] =
99             ((char_array_3[0] & 0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
100         char_array_4[2] =
101             ((char_array_3[1] & 0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
102         char_array_4[3] = char_array_3[2] & 0x3f;
103
104         for (j = 0; (j < i + 1); ++j) {
105             ret += chars[char_array_4[j]];
106         }
107
108         while ((i++ < 3)) {
109             ret += '=';
110         }
111     }
112
113     return ret;
114 }
115
116 std::string Base64::decode(const std::string& str)
117 {
118     if (!is_base64_string(str)) {
119         ThrowMsg(InvalidArgumentException,
120                  "Invalid length of base64 string.");
121     }
122     int in_len = str.size();
123     int i = 0;
124     int j = 0;
125     int in_ = 0;
126     unsigned char char_array_4[4], char_array_3[3];
127     std::string ret;
128
129     while (in_len-- && (str[in_] != '=')) {
130         if (!is_base64(str[in_])) {
131             ThrowMsg(InvalidArgumentException,
132                      "Invalid characters in base64 string.");
133         }
134         char_array_4[i++] = str[in_];
135         in_++;
136         if (i == 4) {
137             for (i = 0; i < 4; ++i) {
138                 char_array_4[i] = chars.find(char_array_4[i]);
139             }
140
141             char_array_3[0] =
142                 (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
143             char_array_3[1] =
144                 ((char_array_4[1] &
145                   0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
146             char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
147
148             for (i = 0; i < 3; ++i) {
149                 ret += char_array_3[i];
150             }
151             i = 0;
152         }
153     }
154
155     if (i != 0) {
156         for (j = i; j < 4; ++j) {
157             char_array_4[j] = 0;
158         }
159
160         for (j = 0; j < 4; ++j) {
161             char_array_4[j] = chars.find(char_array_4[j]);
162         }
163
164         char_array_3[0] =
165             (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
166         char_array_3[1] =
167             ((char_array_4[1] & 0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
168         char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
169
170         for (j = 0; (j < i - 1); ++j) {
171             ret += char_array_3[j];
172         }
173     }
174
175     return ret;
176 }
177
178 bool Base64::is_base64_string(const std::string& str)
179 {
180     return ((str.size() % 4) == 0);
181 }
182
183 }
184 } //WrtDeviceApisCommon