c7cad2f7a4b96caf0a7c3542883e1853681c80bb
[gnulib.git] / tests / test-base64.c
1 /* Self tests for base64.
2    Copyright (C) 2004, 2008-2011 Free Software Foundation, Inc.
3    Written by Simon Josefsson.
4
5    This program is free software: you can redistribute it and/or modify
6    it under the terms of the GNU General Public License as published by
7    the Free Software Foundation; either version 3 of the License, or
8    (at your option) any later version.
9
10    This program is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14
15    You should have received a copy of the GNU General Public License
16    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
17
18 #include <config.h>
19
20 #include "base64.h"
21
22 #include <stddef.h>
23 #include <stdbool.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <stdint.h>
27
28 #include "macros.h"
29
30 int
31 main (void)
32 {
33   const char *in = "abcdefghijklmnop";
34   const char *b64in = "YWJjZGVmZw==";
35   char out[255];
36   size_t len;
37   bool ok;
38   char *p;
39
40   memset (out, 0x42, sizeof (out));
41   base64_encode (in, 0, out, 0);
42   ASSERT (out[0] == '\x42');
43
44   memset (out, 0x42, sizeof (out));
45   base64_encode (in, 1, out, 1);
46   ASSERT (memcmp (out, "YQ==", 1) == 0);
47
48   memset (out, 0x42, sizeof (out));
49   base64_encode (in, 1, out, 2);
50   ASSERT (memcmp (out, "YQ==", 2) == 0);
51
52   memset (out, 0x42, sizeof (out));
53   base64_encode (in, 1, out, 3);
54   ASSERT (memcmp (out, "YQ==", 3) == 0);
55
56   memset (out, 0x42, sizeof (out));
57   base64_encode (in, 1, out, 4);
58   ASSERT (memcmp (out, "YQ==", 4) == 0);
59
60   memset (out, 0x42, sizeof (out));
61   base64_encode (in, 1, out, 8);
62   ASSERT (memcmp (out, "YQ==", 4) == 0);
63
64   memset (out, 0x42, sizeof (out));
65   base64_encode (in, 2, out, 4);
66   ASSERT (memcmp (out, "YWI=", 4) == 0);
67
68   memset (out, 0x42, sizeof (out));
69   base64_encode (in, 3, out, 4);
70   ASSERT (memcmp (out, "YWJj", 4) == 0);
71
72   memset (out, 0x42, sizeof (out));
73   base64_encode (in, 4, out, 5);
74   ASSERT (memcmp (out, "YWJjZA==", 5) == 0);
75
76   memset (out, 0x42, sizeof (out));
77   base64_encode (in, 4, out, 100);
78   ASSERT (memcmp (out, "YWJjZA==", 6) == 0);
79
80   /* Decode. */
81
82   memset (out, 0x42, sizeof (out));
83   len = 0;
84   ok = base64_decode (b64in, 4, out, &len);
85   ASSERT (ok);
86   ASSERT (len == 0);
87
88   memset (out, 0x42, sizeof (out));
89   len = 1;
90   ok = base64_decode (b64in, 4, out, &len);
91   ASSERT (ok);
92   ASSERT (len == 1);
93   ASSERT (memcmp (out, "abcdefg", 1) == 0);
94
95   memset (out, 0x42, sizeof (out));
96   len = 2;
97   ok = base64_decode (b64in, 4, out, &len);
98   ASSERT (ok);
99   ASSERT (len == 2);
100   ASSERT (memcmp (out, "abcdefg", 2) == 0);
101
102   memset (out, 0x42, sizeof (out));
103   len = 3;
104   ok = base64_decode (b64in, 4, out, &len);
105   ASSERT (ok);
106   ASSERT (len == 3);
107   ASSERT (memcmp (out, "abcdefg", 3) == 0);
108
109   memset (out, 0x42, sizeof (out));
110   len = 4;
111   ok = base64_decode (b64in, 4, out, &len);
112   ASSERT (ok);
113   ASSERT (len == 3);
114   ASSERT (memcmp (out, "abcdefg", 3) == 0);
115
116   memset (out, 0x42, sizeof (out));
117   len = 100;
118   ok = base64_decode (b64in, strlen (b64in), out, &len);
119   ASSERT (ok);
120   ASSERT (len == 7);
121   ASSERT (memcmp (out, "abcdefg", 7) == 0);
122
123   /* Allocating encode */
124
125   len = base64_encode_alloc (in, strlen (in), &p);
126   ASSERT (len == 24);
127   ASSERT (strcmp (p, "YWJjZGVmZ2hpamtsbW5vcA==") == 0);
128   free (p);
129
130   len = base64_encode_alloc (in, SIZE_MAX - 5, &p);
131   ASSERT (len == 0);
132
133   /* Decode context function */
134   {
135     struct base64_decode_context ctx;
136
137     base64_decode_ctx_init (&ctx);
138
139     len = sizeof (out);
140     ok = base64_decode_ctx (&ctx, b64in, strlen (b64in), out, &len);
141     ASSERT (ok);
142     ASSERT (len == 7);
143     ASSERT (memcmp (out, "abcdefg", len) == 0);
144   }
145
146   /* Allocating decode context function */
147
148   ok = base64_decode_alloc_ctx (NULL, b64in, strlen (b64in), &p, &len);
149   ASSERT (ok);
150   ASSERT (len == 7);
151   ASSERT (memcmp (out, "abcdefg", len) == 0);
152
153   {
154     struct base64_decode_context ctx;
155     const char *newlineb64 = "YWJjZG\nVmZ2hp\namtsbW5vcA==";
156
157     base64_decode_ctx_init (&ctx);
158
159     ok = base64_decode_alloc_ctx (&ctx, newlineb64, strlen (newlineb64), &p, &len);
160     ASSERT (ok);
161     ASSERT (len == strlen (in));
162     ASSERT (memcmp (p, in, len) == 0);
163   }
164
165   {
166     struct base64_decode_context ctx;
167     base64_decode_ctx_init (&ctx);
168
169     ok = base64_decode_alloc_ctx (&ctx, "YW\nJjZGVmZ2hp", 13, &p, &len);
170     ASSERT (ok);
171     ASSERT (len == 9);
172     ASSERT (memcmp (p, "abcdefghi", len) == 0);
173
174     base64_decode_ctx_init (&ctx);
175
176     ok = base64_decode_alloc_ctx (&ctx, "YW\n", 3, &p, &len);
177     ASSERT (ok);
178     ASSERT (len == 0);
179
180     ok = base64_decode_alloc_ctx (&ctx, "JjZGVmZ2", 8, &p, &len);
181     ASSERT (ok);
182     ASSERT (len == 6);
183     ASSERT (memcmp (p, "abcdef", len) == 0);
184
185     ok = base64_decode_alloc_ctx (&ctx, "hp", 2, &p, &len);
186     ASSERT (ok);
187     ASSERT (len == 2);
188     /* Actually this looks buggy.  Shouldn't output be 'ghi'? */
189     ASSERT (memcmp (p, "gh", len) == 0);
190     ok = base64_decode_alloc_ctx (&ctx, "", 0, &p, &len);
191     ASSERT (ok);
192   }
193
194   {
195     struct base64_decode_context ctx;
196     const char *newlineb64 = "\n\n\n\n\n";
197
198     base64_decode_ctx_init (&ctx);
199
200     ok = base64_decode_alloc_ctx (&ctx, newlineb64, strlen (newlineb64), &p, &len);
201     ASSERT (ok);
202     ASSERT (len == 0);
203   }
204
205   ok = base64_decode_alloc_ctx (NULL, " ! ", 3, &p, &len);
206   ASSERT (!ok);
207
208   ok = base64_decode_alloc_ctx (NULL, "abc\ndef", 7, &p, &len);
209   ASSERT (!ok);
210
211   ok = base64_decode_alloc_ctx (NULL, "aa", 2, &p, &len);
212   ASSERT (!ok);
213
214   ok = base64_decode_alloc_ctx (NULL, "aa=", 3, &p, &len);
215   ASSERT (!ok);
216
217   ok = base64_decode_alloc_ctx (NULL, "aax", 3, &p, &len);
218   ASSERT (!ok);
219
220   ok = base64_decode_alloc_ctx (NULL, "aa=X", 4, &p, &len);
221   ASSERT (!ok);
222
223   ok = base64_decode_alloc_ctx (NULL, "aa=X", 4, &p, &len);
224   ASSERT (!ok);
225
226   ok = base64_decode_alloc_ctx (NULL, "aax=X", 5, &p, &len);
227   ASSERT (!ok);
228
229   return 0;
230 }