Line data Source code
1 : /*
2 : Unix SMB/CIFS implementation.
3 : test suite for the charcnv functions
4 :
5 : Copyright (C) Andrew Bartlett 2011
6 :
7 : This program is free software; you can redistribute it and/or modify
8 : it under the terms of the GNU General Public License as published by
9 : the Free Software Foundation; either version 3 of the License, or
10 : (at your option) any later version.
11 :
12 : This program is distributed in the hope that it will be useful,
13 : but WITHOUT ANY WARRANTY; without even the implied warranty of
14 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 : GNU General Public License for more details.
16 :
17 : You should have received a copy of the GNU General Public License
18 : along with this program. If not, see <http://www.gnu.org/licenses/>.
19 : */
20 :
21 : #include "includes.h"
22 : #include "torture/torture.h"
23 : #include "lib/util/charset/charset.h"
24 : #include "param/param.h"
25 : #include "lib/util/base64.h"
26 :
27 : struct torture_suite *torture_local_convert_string_handle(TALLOC_CTX *mem_ctx);
28 : struct torture_suite *torture_local_string_case_handle(TALLOC_CTX *mem_ctx);
29 : struct torture_suite *torture_local_convert_string(TALLOC_CTX *mem_ctx);
30 : struct torture_suite *torture_local_string_case(TALLOC_CTX *mem_ctx);
31 :
32 : /* The text below is in ancient and a latin charset transliteration of
33 : * greek, and an english translation. It from Apology by Plato and sourced from
34 : * http://en.wikipedia.org/w/index.php?title=Ancient_Greek&oldid=421361065#Example_text
35 : */
36 :
37 : const char *plato_english_ascii =
38 : "What you, men of Athens, have learned from my accusers, I do not"
39 : " know: but I, for my part, nearly forgot who I was thanks to them since"
40 : " they spoke so persuasively. And yet, of the truth, they have spoken,"
41 : " one might say, nothing at all.";
42 :
43 : const char *plato_english_utf16le_base64 =
44 : "VwBoAGEAdAAgAHkAbwB1ACwAIABtAGUAbgAgAG8AZgAgAEEAdABoAGUAbgBzACwAIABoAGEAdgBl"
45 : "ACAAbABlAGEAcgBuAGUAZAAgAGYAcgBvAG0AIABtAHkAIABhAGMAYwB1AHMAZQByAHMALAAgAEkA"
46 : "IABkAG8AIABuAG8AdAAgAGsAbgBvAHcAOgAgAGIAdQB0ACAASQAsACAAZgBvAHIAIABtAHkAIABw"
47 : "AGEAcgB0ACwAIABuAGUAYQByAGwAeQAgAGYAbwByAGcAbwB0ACAAdwBoAG8AIABJACAAdwBhAHMA"
48 : "IAB0AGgAYQBuAGsAcwAgAHQAbwAgAHQAaABlAG0AIABzAGkAbgBjAGUAIAB0AGgAZQB5ACAAcwBw"
49 : "AG8AawBlACAAcwBvACAAcABlAHIAcwB1AGEAcwBpAHYAZQBsAHkALgAgAEEAbgBkACAAeQBlAHQA"
50 : "LAAgAG8AZgAgAHQAaABlACAAdAByAHUAdABoACwAIAB0AGgAZQB5ACAAaABhAHYAZQAgAHMAcABv"
51 : "AGsAZQBuACwAIABvAG4AZQAgAG0AaQBnAGgAdAAgAHMAYQB5ACwAIABuAG8AdABoAGkAbgBnACAA"
52 : "YQB0ACAAYQBsAGwALgA=";
53 :
54 : static const char *plato_utf8_base64 =
55 : "4b2Nz4TOuSDOvOG9ss69IOG9kc68zrXhv5bPgiwg4b2mIOG8hM69zrTPgc61z4IgzobOuM63zr3O"
56 : "seG/ls6/zrksIM+AzrXPgM+Mzr3OuM6xz4TOtSDhvZHPgOG9uCDPhOG/ts69IOG8kM684b+2zr0g"
57 : "zrrOsc+EzrfOs8+Mz4HPic69LCDOv+G9kM66IM6/4by2zrTOsTog4byQzrPhvbwgzrQnIM6/4b2W"
58 : "zr0gzrrOseG9tiDOseG9kM+E4b24z4Ig4b2Rz4AnIM6x4b2Qz4Thv7bOvSDhvYDOu86vzrPOv8+F"
59 : "IOG8kM68zrHPhc+Ezr/hv6Yg4byQz4DOtc67zrHOuM+MzrzOt869LCDOv+G9lc+Ez4kgz4DOuc64"
60 : "zrHOveG/ts+CIOG8lM67zrXOs86/zr0uIM6azrHOr8+Ezr/OuSDhvIDOu863zrjOrc+CIM6zzrUg"
61 : "4b2hz4Ig4byUz4DOv8+CIM614bywz4DOteG/ls69IM6/4b2QzrThvbLOvSDOteG8sM+Bzq7Ous6x"
62 : "z4POuc69Lg==";
63 :
64 : static const char *plato_utf16le_base64 =
65 : "TR/EA7kDIAC8A3IfvQMgAFEfvAO1A9YfwgMsACAAZh8gAAQfvQO0A8EDtQPCAyAAhgO4A7cDvQOx"
66 : "A9YfvwO5AywAIADAA7UDwAPMA70DuAOxA8QDtQMgAFEfwAN4HyAAxAP2H70DIAAQH7wD9h+9AyAA"
67 : "ugOxA8QDtwOzA8wDwQPJA70DLAAgAL8DUB+6AyAAvwM2H7QDsQM6ACAAEB+zA3wfIAC0AycAIAC/"
68 : "A1YfvQMgALoDsQN2HyAAsQNQH8QDeB/CAyAAUR/AAycAIACxA1AfxAP2H70DIABAH7sDrwOzA78D"
69 : "xQMgABAfvAOxA8UDxAO/A+YfIAAQH8ADtQO7A7EDuAPMA7wDtwO9AywAIAC/A1UfxAPJAyAAwAO5"
70 : "A7gDsQO9A/YfwgMgABQfuwO1A7MDvwO9Ay4AIACaA7EDrwPEA78DuQMgAAAfuwO3A7gDrQPCAyAA"
71 : "swO1AyAAYR/CAyAAFB/AA78DwgMgALUDMB/AA7UD1h+9AyAAvwNQH7QDch+9AyAAtQMwH8EDrgO6"
72 : "A7EDwwO5A70DLgA=";
73 :
74 : static const char *plato_latin_utf8_base64 =
75 : "SMOzdGkgbcOobiBodW1lw65zLCDDtCDDoW5kcmVzIEF0aMSTbmHDrm9pLCBwZXDDs250aGF0ZSBo"
76 : "dXDDsiB0w7RuIGVtw7RuIGthdMSTZ8OzcsWNbiwgb3VrIG/DrmRhOiBlZ+G5kSBkJyBvw7tuIGth"
77 : "w6wgYXV0w7JzIGh1cCcgYXV0xY1uIG9sw61nb3UgZW1hdXRvw7sgZXBlbGF0aMOzbcSTbiwgaG/D"
78 : "unTFjSBwaXRoYW7DtHMgw6lsZWdvbi4gS2HDrXRvaSBhbMSTdGjDqXMgZ2UgaMWNcyDDqXBvcyBl"
79 : "aXBlw65uIG91ZMOobiBlaXLhuJdrYXNpbi4=";
80 :
81 : static const char *plato_latin_utf16le_base64 =
82 : "SADzAHQAaQAgAG0A6ABuACAAaAB1AG0AZQDuAHMALAAgAPQAIADhAG4AZAByAGUAcwAgAEEAdABo"
83 : "ABMBbgBhAO4AbwBpACwAIABwAGUAcADzAG4AdABoAGEAdABlACAAaAB1AHAA8gAgAHQA9ABuACAA"
84 : "ZQBtAPQAbgAgAGsAYQB0ABMBZwDzAHIATQFuACwAIABvAHUAawAgAG8A7gBkAGEAOgAgAGUAZwBR"
85 : "HiAAZAAnACAAbwD7AG4AIABrAGEA7AAgAGEAdQB0APIAcwAgAGgAdQBwACcAIABhAHUAdABNAW4A"
86 : "IABvAGwA7QBnAG8AdQAgAGUAbQBhAHUAdABvAPsAIABlAHAAZQBsAGEAdABoAPMAbQATAW4ALAAg"
87 : "AGgAbwD6AHQATQEgAHAAaQB0AGgAYQBuAPQAcwAgAOkAbABlAGcAbwBuAC4AIABLAGEA7QB0AG8A"
88 : "aQAgAGEAbAATAXQAaADpAHMAIABnAGUAIABoAE0BcwAgAOkAcABvAHMAIABlAGkAcABlAO4AbgAg"
89 : "AG8AdQBkAOgAbgAgAGUAaQByABceawBhAHMAaQBuAC4A";
90 :
91 : static const char *gd_utf8_base64 = "R8O8bnRoZXIgRGVzY2huZXI=";
92 : static const char *gd_utf8_upper_base64 = "R8OcTlRIRVIgREVTQ0hORVI=";
93 : static const char *gd_utf8_lower_base64 = "Z8O8bnRoZXIgZGVzY2huZXI=";
94 : static const char *gd_cp850_base64 = "R4FudGhlciBEZXNjaG5lcg==";
95 : static const char *gd_cp850_upper_base64 = "R5pOVEhFUiBERVNDSE5FUg==";
96 : static const char *gd_cp850_lower_base64 = "Z4FudGhlciBkZXNjaG5lcg==";
97 : static const char *gd_iso8859_1_base64 = "R/xudGhlciBEZXNjaG5lcg==";
98 : static const char *gd_utf16le_base64 = "RwD8AG4AdABoAGUAcgAgAEQAZQBzAGMAaABuAGUAcgA=";
99 : /* täst */
100 : static const char *utf8_nfc_base64 = "dMOkc3QA";
101 : /* täst, where ä = a + combining diaeresis */
102 : static const char *utf8_nfd_base64 = "dGHMiHN0AA==";
103 :
104 : /*
105 : * These cp850 bytes correspond to high Unicode codes, stretching out to
106 : * 3-byte sequences in utf-8.
107 : */
108 : static const char *cp850_high_points = "\xb9\xba\xbb\xbc\xcd\xce";
109 : static const char *utf8_high_points = "╣║╗╝═╬";
110 :
111 0 : static bool test_cp850_high_points(struct torture_context *tctx)
112 : {
113 0 : struct smb_iconv_handle *iconv_handle = NULL;
114 0 : DATA_BLOB cp850 = data_blob_string_const(cp850_high_points);
115 : DATA_BLOB utf8;
116 : DATA_BLOB cp850_return;
117 :
118 0 : iconv_handle = get_iconv_testing_handle(tctx, "CP850", "UTF8",
119 0 : lpcfg_parm_bool(tctx->lp_ctx,
120 : NULL,
121 : "iconv",
122 : "use_builtin_handlers",
123 : true));
124 :
125 0 : torture_assert(tctx, iconv_handle, "creating iconv handle");
126 :
127 0 : torture_assert(tctx,
128 : convert_string_talloc_handle(tctx, iconv_handle,
129 : CH_DOS, CH_UTF8,
130 : cp850.data, cp850.length,
131 : (void *)&utf8.data, &utf8.length),
132 : "conversion from CP850 to UTF-8");
133 :
134 0 : torture_assert(tctx, utf8.length == cp850.length * 3,
135 : "CP850 high bytes expand to the right size");
136 :
137 0 : torture_assert(tctx,
138 : memcmp(utf8.data, utf8_high_points, utf8.length) == 0,
139 : "cp850 converted to utf8 matches expected value");
140 :
141 0 : torture_assert(tctx,
142 : convert_string_talloc_handle(tctx, iconv_handle,
143 : CH_UTF8, CH_DOS,
144 : utf8.data, utf8.length,
145 : (void *)&cp850_return.data,
146 : &cp850_return.length),
147 : "conversion from UTF-8 back to CP850");
148 :
149 0 : torture_assert(tctx, data_blob_cmp(&cp850_return, &cp850) == 0,
150 : "UTF-8 returned to CP850 matches the original");
151 0 : return true;
152 : }
153 :
154 :
155 0 : static bool test_gd_iso8859_cp850_handle(struct torture_context *tctx)
156 : {
157 : struct smb_iconv_handle *iconv_handle;
158 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
159 0 : DATA_BLOB gd_cp850 = base64_decode_data_blob(gd_cp850_base64);
160 0 : DATA_BLOB gd_iso8859_1 = base64_decode_data_blob(gd_iso8859_1_base64);
161 0 : DATA_BLOB gd_utf16le = base64_decode_data_blob(gd_utf16le_base64);
162 : DATA_BLOB gd_output;
163 : DATA_BLOB gd_output2;
164 :
165 0 : talloc_steal(tctx, gd_utf8.data);
166 0 : talloc_steal(tctx, gd_cp850.data);
167 0 : talloc_steal(tctx, gd_iso8859_1.data);
168 0 : talloc_steal(tctx, gd_utf16le.data);
169 :
170 0 : iconv_handle = get_iconv_testing_handle(tctx, "ISO-8859-1", "CP850",
171 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
172 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
173 :
174 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
175 : CH_UTF8, CH_DOS,
176 : gd_utf8.data, gd_utf8.length,
177 : (void *)&gd_output.data, &gd_output.length),
178 : "conversion from UTF8 to (dos charset) ISO-8859-1");
179 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_iso8859_1, "conversion from UTF8 to (dos charset) ISO-8859-1 incorrect");
180 :
181 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
182 : CH_UTF8, CH_DOS,
183 : gd_utf8.data, gd_utf8.length,
184 : (void *)gd_output.data, gd_output.length,
185 : &gd_output.length),
186 : "conversion from UTF8 to (dos charset) ISO-8859-1");
187 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_iso8859_1, "conversion from UTF8 to (dos charset) ISO-8859-1 incorrect");
188 :
189 : /* Short output handling confirmation */
190 0 : gd_output.length = 1;
191 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
192 : CH_UTF8, CH_DOS,
193 : gd_utf8.data, gd_utf8.length,
194 : (void *)gd_output.data, gd_output.length,
195 : &gd_output.length) == false,
196 : "conversion from UTF8 to (dos charset) ISO-8859-1 should fail due to too short");
197 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to (dos charset) ISO-8859-1 should fail E2BIG");
198 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
199 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "conversion from UTF8 to (dos charset) ISO-8859-1 incorrect");
200 :
201 : /* Short output handling confirmation */
202 0 : gd_output.length = 2;
203 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
204 : CH_UTF8, CH_DOS,
205 : gd_utf8.data, gd_utf8.length,
206 : (void *)gd_output.data, gd_output.length,
207 : &gd_output.length) == false,
208 : "conversion from UTF8 to (dos charset) ISO-8859-1 should fail due to too short");
209 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to (dos charset) ISO-8859-1 should fail E2BIG");
210 0 : torture_assert_int_equal(tctx, gd_output.length, 2, "Should only get 2 char of output");
211 :
212 : /* Short input handling confirmation */
213 0 : gd_output.length = gd_iso8859_1.length;
214 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
215 : CH_UTF8, CH_DOS,
216 : gd_utf8.data, 2,
217 : (void *)gd_output.data, gd_output.length,
218 : &gd_output.length) == false,
219 : "conversion from UTF8 to (dos charset) ISO-8859-1 should fail due to too short");
220 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion from short UTF8 to (dos charset) ISO-8859-1 should fail EINVAL");
221 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
222 :
223 : /* Short output handling confirmation */
224 0 : gd_output.length = 1;
225 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
226 : CH_UTF16LE, CH_UTF8,
227 : gd_utf16le.data, gd_utf16le.length,
228 : (void *)gd_output.data, gd_output.length,
229 : &gd_output.length) == false,
230 : "conversion from UTF16 to UTF8 should fail due to too short");
231 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16 to (utf8 charset) ISO-8859-1 should fail E2BIG");
232 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
233 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "conversion from UTF16 to UTF8 incorrect");
234 :
235 : /* Short output handling confirmation */
236 0 : gd_output.length = 3;
237 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
238 : CH_UTF16LE, CH_UTF8,
239 : gd_utf16le.data, gd_utf16le.length,
240 : (void *)gd_output.data, gd_output.length,
241 : &gd_output.length) == false,
242 : "conversion from UTF16 to UTF8 should fail due to too short");
243 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16 to (utf8 charset) ISO-8859-1 should fail E2BIG");
244 0 : torture_assert_int_equal(tctx, gd_output.length, 3, "Should get 3 bytes output for UTF8");
245 :
246 : /* Short input handling confirmation */
247 0 : gd_output.length = gd_utf8.length;
248 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
249 : CH_UTF16LE, CH_UTF8,
250 : gd_utf16le.data, 3,
251 : (void *)gd_output.data, gd_output.length,
252 : &gd_output.length) == false,
253 : "conversion from UTF16 to UTF8 should fail due to too short");
254 0 : torture_assert_errno_equal(tctx, EINVAL, "conversion from short UTF16 to UTF8 should fail EINVAL");
255 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
256 :
257 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
258 : CH_UTF8, CH_UNIX,
259 : gd_utf8.data, gd_utf8.length,
260 : (void *)&gd_output.data, &gd_output.length),
261 : "conversion from UTF8 to (unix charset) CP850");
262 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_cp850, "conversion from UTF8 to (unix charset) CP850 incorrect");
263 :
264 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
265 : CH_UTF8, CH_UTF8,
266 : gd_utf8.data, gd_utf8.length,
267 : (void *)&gd_output.data, &gd_output.length),
268 : "conversion from UTF8 to UTF8");
269 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8, "conversion from UTF8 to UTF8 incorrect");
270 :
271 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
272 : CH_UTF16LE, CH_DOS,
273 : gd_utf16le.data, gd_utf16le.length,
274 : (void *)&gd_output.data, &gd_output.length),
275 : "conversion from UTF16LE to (dos charset) ISO-8859-1");
276 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_iso8859_1, "conversion from UTF16LE to (dos charset) ISO-8859-1 incorrect");
277 :
278 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
279 : CH_DOS, CH_UTF16LE,
280 : gd_output.data, gd_output.length,
281 : (void *)&gd_output2.data, &gd_output2.length),
282 : "round trip conversion from (dos charset) ISO-8859-1 back to UTF16LE");
283 0 : torture_assert_data_blob_equal(tctx, gd_output2, gd_utf16le, "round trip conversion from (dos charset) ISO-8859-1 back to UTF16LE");
284 :
285 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
286 : CH_UTF16LE, CH_UNIX,
287 : gd_utf16le.data, gd_utf16le.length,
288 : (void *)&gd_output.data, &gd_output.length),
289 : "conversion from UTF16LE to (unix charset) CP850");
290 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_cp850, "conversion from UTF16LE to (unix charset) CP850 incorrect");
291 :
292 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
293 : CH_UTF16LE, CH_UTF8,
294 : gd_utf16le.data, gd_utf16le.length,
295 : (void *)&gd_output.data, &gd_output.length),
296 : "conversion from UTF16LE to UTF8");
297 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8, "conversion from UTF16LE to UTF8 incorrect");
298 :
299 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
300 : CH_DOS, CH_DOS,
301 : gd_iso8859_1.data, gd_iso8859_1.length,
302 : (void *)&gd_output.data, &gd_output.length),
303 : "conversion from (dos charset) ISO-8859-1 to (dos charset) ISO-8859-1");
304 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_iso8859_1, "conversion from UTF16LE to (dos charset) ISO-8859-1 incorrect");
305 :
306 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
307 : CH_DOS, CH_UNIX,
308 : gd_iso8859_1.data, gd_iso8859_1.length,
309 : (void *)&gd_output.data, &gd_output.length),
310 : "conversion from (dos charset) ISO-8859-1 to (unix charset) CP850");
311 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_cp850, "conversion from UTF16LE to (unix charset) CP850 incorrect");
312 :
313 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
314 : CH_DOS, CH_UTF8,
315 : gd_iso8859_1.data, gd_iso8859_1.length,
316 : (void *)&gd_output.data, &gd_output.length),
317 : "conversion from (dos charset) ISO-8859-1 to UTF8");
318 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8, "conversion from UTF16LE to UTF8 incorrect");
319 :
320 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
321 : CH_DOS, CH_UTF16LE,
322 : gd_iso8859_1.data, gd_iso8859_1.length,
323 : (void *)&gd_output.data, &gd_output.length),
324 : "conversion from (dos charset) ISO-8859-1 to UTF16LE");
325 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le, "conversion from (dos charset) ISO-8859-1 to UTF16LE");
326 0 : torture_assert_int_equal(tctx,
327 : strlen_m_ext_handle(iconv_handle,
328 : (const char *)gd_iso8859_1.data,
329 : CH_DOS, CH_UTF16LE),
330 : gd_output.length / 2,
331 : "checking strlen_m_ext of round trip conversion of UTF16 latin charset greek to UTF8 and back again");
332 :
333 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
334 : CH_DOS, CH_UTF8,
335 : gd_iso8859_1.data, gd_iso8859_1.length,
336 : (void *)&gd_output.data, &gd_output.length),
337 : "conversion from (dos charset) ISO-8859-1 to UTF8");
338 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8, "conversion from (dos charset) ISO-8859-1 to UTF8");
339 0 : torture_assert_int_equal(tctx,
340 : strlen_m_ext_handle(iconv_handle,
341 : (const char *)gd_iso8859_1.data,
342 : CH_DOS, CH_UTF8),
343 : gd_output.length,
344 : "checking strlen_m_ext of conversion from (dos charset) ISO-8859-1 to UTF8");
345 0 : return true;
346 : }
347 :
348 0 : static bool test_gd_minus_1_handle(struct torture_context *tctx)
349 : {
350 : struct smb_iconv_handle *iconv_handle;
351 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
352 0 : DATA_BLOB gd_cp850 = base64_decode_data_blob(gd_cp850_base64);
353 0 : DATA_BLOB gd_utf16le = base64_decode_data_blob(gd_utf16le_base64);
354 : DATA_BLOB gd_output;
355 : DATA_BLOB gd_utf8_terminated;
356 : DATA_BLOB gd_cp850_terminated;
357 : DATA_BLOB gd_utf16le_terminated;
358 :
359 0 : talloc_steal(tctx, gd_utf8.data);
360 0 : talloc_steal(tctx, gd_cp850.data);
361 0 : talloc_steal(tctx, gd_utf16le.data);
362 :
363 0 : iconv_handle = get_iconv_testing_handle(tctx, "CP850", "CP850",
364 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
365 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
366 :
367 0 : gd_utf8_terminated = data_blob_talloc(tctx, NULL, gd_utf8.length + 1);
368 0 : memcpy(gd_utf8_terminated.data, gd_utf8.data, gd_utf8.length);
369 0 : gd_utf8_terminated.data[gd_utf8.length] = '\0';
370 :
371 0 : gd_cp850_terminated = data_blob_talloc(tctx, NULL, gd_cp850.length + 1);
372 0 : memcpy(gd_cp850_terminated.data, gd_cp850.data, gd_cp850.length);
373 0 : gd_cp850_terminated.data[gd_cp850.length] = '\0';
374 :
375 0 : gd_utf16le_terminated = data_blob_talloc(tctx, NULL, gd_utf16le.length + 2);
376 0 : memcpy(gd_utf16le_terminated.data, gd_utf16le.data, gd_utf16le.length);
377 0 : gd_utf16le_terminated.data[gd_utf16le.length] = '\0';
378 0 : gd_utf16le_terminated.data[gd_utf16le.length + 1] = '\0';
379 :
380 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
381 :
382 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
383 : CH_UTF8, CH_UTF16LE,
384 : gd_utf8_terminated.data, -1,
385 : (void *)gd_output.data, gd_output.length, &gd_output.length),
386 : "conversion from UTF8 to UTF16LE null terminated");
387 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated");
388 :
389 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
390 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
391 : CH_UTF8, CH_UTF16LE,
392 : gd_utf8_terminated.data, -1,
393 : (void *)gd_output.data, gd_utf16le.length, &gd_output.length) == false,
394 : "conversion from UTF8 to UTF16LE null terminated should fail");
395 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
396 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le, "conversion from UTF8 to UTF16LE null terminated");
397 :
398 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
399 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
400 : CH_UTF8, CH_UTF16LE,
401 : gd_utf8_terminated.data, -1,
402 : (void *)gd_output.data, gd_utf16le.length - 1, &gd_output.length) == false,
403 : "conversion from UTF8 to UTF16LE null terminated should fail");
404 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
405 :
406 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
407 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
408 : CH_UTF8, CH_UTF16LE,
409 : gd_utf8_terminated.data, -1,
410 : (void *)gd_output.data, gd_utf16le.length - 2, &gd_output.length) == false,
411 : "conversion from UTF8 to UTF16LE null terminated should fail");
412 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
413 :
414 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
415 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
416 : CH_UTF16LE, CH_UTF8,
417 : gd_utf16le_terminated.data, -1,
418 : (void *)gd_output.data, gd_output.length, &gd_output.length),
419 : "conversion from UTF16LE to UTF8 null terminated");
420 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated");
421 :
422 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
423 :
424 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
425 : CH_UTF16LE, CH_UTF8,
426 : gd_utf16le_terminated.data, -1,
427 : (void *)gd_output.data, gd_utf8.length, &gd_output.length) == false,
428 : "conversion from UTF16LE to UTF8 null terminated should fail");
429 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
430 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8, "conversion from UTF16LE to UTF8 null terminated");
431 :
432 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
433 :
434 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
435 : CH_UTF16LE, CH_UTF8,
436 : gd_utf16le_terminated.data, -1,
437 : (void *)gd_output.data, gd_utf8.length - 1, &gd_output.length) == false,
438 : "conversion from UTF16LE to UTF8 null terminated should fail");
439 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
440 :
441 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
442 :
443 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
444 : CH_UTF16LE, CH_UTF8,
445 : gd_utf16le_terminated.data, -1,
446 : (void *)gd_output.data, gd_utf8.length - 2, &gd_output.length) == false,
447 : "conversion from UTF16LE to UTF8 null terminated should fail");
448 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
449 :
450 0 : gd_output = data_blob_talloc(tctx, NULL, gd_cp850.length + 10);
451 :
452 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
453 : CH_UTF16LE, CH_DOS,
454 : gd_utf16le_terminated.data, -1,
455 : (void *)gd_output.data, gd_output.length, &gd_output.length),
456 : "conversion from UTF16LE to CP850 (dos) null terminated");
457 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_cp850_terminated, "conversion from UTF16LE to CP850 (dos) null terminated");
458 :
459 : /* Now null terminate the string early, the confirm we don't skip the NULL and convert any further */
460 0 : gd_utf8_terminated.data[3] = '\0';
461 0 : gd_utf8_terminated.length = 4; /* used for the comparison only */
462 :
463 0 : gd_cp850_terminated.data[2] = '\0';
464 0 : gd_cp850_terminated.length = 3; /* used for the comparison only */
465 :
466 0 : gd_utf16le_terminated.data[4] = '\0';
467 0 : gd_utf16le_terminated.data[5] = '\0';
468 0 : gd_utf16le_terminated.length = 6; /* used for the comparison only */
469 :
470 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
471 :
472 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
473 : CH_UTF8, CH_UTF16LE,
474 : gd_utf8_terminated.data, -1,
475 : (void *)gd_output.data, gd_output.length, &gd_output.length),
476 : "conversion from UTF8 to UTF16LE null terminated");
477 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated early");
478 :
479 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
480 :
481 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
482 : CH_UTF16LE, CH_UTF8,
483 : gd_utf16le_terminated.data, -1,
484 : (void *)gd_output.data, gd_output.length, &gd_output.length),
485 : "conversion from UTF16LE to UTF8 null terminated");
486 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated early");
487 :
488 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
489 :
490 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
491 : CH_DOS, CH_UTF16LE,
492 : gd_cp850_terminated.data, -1,
493 : (void *)gd_output.data, gd_output.length, &gd_output.length),
494 : "conversion from CP850 to UTF16LE null terminated");
495 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated early");
496 :
497 0 : gd_output = data_blob_talloc(tctx, NULL, gd_cp850.length + 10);
498 :
499 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
500 : CH_UTF16LE, CH_DOS,
501 : gd_utf16le_terminated.data, -1,
502 : (void *)gd_output.data, gd_output.length, &gd_output.length),
503 : "conversion from UTF16LE to UTF8 null terminated");
504 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_cp850_terminated, "conversion from UTF16LE to UTF8 null terminated early");
505 :
506 : /* Now null terminate the string particularly early, the confirm we don't skip the NULL and convert any further */
507 0 : gd_utf8_terminated.data[1] = '\0';
508 0 : gd_utf8_terminated.length = 2; /* used for the comparison only */
509 :
510 0 : gd_utf16le_terminated.data[2] = '\0';
511 0 : gd_utf16le_terminated.data[3] = '\0';
512 0 : gd_utf16le_terminated.length = 4; /* used for the comparison only */
513 :
514 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf16le.length + 10);
515 :
516 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle, CH_UTF8, CH_UTF16LE,
517 : gd_utf8_terminated.data, -1,
518 : (void *)gd_output.data, gd_output.length, &gd_output.length),
519 : "conversion from UTF8 to UTF16LE null terminated");
520 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated very early");
521 :
522 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length + 10);
523 :
524 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
525 : CH_UTF16LE, CH_UTF8,
526 : gd_utf16le_terminated.data, -1,
527 : (void *)gd_output.data, gd_output.length, &gd_output.length),
528 : "conversion from UTF16LE to UTF8 null terminated");
529 0 : torture_assert_data_blob_equal(tctx, gd_output, gd_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated very early");
530 :
531 0 : return true;
532 : }
533 :
534 0 : static bool test_gd_ascii_handle(struct torture_context *tctx)
535 : {
536 : struct smb_iconv_handle *iconv_handle;
537 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
538 0 : DATA_BLOB gd_cp850 = base64_decode_data_blob(gd_cp850_base64);
539 0 : DATA_BLOB gd_iso8859_1 = base64_decode_data_blob(gd_iso8859_1_base64);
540 0 : DATA_BLOB gd_utf16le = base64_decode_data_blob(gd_utf16le_base64);
541 : DATA_BLOB gd_output;
542 :
543 0 : talloc_steal(tctx, gd_utf8.data);
544 0 : talloc_steal(tctx, gd_cp850.data);
545 0 : talloc_steal(tctx, gd_iso8859_1.data);
546 0 : talloc_steal(tctx, gd_utf16le.data);
547 :
548 0 : iconv_handle = get_iconv_testing_handle(tctx, "ASCII", "UTF8",
549 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
550 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
551 :
552 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
553 : CH_UTF8, CH_DOS,
554 : gd_utf8.data, gd_utf8.length,
555 : (void *)&gd_output.data, &gd_output.length) == false,
556 : "conversion from UTF8 to (dos charset) ASCII should fail");
557 :
558 0 : gd_output = data_blob_talloc(tctx, NULL, gd_utf8.length);
559 :
560 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
561 : CH_UTF8, CH_DOS,
562 : gd_utf8.data, gd_utf8.length,
563 : (void *)gd_output.data, gd_output.length,
564 : &gd_output.length) == false,
565 : "conversion from UTF8 to (dos charset) ASCII should fail");
566 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion from UTF8 to (dos charset) ISO-8859-1 should fail E2BIG");
567 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
568 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "partial conversion from UTF8 to (dos charset) ASCII incorrect");
569 :
570 : /* Short output handling confirmation */
571 0 : gd_output.length = 1;
572 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
573 : CH_UTF8, CH_DOS,
574 : gd_utf8.data, gd_utf8.length,
575 : (void *)gd_output.data, gd_output.length,
576 : &gd_output.length) == false,
577 : "conversion from UTF8 to (dos charset) ASCII should fail due to too short");
578 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to (dos charset) ASCII too short");
579 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
580 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "conversion from UTF8 to (dos charset) ASCII incorrect");
581 :
582 : /* Short output handling confirmation */
583 0 : gd_output.length = 2;
584 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
585 : CH_UTF8, CH_DOS,
586 : gd_utf8.data, gd_utf8.length,
587 : (void *)gd_output.data, gd_output.length,
588 : &gd_output.length) == false,
589 : "conversion from UTF8 to (dos charset) ASCII should fail due to too illigal seqence");
590 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion from UTF8 to (dos charset) ISO-8859-1 should fail EILSEQ");
591 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 2 char of output");
592 :
593 : /* Short input handling confirmation */
594 0 : gd_output.length = gd_utf8.length;
595 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
596 : CH_UTF8, CH_DOS,
597 : gd_utf8.data, 2,
598 : (void *)gd_output.data, gd_output.length,
599 : &gd_output.length) == false,
600 : "conversion from UTF8 to (dos charset) ASCII should fail due to too short");
601 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion from short UTF8 to (dos charset) ASCII should fail EILSEQ");
602 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
603 0 : return true;
604 : }
605 :
606 0 : static bool test_plato_english_iso8859_cp850_handle(struct torture_context *tctx)
607 : {
608 : struct smb_iconv_handle *iconv_handle;
609 0 : DATA_BLOB plato_english_utf8 = data_blob_string_const(plato_english_ascii);
610 0 : DATA_BLOB plato_english_cp850 = plato_english_utf8;
611 0 : DATA_BLOB plato_english_iso8859_1 = plato_english_utf8;
612 0 : DATA_BLOB plato_english_utf16le = base64_decode_data_blob(plato_english_utf16le_base64);
613 : DATA_BLOB plato_english_output;
614 : DATA_BLOB plato_english_output2;
615 :
616 0 : talloc_steal(tctx, plato_english_utf16le.data);
617 :
618 0 : iconv_handle = get_iconv_testing_handle(tctx, "ISO-8859-1", "CP850",
619 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
620 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
621 :
622 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
623 : CH_UTF8, CH_DOS,
624 : plato_english_utf8.data, plato_english_utf8.length,
625 : (void *)&plato_english_output.data, &plato_english_output.length),
626 : "conversion from UTF8 to (dos charset) ISO-8859-1");
627 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_iso8859_1, "conversion from UTF8 to (dos charset) ISO-8859-1 incorrect");
628 :
629 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
630 : CH_UTF8, CH_UNIX,
631 : plato_english_utf8.data, plato_english_utf8.length,
632 : (void *)&plato_english_output.data, &plato_english_output.length),
633 : "conversion from UTF8 to (unix charset) CP850");
634 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_cp850, "conversion from UTF8 to (unix charset) CP850 incorrect");
635 :
636 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
637 : CH_UTF8, CH_UTF8,
638 : plato_english_utf8.data, plato_english_utf8.length,
639 : (void *)&plato_english_output.data, &plato_english_output.length),
640 : "conversion from UTF8 to UTF8");
641 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF8 to UTF8 incorrect");
642 :
643 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
644 : CH_UTF16LE, CH_DOS,
645 : plato_english_utf16le.data, plato_english_utf16le.length,
646 : (void *)&plato_english_output.data, &plato_english_output.length),
647 : "conversion from UTF16LE to (dos charset) ISO-8859-1");
648 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_iso8859_1, "conversion from UTF16LE to (dos charset) ISO-8859-1 incorrect");
649 :
650 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
651 : CH_DOS, CH_UTF16LE,
652 : plato_english_output.data, plato_english_output.length,
653 : (void *)&plato_english_output2.data, &plato_english_output2.length),
654 : "round trip conversion from (dos charset) ISO-8859-1 back to UTF16LE");
655 0 : torture_assert_data_blob_equal(tctx, plato_english_output2, plato_english_utf16le, "round trip conversion from (dos charset) ISO-8859-1 back to UTF16LE");
656 :
657 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
658 : CH_UTF16LE, CH_UTF8,
659 : plato_english_utf16le.data, plato_english_utf16le.length,
660 : (void *)&plato_english_output.data, &plato_english_output.length),
661 : "conversion from UTF16LE to UTF8");
662 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF16LE to UTF8 incorrect");
663 :
664 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
665 : CH_UTF16LE, CH_UTF8,
666 : plato_english_utf16le.data, plato_english_utf16le.length,
667 : (void *)plato_english_output.data, plato_english_output.length,
668 : &plato_english_output.length),
669 : "conversion from UTF16LE to UTF8");
670 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF16LE to UTF8 incorrect");
671 :
672 0 : plato_english_output.length = 5;
673 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
674 : CH_UTF16LE, CH_UTF8,
675 : plato_english_utf16le.data, plato_english_utf16le.length,
676 : (void *)plato_english_output.data, plato_english_output.length,
677 : &plato_english_output.length) == false,
678 : "conversion from UTF16LE to UTF8 should fail due to short output");
679 0 : torture_assert_data_blob_equal(tctx, plato_english_output, data_blob_string_const("What "), "conversion from UTF16LE to UTF8 incorrect");
680 0 : torture_assert_int_equal(tctx, plato_english_output.length, 5, "short conversion failed");
681 :
682 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
683 : CH_UTF16LE, CH_UNIX,
684 : plato_english_utf16le.data, plato_english_utf16le.length,
685 : (void *)&plato_english_output.data, &plato_english_output.length),
686 : "conversion from UTF16LE to (unix charset) CP850");
687 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_cp850, "conversion from UTF16LE to (unix charset) CP850 incorrect");
688 :
689 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
690 : CH_UTF16LE, CH_UTF8,
691 : plato_english_utf16le.data, plato_english_utf16le.length,
692 : (void *)&plato_english_output.data, &plato_english_output.length),
693 : "conversion from UTF16LE to UTF8");
694 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF16LE to UTF8 incorrect");
695 :
696 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
697 : CH_DOS, CH_DOS,
698 : plato_english_iso8859_1.data, plato_english_iso8859_1.length,
699 : (void *)&plato_english_output.data, &plato_english_output.length),
700 : "conversion from (dos charset) ISO-8859-1 to (dos charset) ISO-8859-1");
701 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_iso8859_1, "conversion from UTF16LE to (dos charset) ISO-8859-1 incorrect");
702 :
703 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
704 : CH_DOS, CH_UNIX,
705 : plato_english_iso8859_1.data, plato_english_iso8859_1.length,
706 : (void *)&plato_english_output.data, &plato_english_output.length),
707 : "conversion from (dos charset) ISO-8859-1 to (unix charset) CP850");
708 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_cp850, "conversion from UTF16LE to (unix charset) CP850 incorrect");
709 :
710 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
711 : CH_DOS, CH_UTF8,
712 : plato_english_iso8859_1.data, plato_english_iso8859_1.length,
713 : (void *)&plato_english_output.data, &plato_english_output.length),
714 : "conversion from (dos charset) ISO-8859-1 to UTF8");
715 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF16LE to UTF8 incorrect");
716 :
717 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
718 : CH_DOS, CH_UTF16LE,
719 : plato_english_iso8859_1.data, plato_english_iso8859_1.length,
720 : (void *)&plato_english_output.data, &plato_english_output.length),
721 : "conversion from (dos charset) ISO-8859-1 to UTF16LE");
722 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf16le, "conversion from (dos charset) ISO-8859-1 to UTF16LE");
723 0 : return true;
724 : }
725 :
726 0 : static bool test_plato_english_minus_1_handle(struct torture_context *tctx)
727 : {
728 : struct smb_iconv_handle *iconv_handle;
729 0 : DATA_BLOB plato_english_utf8 = data_blob_string_const(plato_english_ascii);
730 0 : DATA_BLOB plato_english_utf16le = base64_decode_data_blob(plato_english_utf16le_base64);
731 : DATA_BLOB plato_english_output;
732 : DATA_BLOB plato_english_utf8_terminated;
733 : DATA_BLOB plato_english_utf16le_terminated;
734 :
735 0 : talloc_steal(tctx, plato_english_utf16le.data);
736 :
737 0 : iconv_handle = get_iconv_testing_handle(tctx, "ISO-8859-1", "CP850",
738 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
739 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
740 :
741 0 : plato_english_utf8_terminated = data_blob_talloc(tctx, NULL, plato_english_utf8.length + 1);
742 0 : memcpy(plato_english_utf8_terminated.data, plato_english_utf8.data, plato_english_utf8.length);
743 0 : plato_english_utf8_terminated.data[plato_english_utf8.length] = '\0';
744 :
745 0 : plato_english_utf16le_terminated = data_blob_talloc(tctx, NULL, plato_english_utf16le.length + 2);
746 0 : memcpy(plato_english_utf16le_terminated.data, plato_english_utf16le.data, plato_english_utf16le.length);
747 0 : plato_english_utf16le_terminated.data[plato_english_utf16le.length] = '\0';
748 0 : plato_english_utf16le_terminated.data[plato_english_utf16le.length + 1] = '\0';
749 :
750 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf16le.length + 10);
751 :
752 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
753 : CH_UTF8, CH_UTF16LE,
754 : plato_english_utf8_terminated.data, -1,
755 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
756 : "conversion from UTF8 to UTF16LE null terminated");
757 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated");
758 :
759 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
760 : CH_UTF8, CH_UTF16LE,
761 : plato_english_utf8_terminated.data, -1,
762 : (void *)plato_english_output.data, plato_english_utf16le.length, &plato_english_output.length) == false,
763 : "conversion from UTF8 to UTF16LE null terminated should fail");
764 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
765 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf16le, "conversion from UTF8 to UTF16LE null terminated");
766 :
767 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
768 : CH_UTF8, CH_UTF16LE,
769 : plato_english_utf8_terminated.data, -1,
770 : (void *)plato_english_output.data, plato_english_utf16le.length - 1, &plato_english_output.length) == false,
771 : "conversion from UTF8 to UTF16LE null terminated should fail");
772 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
773 :
774 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
775 : CH_UTF8, CH_UTF16LE,
776 : plato_english_utf8_terminated.data, -1,
777 : (void *)plato_english_output.data, plato_english_utf16le.length - 2, &plato_english_output.length) == false,
778 : "conversion from UTF8 to UTF16LE null terminated should fail");
779 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
780 :
781 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf8.length + 10);
782 :
783 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
784 : CH_UTF16LE, CH_UTF8,
785 : plato_english_utf16le_terminated.data, -1,
786 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
787 : "conversion from UTF16LE to UTF8 null terminated");
788 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated");
789 :
790 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
791 : CH_UTF16LE, CH_UTF8,
792 : plato_english_utf16le_terminated.data, -1,
793 : (void *)plato_english_output.data, plato_english_utf8.length, &plato_english_output.length) == false,
794 : "conversion from UTF16LE to UTF8 null terminated should fail");
795 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
796 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8, "conversion from UTF16LE to UTF8 null terminated");
797 :
798 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
799 : CH_UTF16LE, CH_UTF8,
800 : plato_english_utf16le_terminated.data, -1,
801 : (void *)plato_english_output.data, plato_english_utf8.length - 1, &plato_english_output.length) == false,
802 : "conversion from UTF16LE to UTF8 null terminated should fail");
803 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
804 :
805 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
806 : CH_UTF16LE, CH_UTF8,
807 : plato_english_utf16le_terminated.data, -1,
808 : (void *)plato_english_output.data, plato_english_utf8.length - 2, &plato_english_output.length) == false,
809 : "conversion from UTF16LE to UTF8 null terminated should fail");
810 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
811 :
812 : /* Now null terminate the string early, the confirm we don't skip the NULL and convert any further */
813 0 : plato_english_utf8_terminated.data[3] = '\0';
814 0 : plato_english_utf8_terminated.length = 4; /* used for the comparison only */
815 :
816 0 : plato_english_utf16le_terminated.data[6] = '\0';
817 0 : plato_english_utf16le_terminated.data[7] = '\0';
818 0 : plato_english_utf16le_terminated.length = 8; /* used for the comparison only */
819 :
820 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf16le.length + 10);
821 :
822 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
823 : CH_UTF8, CH_UTF16LE,
824 : plato_english_utf8_terminated.data, -1,
825 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
826 : "conversion from UTF8 to UTF16LE null terminated");
827 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated early");
828 :
829 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf8.length + 10);
830 :
831 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
832 : CH_UTF16LE, CH_UTF8,
833 : plato_english_utf16le_terminated.data, -1,
834 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
835 : "conversion from UTF16LE to UTF8 null terminated");
836 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated early");
837 :
838 :
839 : /* Now null terminate the string particularly early, the confirm we don't skip the NULL and convert any further */
840 0 : plato_english_utf8_terminated.data[1] = '\0';
841 0 : plato_english_utf8_terminated.length = 2; /* used for the comparison only */
842 :
843 0 : plato_english_utf16le_terminated.data[2] = '\0';
844 0 : plato_english_utf16le_terminated.data[3] = '\0';
845 0 : plato_english_utf16le_terminated.length = 4; /* used for the comparison only */
846 :
847 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf16le.length + 10);
848 :
849 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle, CH_UTF8, CH_UTF16LE,
850 : plato_english_utf8_terminated.data, -1,
851 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
852 : "conversion from UTF8 to UTF16LE null terminated");
853 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated very early");
854 :
855 0 : plato_english_output = data_blob_talloc(tctx, NULL, plato_english_utf8.length + 10);
856 :
857 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
858 : CH_UTF16LE, CH_UTF8,
859 : plato_english_utf16le_terminated.data, -1,
860 : (void *)plato_english_output.data, plato_english_output.length, &plato_english_output.length),
861 : "conversion from UTF16LE to UTF8 null terminated");
862 0 : torture_assert_data_blob_equal(tctx, plato_english_output, plato_english_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated very early");
863 :
864 0 : return true;
865 : }
866 :
867 0 : static bool test_plato_minus_1_handle(struct torture_context *tctx)
868 : {
869 : struct smb_iconv_handle *iconv_handle;
870 0 : DATA_BLOB plato_utf8 = base64_decode_data_blob(plato_utf8_base64);
871 0 : DATA_BLOB plato_utf16le = base64_decode_data_blob(plato_utf16le_base64);
872 : DATA_BLOB plato_output;
873 : DATA_BLOB plato_utf8_terminated;
874 : DATA_BLOB plato_utf16le_terminated;
875 :
876 0 : talloc_steal(tctx, plato_utf8.data);
877 0 : talloc_steal(tctx, plato_utf16le.data);
878 :
879 0 : iconv_handle = get_iconv_testing_handle(tctx, "ISO-8859-1", "CP850",
880 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
881 0 : torture_assert(tctx, iconv_handle, "getting iconv handle");
882 :
883 0 : plato_utf8_terminated = data_blob_talloc(tctx, NULL, plato_utf8.length + 1);
884 0 : memcpy(plato_utf8_terminated.data, plato_utf8.data, plato_utf8.length);
885 0 : plato_utf8_terminated.data[plato_utf8.length] = '\0';
886 :
887 0 : plato_utf16le_terminated = data_blob_talloc(tctx, NULL, plato_utf16le.length + 2);
888 0 : memcpy(plato_utf16le_terminated.data, plato_utf16le.data, plato_utf16le.length);
889 0 : plato_utf16le_terminated.data[plato_utf16le.length] = '\0';
890 0 : plato_utf16le_terminated.data[plato_utf16le.length + 1] = '\0';
891 :
892 0 : plato_output = data_blob_talloc(tctx, NULL, plato_utf16le.length + 10);
893 :
894 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
895 : CH_UTF8, CH_UTF16LE,
896 : plato_utf8_terminated.data, -1,
897 : (void *)plato_output.data, plato_output.length, &plato_output.length),
898 : "conversion from UTF8 to UTF16LE null terminated");
899 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated");
900 :
901 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
902 : CH_UTF8, CH_UTF16LE,
903 : plato_utf8_terminated.data, -1,
904 : (void *)plato_output.data, plato_utf16le.length, &plato_output.length) == false,
905 : "conversion from UTF8 to UTF16LE null terminated should fail");
906 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
907 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le, "conversion from UTF8 to UTF16LE null terminated");
908 :
909 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
910 : CH_UTF8, CH_UTF16LE,
911 : plato_utf8_terminated.data, -1,
912 : (void *)plato_output.data, plato_utf16le.length - 1, &plato_output.length) == false,
913 : "conversion from UTF8 to UTF16LE null terminated should fail");
914 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
915 :
916 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
917 : CH_UTF8, CH_UTF16LE,
918 : plato_utf8_terminated.data, -1,
919 : (void *)plato_output.data, plato_utf16le.length - 2, &plato_output.length) == false,
920 : "conversion from UTF8 to UTF16LE null terminated should fail");
921 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to UTF16LE should fail E2BIG");
922 :
923 0 : plato_output = data_blob_talloc(tctx, NULL, plato_utf8.length + 10);
924 :
925 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
926 : CH_UTF16LE, CH_UTF8,
927 : plato_utf16le_terminated.data, -1,
928 : (void *)plato_output.data, plato_output.length, &plato_output.length),
929 : "conversion from UTF16LE to UTF8 null terminated");
930 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated");
931 :
932 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
933 : CH_UTF16LE, CH_UTF8,
934 : plato_utf16le_terminated.data, -1,
935 : (void *)plato_output.data, plato_utf8.length, &plato_output.length) == false,
936 : "conversion from UTF16LE to UTF8 null terminated should fail");
937 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
938 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF16LE to UTF8 null terminated");
939 :
940 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
941 : CH_UTF16LE, CH_UTF8,
942 : plato_utf16le_terminated.data, -1,
943 : (void *)plato_output.data, plato_utf8.length - 1, &plato_output.length) == false,
944 : "conversion from UTF16LE to UTF8 null terminated should fail");
945 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
946 :
947 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
948 : CH_UTF16LE, CH_UTF8,
949 : plato_utf16le_terminated.data, -1,
950 : (void *)plato_output.data, plato_utf8.length - 2, &plato_output.length) == false,
951 : "conversion from UTF16LE to UTF8 null terminated should fail");
952 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16LE to UTF8 should fail E2BIG");
953 :
954 : /* Now null terminate the string early, the confirm we don't skip the NULL and convert any further */
955 0 : plato_utf8_terminated.data[5] = '\0';
956 0 : plato_utf8_terminated.length = 6; /* used for the comparison only */
957 :
958 0 : plato_utf16le_terminated.data[4] = '\0';
959 0 : plato_utf16le_terminated.data[5] = '\0';
960 0 : plato_utf16le_terminated.length = 6; /* used for the comparison only */
961 :
962 0 : plato_output = data_blob_talloc(tctx, NULL, plato_utf16le.length + 10);
963 :
964 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
965 : CH_UTF8, CH_UTF16LE,
966 : plato_utf8_terminated.data, -1,
967 : (void *)plato_output.data, plato_output.length, &plato_output.length),
968 : "conversion from UTF8 to UTF16LE null terminated");
969 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le_terminated, "conversion from UTF8 to UTF16LE null terminated early");
970 :
971 0 : plato_output = data_blob_talloc(tctx, NULL, plato_utf8.length + 10);
972 :
973 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
974 : CH_UTF16LE, CH_UTF8,
975 : plato_utf16le_terminated.data, -1,
976 : (void *)plato_output.data, plato_output.length, &plato_output.length),
977 : "conversion from UTF16LE to UTF8 null terminated");
978 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8_terminated, "conversion from UTF16LE to UTF8 null terminated early");
979 :
980 0 : return true;
981 : }
982 :
983 0 : static bool test_plato_cp850_utf8_handle(struct torture_context *tctx)
984 : {
985 : struct smb_iconv_handle *iconv_handle;
986 0 : DATA_BLOB plato_utf8 = base64_decode_data_blob(plato_utf8_base64);
987 0 : DATA_BLOB plato_utf16le = base64_decode_data_blob(plato_utf16le_base64);
988 : DATA_BLOB plato_output;
989 : DATA_BLOB plato_output2;
990 :
991 0 : talloc_steal(tctx, plato_utf8.data);
992 0 : talloc_steal(tctx, plato_utf16le.data);
993 :
994 0 : iconv_handle = get_iconv_testing_handle(tctx, "CP850", "UTF8",
995 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
996 0 : torture_assert(tctx, iconv_handle, "creating iconv handle");
997 :
998 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
999 : CH_UTF8, CH_UTF16LE,
1000 : plato_utf8.data, plato_utf8.length,
1001 : (void *)&plato_output.data, &plato_output.length),
1002 : "conversion of UTF8 ancient greek to UTF16 failed");
1003 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le, "conversion from UTF8 to UTF16LE incorrect");
1004 :
1005 0 : torture_assert_int_equal(tctx,
1006 : strlen_m_ext_handle(iconv_handle,
1007 : (const char *)plato_utf8.data,
1008 : CH_UTF8, CH_UTF16LE),
1009 : plato_output.length / 2,
1010 : "checking strlen_m_ext of conversion of UTF8 to UTF16LE");
1011 :
1012 0 : memset(plato_output.data, '\0', plato_output.length);
1013 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1014 : CH_UTF8, CH_UTF16LE,
1015 : plato_utf8.data, plato_utf8.length,
1016 : (void *)plato_output.data, plato_output.length,
1017 : &plato_output.length),
1018 : "conversion of UTF8 ancient greek to UTF16 failed");
1019 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le, "conversion from UTF8 to UTF16LE incorrect");
1020 :
1021 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1022 : CH_UTF16LE, CH_UTF8,
1023 : plato_output.data, plato_output.length,
1024 : (void *)&plato_output2.data, &plato_output2.length),
1025 : "conversion of UTF8 ancient greek to UTF16 failed");
1026 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf8, "conversion from UTF8 to UTF16LE incorrect");
1027 :
1028 0 : memset(plato_output2.data, '\0', plato_output2.length);
1029 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1030 : CH_UTF16LE, CH_UTF8,
1031 : plato_output.data, plato_output.length,
1032 : (void *)plato_output2.data, plato_output2.length, &plato_output2.length),
1033 : "conversion of UTF8 ancient greek to UTF16 failed");
1034 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf8, "conversion from UTF8 to UTF16LE incorrect");
1035 :
1036 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1037 : CH_UTF8, CH_UTF8,
1038 : plato_utf8.data, plato_utf8.length,
1039 : (void *)&plato_output.data, &plato_output.length),
1040 : "conversion of UTF8 to UTF8");
1041 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8,
1042 : "conversion of UTF8 to UTF8");
1043 0 : torture_assert_int_equal(tctx,
1044 : strlen_m_ext_handle(iconv_handle,
1045 : (const char *)plato_utf8.data,
1046 : CH_UTF8, CH_UTF8),
1047 : plato_output.length,
1048 : "checking strlen_m_ext of conversion of UTF8 to UTF8");
1049 0 : memset(plato_output.data, '\0', plato_output.length);
1050 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1051 : CH_UTF8, CH_UTF8,
1052 : plato_utf8.data, plato_utf8.length,
1053 : (void *)plato_output.data, plato_output.length,
1054 : &plato_output.length),
1055 : "conversion of UTF8 to UTF8");
1056 :
1057 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1058 : CH_UTF8, CH_DOS,
1059 : plato_utf8.data, plato_utf8.length,
1060 : (void *)&plato_output.data, &plato_output.length) == false,
1061 : "conversion of UTF8 ancient greek to DOS charset CP850 should fail");
1062 :
1063 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1064 : CH_UTF8, CH_UNIX,
1065 : plato_utf8.data, plato_utf8.length,
1066 : (void *)&plato_output.data, &plato_output.length),
1067 : "conversion of UTF16 ancient greek to unix charset UTF8 failed");
1068 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF8 to (unix charset) UTF8 incorrect");
1069 :
1070 0 : memset(plato_output.data, '\0', plato_output.length);
1071 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1072 : CH_UTF8, CH_UNIX,
1073 : plato_utf8.data, plato_utf8.length,
1074 : (void *)plato_output.data, plato_output.length,
1075 : &plato_output.length),
1076 : "conversion of UTF16 ancient greek to unix charset UTF8 failed");
1077 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF8 to (unix charset) UTF8 incorrect");
1078 :
1079 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1080 : CH_UTF8, CH_UTF8,
1081 : plato_utf8.data, plato_utf8.length,
1082 : (void *)&plato_output.data, &plato_output.length),
1083 : "conversion of UTF16 ancient greek to unix charset UTF8 failed");
1084 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF8 to UTF8 incorrect");
1085 :
1086 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1087 : CH_UTF16LE, CH_DOS,
1088 : plato_utf16le.data, plato_utf16le.length,
1089 : (void *)&plato_output.data, &plato_output.length) == false,
1090 : "conversion of UTF16 ancient greek to DOS charset CP850 should fail");
1091 :
1092 : /* Allocate enough space, if it were possible do do the conversion */
1093 0 : plato_output = data_blob_talloc(tctx, NULL, plato_utf16le.length);
1094 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1095 : CH_UTF16LE, CH_DOS,
1096 : plato_utf16le.data, plato_utf16le.length,
1097 : (void *)plato_output.data, plato_output.length,
1098 : &plato_output.length) == false,
1099 : "conversion of UTF16 ancient greek to DOS charset CP850 should fail");
1100 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion of UTF16 ancient greek to DOS charset CP850 should fail");
1101 :
1102 : /* Allocate only enough space for a partial conversion */
1103 0 : plato_output = data_blob_talloc(tctx, NULL, 9);
1104 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1105 : CH_UTF16LE, CH_UTF8,
1106 : plato_utf16le.data, plato_utf16le.length,
1107 : (void *)plato_output.data, plato_output.length,
1108 : &plato_output.length) == false,
1109 : "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1110 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1111 0 : torture_assert_int_equal(tctx, plato_output.length, 8,
1112 : "conversion of UTF16 ancient greek to UTF8 should stop on multibyte boundary");
1113 :
1114 0 : plato_output = data_blob_talloc(tctx, NULL, 2);
1115 0 : torture_assert(tctx, convert_string_error_handle(iconv_handle,
1116 : CH_UTF16LE, CH_UTF8,
1117 : plato_utf16le.data, plato_utf16le.length,
1118 : (void *)plato_output.data, plato_output.length,
1119 : &plato_output.length) == false,
1120 : "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1121 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1122 0 : torture_assert_int_equal(tctx, plato_output.length, 0,
1123 : "conversion of UTF16 ancient greek to UTF8 should stop on multibyte boundary");
1124 :
1125 :
1126 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1127 : CH_UTF16LE, CH_UNIX,
1128 : plato_utf16le.data, plato_utf16le.length,
1129 : (void *)&plato_output.data, &plato_output.length),
1130 : "conversion of UTF16 ancient greek to unix charset UTF8 failed");
1131 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF16LE to (unix charset) UTF8 incorrect");
1132 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1133 : CH_UTF16LE, CH_UTF8,
1134 : plato_utf16le.data, plato_utf16le.length,
1135 : (void *)&plato_output.data, &plato_output.length),
1136 : "conversion of UTF16 ancient greek to UTF8 failed");
1137 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF16LE to UTF8 incorrect");
1138 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1139 : CH_UTF16LE, CH_UTF8,
1140 : plato_utf16le.data, plato_utf16le.length,
1141 : (void *)&plato_output.data, &plato_output.length),
1142 : "conversion of UTF16 ancient greek to UTF8 failed");
1143 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8, "conversion from UTF16LE to UTF8 incorrect");
1144 :
1145 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1146 : CH_UTF8, CH_UTF16LE,
1147 : plato_output.data, plato_output.length,
1148 : (void *)&plato_output2.data, &plato_output2.length),
1149 : "round trip conversion of UTF16 ancient greek to UTF8 and back again failed");
1150 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf16le,
1151 : "round trip conversion of UTF16 ancient greek to UTF8 and back again failed");
1152 0 : torture_assert_int_equal(tctx,
1153 : strlen_m_ext_handle(iconv_handle,
1154 : (const char *)plato_output.data,
1155 : CH_UTF8, CH_UTF16LE),
1156 : plato_output2.length / 2,
1157 : "checking strlen_m_ext of round trip conversion of UTF16 latin charset greek to UTF8 and back again");
1158 :
1159 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1160 : CH_UTF8, CH_UTF8,
1161 : plato_output.data, plato_output.length,
1162 : (void *)&plato_output2.data, &plato_output2.length),
1163 : "conversion of UTF8 to UTF8");
1164 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf8,
1165 : "conversion of UTF8 to UTF8");
1166 0 : torture_assert_int_equal(tctx,
1167 : strlen_m_ext_handle(iconv_handle,
1168 : (const char *)plato_output.data,
1169 : CH_UTF8, CH_UTF8),
1170 : plato_output2.length,
1171 : "checking strlen_m_ext of conversion of UTF8 to UTF8");
1172 0 : return true;
1173 : }
1174 :
1175 0 : static bool test_plato_latin_cp850_utf8_handle(struct torture_context *tctx)
1176 : {
1177 : struct smb_iconv_handle *iconv_handle;
1178 0 : DATA_BLOB plato_latin_utf8 = base64_decode_data_blob(plato_latin_utf8_base64);
1179 0 : DATA_BLOB plato_latin_utf16le = base64_decode_data_blob(plato_latin_utf16le_base64);
1180 : DATA_BLOB plato_latin_output;
1181 : DATA_BLOB plato_latin_output2;
1182 :
1183 0 : talloc_steal(tctx, plato_latin_utf8.data);
1184 0 : talloc_steal(tctx, plato_latin_utf16le.data);
1185 :
1186 0 : iconv_handle = get_iconv_testing_handle(tctx, "CP850", "UTF8",
1187 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
1188 0 : torture_assert(tctx, iconv_handle, "creating iconv handle");
1189 :
1190 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1191 : CH_UTF8, CH_DOS,
1192 : plato_latin_utf8.data, plato_latin_utf8.length,
1193 : (void *)&plato_latin_output.data, &plato_latin_output.length) == false,
1194 : "conversion of UTF8 latin charset greek to DOS charset CP850 should fail");
1195 :
1196 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1197 : CH_UTF8, CH_UNIX,
1198 : plato_latin_utf8.data, plato_latin_utf8.length,
1199 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1200 : "conversion of UTF16 latin charset greek to unix charset UTF8 failed");
1201 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf8, "conversion from UTF8 to (unix charset) UTF8 incorrect");
1202 :
1203 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1204 : CH_UTF8, CH_UTF8,
1205 : plato_latin_utf8.data, plato_latin_utf8.length,
1206 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1207 : "conversion of UTF16 latin charset greek to unix charset UTF8 failed");
1208 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf8, "conversion from UTF8 to UTF8 incorrect");
1209 :
1210 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1211 : CH_UTF16LE, CH_DOS,
1212 : plato_latin_utf16le.data, plato_latin_utf16le.length,
1213 : (void *)&plato_latin_output.data, &plato_latin_output.length) == false,
1214 : "conversion of UTF16 latin charset greek to DOS charset CP850 should fail");
1215 :
1216 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1217 : CH_UTF16LE, CH_UNIX,
1218 : plato_latin_utf16le.data, plato_latin_utf16le.length,
1219 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1220 : "conversion of UTF16 latin charset greek to unix charset UTF8 failed");
1221 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf8, "conversion from UTF16LE to (unix charset) CP850 incorrect");
1222 :
1223 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1224 : CH_UTF16LE, CH_UTF8,
1225 : plato_latin_utf16le.data, plato_latin_utf16le.length,
1226 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1227 : "conversion of UTF16 latin charset greek to UTF8 failed");
1228 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf8, "conversion from UTF16LE to UTF8 incorrect");
1229 :
1230 0 : torture_assert(tctx, convert_string_talloc_handle(tctx, iconv_handle,
1231 : CH_UTF8, CH_UTF16LE,
1232 : plato_latin_output.data, plato_latin_output.length,
1233 : (void *)&plato_latin_output2.data, &plato_latin_output2.length),
1234 : "round trip conversion of UTF16 latin charset greek to UTF8 and back again failed");
1235 0 : torture_assert_data_blob_equal(tctx, plato_latin_output2, plato_latin_utf16le,
1236 : "round trip conversion of UTF16 latin charset greek to UTF8 and back again failed");
1237 0 : torture_assert_int_equal(tctx,
1238 : strlen_m_ext_handle(iconv_handle,
1239 : (const char *)plato_latin_output.data,
1240 : CH_UTF8, CH_UTF16LE),
1241 : plato_latin_output2.length / 2,
1242 : "checking strlen_m_ext of round trip conversion of UTF16 latin charset greek to UTF8 and back again");
1243 0 : return true;
1244 : }
1245 :
1246 0 : static bool test_utf8_nfc_to_nfd_overflow(struct torture_context *tctx)
1247 : {
1248 : smb_iconv_t ic;
1249 : DATA_BLOB utf8_nfc_blob;
1250 : DATA_BLOB utf8_nfd_blob;
1251 : DATA_BLOB src_blob;
1252 : DATA_BLOB blob;
1253 : size_t nconv;
1254 0 : const char *src = NULL;
1255 0 : char *dst = NULL;
1256 : size_t dst_left;
1257 : size_t srclen;
1258 0 : bool ret = true;
1259 :
1260 0 : ic = smb_iconv_open("UTF8-NFD", "UTF8-NFC");
1261 0 : torture_assert_goto(tctx, ic != (smb_iconv_t)-1, ret, done,
1262 : "creating iconv handle\n");
1263 :
1264 0 : utf8_nfc_blob = base64_decode_data_blob_talloc(tctx, utf8_nfc_base64);
1265 0 : torture_assert_not_null_goto(tctx, utf8_nfc_blob.data, ret, done,
1266 : "OOM\n");
1267 :
1268 0 : utf8_nfd_blob = base64_decode_data_blob_talloc(tctx, utf8_nfd_base64);
1269 0 : torture_assert_not_null_goto(tctx, utf8_nfd_blob.data, ret, done,
1270 : "OOM\n");
1271 :
1272 0 : blob = data_blob_talloc_zero(tctx, 255);
1273 0 : torture_assert_not_null_goto(tctx, blob.data, ret, done, "OOM\n");
1274 :
1275 : /*
1276 : * Unfortunately the current implementation that performs the conversion
1277 : * (using libicu) returns EINVAL if the result buffer is too small, not
1278 : * E2BIG like iconv().
1279 : */
1280 :
1281 0 : src = "foo";
1282 0 : srclen = 3;
1283 0 : dst = (char *)blob.data;
1284 0 : dst_left = 0;
1285 0 : nconv = smb_iconv(ic,
1286 : &src,
1287 : &srclen,
1288 : &dst,
1289 : &dst_left);
1290 0 : torture_assert_int_equal_goto(tctx, nconv, -1, ret, done,
1291 : "smb_iconv failed\n");
1292 0 : torture_assert_errno_equal_goto(tctx, EINVAL, ret, done,
1293 : "Wrong errno\n");
1294 :
1295 0 : src = "foo";
1296 0 : srclen = 3;
1297 0 : dst = (char *)blob.data;
1298 0 : dst_left = 1;
1299 0 : nconv = smb_iconv(ic,
1300 : &src,
1301 : &srclen,
1302 : &dst,
1303 : &dst_left);
1304 0 : torture_assert_int_equal_goto(tctx, nconv, -1, ret, done,
1305 : "smb_iconv failed\n");
1306 0 : torture_assert_errno_equal_goto(tctx, EINVAL, ret, done,
1307 : "Wrong errno\n");
1308 :
1309 0 : src = "foo";
1310 0 : srclen = 3;
1311 0 : dst = (char *)blob.data;
1312 0 : dst_left = 2;
1313 0 : nconv = smb_iconv(ic,
1314 : &src,
1315 : &srclen,
1316 : &dst,
1317 : &dst_left);
1318 0 : torture_assert_int_equal_goto(tctx, nconv, -1, ret, done,
1319 : "smb_iconv failed\n");
1320 0 : torture_assert_errno_equal_goto(tctx, EINVAL, ret, done,
1321 : "Wrong errno\n");
1322 :
1323 0 : src_blob = data_blob_const("foo", 3);
1324 0 : src = (const char *)src_blob.data;
1325 0 : srclen = src_blob.length;
1326 0 : dst = (char *)blob.data;
1327 0 : dst_left = 3;
1328 0 : nconv = smb_iconv(ic,
1329 : &src,
1330 : &srclen,
1331 : &dst,
1332 : &dst_left);
1333 0 : torture_assert_int_equal_goto(tctx, nconv, 3, ret, done,
1334 : "smb_iconv failed\n");
1335 :
1336 0 : blob.length = nconv;
1337 0 : torture_assert_data_blob_equal(tctx,
1338 : src_blob,
1339 : blob,
1340 : "Conversion failed\n");
1341 :
1342 0 : src_blob = data_blob_const("foo", 4);
1343 0 : src = (const char *)src_blob.data;
1344 0 : srclen = src_blob.length;
1345 0 : dst = (char *)blob.data;
1346 0 : dst_left = 4;
1347 0 : nconv = smb_iconv(ic,
1348 : &src,
1349 : &srclen,
1350 : &dst,
1351 : &dst_left);
1352 0 : torture_assert_int_equal_goto(tctx, nconv, 4, ret, done,
1353 : "smb_iconv failed\n");
1354 :
1355 0 : blob.length = nconv;
1356 0 : torture_assert_data_blob_equal(tctx,
1357 : src_blob,
1358 : blob,
1359 : "Conversion failed\n");
1360 :
1361 0 : done:
1362 0 : return ret;
1363 : }
1364 :
1365 0 : static bool test_utf8_nfc_to_nfd(struct torture_context *tctx)
1366 : {
1367 : smb_iconv_t ic;
1368 : DATA_BLOB utf8_nfc_blob;
1369 : DATA_BLOB utf8_nfd_blob;
1370 : DATA_BLOB blob;
1371 : size_t nconv;
1372 0 : const char *src = NULL;
1373 0 : char *dst = NULL;
1374 : size_t dst_left;
1375 : size_t srclen;
1376 0 : bool ret = true;
1377 :
1378 0 : ic = smb_iconv_open("UTF8-NFD", "UTF8-NFC");
1379 0 : torture_assert_goto(tctx, ic != (smb_iconv_t)-1, ret, done,
1380 : "creating iconv handle\n");
1381 :
1382 0 : utf8_nfc_blob = base64_decode_data_blob_talloc(tctx, utf8_nfc_base64);
1383 0 : torture_assert_not_null_goto(tctx, utf8_nfc_blob.data, ret, done,
1384 : "OOM\n");
1385 :
1386 0 : utf8_nfd_blob = base64_decode_data_blob_talloc(tctx, utf8_nfd_base64);
1387 0 : torture_assert_not_null_goto(tctx, utf8_nfd_blob.data, ret, done,
1388 : "OOM\n");
1389 :
1390 0 : blob = data_blob_talloc_zero(tctx, 255);
1391 0 : torture_assert_not_null_goto(tctx, blob.data, ret, done, "OOM\n");
1392 :
1393 0 : dst = (char *)blob.data;
1394 0 : dst_left = blob.length;
1395 0 : src = (const char *)utf8_nfc_blob.data;
1396 0 : srclen = strlen(src);
1397 :
1398 0 : nconv = smb_iconv(ic,
1399 : &src,
1400 : &srclen,
1401 : &dst,
1402 : &dst_left);
1403 0 : torture_assert_goto(tctx, nconv != (size_t)-1, ret, done,
1404 : "smb_iconv failed\n");
1405 :
1406 0 : blob.length = nconv + 1; /* +1 for the trailing zero */
1407 0 : torture_assert_data_blob_equal(tctx,
1408 : blob,
1409 : utf8_nfd_blob,
1410 : "Conversion failed\n");
1411 :
1412 0 : done:
1413 0 : return ret;
1414 : }
1415 :
1416 0 : static bool test_utf8_nfd_to_nfc(struct torture_context *tctx)
1417 : {
1418 : smb_iconv_t ic;
1419 : DATA_BLOB utf8_nfc_blob;
1420 : DATA_BLOB utf8_nfd_blob;
1421 : DATA_BLOB blob;
1422 : size_t nconv;
1423 0 : const char *src = NULL;
1424 0 : char *dst = NULL;
1425 : size_t dst_left;
1426 : size_t srclen;
1427 0 : bool ret = true;
1428 :
1429 0 : ic = smb_iconv_open("UTF8-NFC", "UTF8-NFD");
1430 0 : torture_assert_goto(tctx, ic != (smb_iconv_t)-1, ret, done,
1431 : "creating iconv handle\n");
1432 :
1433 0 : utf8_nfc_blob = base64_decode_data_blob_talloc(tctx, utf8_nfc_base64);
1434 0 : torture_assert_not_null_goto(tctx, utf8_nfc_blob.data, ret, done,
1435 : "OOM\n");
1436 :
1437 0 : utf8_nfd_blob = base64_decode_data_blob_talloc(tctx, utf8_nfd_base64);
1438 0 : torture_assert_not_null_goto(tctx, utf8_nfd_blob.data, ret, done,
1439 : "OOM\n");
1440 :
1441 0 : blob = data_blob_talloc_zero(tctx, 255);
1442 0 : torture_assert_not_null_goto(tctx, blob.data, ret, done, "OOM\n");
1443 :
1444 0 : dst = (char *)blob.data;
1445 0 : dst_left = blob.length;
1446 0 : src = (const char *)utf8_nfd_blob.data;
1447 0 : srclen = strlen(src);
1448 :
1449 0 : nconv = smb_iconv(ic,
1450 : &src,
1451 : &srclen,
1452 : &dst,
1453 : &dst_left);
1454 0 : torture_assert_goto(tctx, nconv != (size_t)-1, ret, done,
1455 : "smb_iconv failed\n");
1456 :
1457 0 : blob.length = nconv + 1; /* +1 for the trailing zero */
1458 0 : torture_assert_data_blob_equal(tctx,
1459 : blob,
1460 : utf8_nfc_blob,
1461 : "Conversion failed\n");
1462 :
1463 0 : done:
1464 0 : return ret;
1465 : }
1466 :
1467 0 : static bool test_gd_case_utf8_handle(struct torture_context *tctx)
1468 : {
1469 : struct smb_iconv_handle *iconv_handle;
1470 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
1471 0 : DATA_BLOB gd_utf8_upper = base64_decode_data_blob(gd_utf8_upper_base64);
1472 0 : DATA_BLOB gd_utf8_lower = base64_decode_data_blob(gd_utf8_lower_base64);
1473 : char *gd_lower, *gd_upper;
1474 0 : talloc_steal(tctx, gd_utf8.data);
1475 :
1476 0 : iconv_handle = get_iconv_testing_handle(tctx, "ASCII", "UTF8",
1477 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
1478 0 : torture_assert(tctx, iconv_handle, "getting utf8 iconv handle");
1479 :
1480 0 : torture_assert(tctx,
1481 : strhasupper_handle(iconv_handle, (const char *)gd_utf8.data),
1482 : "GD's name has an upper case character");
1483 0 : torture_assert(tctx,
1484 : strhaslower_handle(iconv_handle, (const char *)gd_utf8.data),
1485 : "GD's name has an lower case character");
1486 0 : gd_lower = strlower_talloc_handle(iconv_handle, tctx, (const char *)gd_utf8.data);
1487 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into lower case");
1488 0 : torture_assert_data_blob_equal(tctx, data_blob_string_const(gd_lower), gd_utf8_lower,
1489 : "convert GD's name into lower case");
1490 0 : gd_upper = strupper_talloc_n_handle(iconv_handle, tctx, (const char *)gd_utf8.data, gd_utf8.length);
1491 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into upper case");
1492 0 : torture_assert_data_blob_equal(tctx, data_blob_string_const(gd_upper), gd_utf8_upper,
1493 : "convert GD's name into upper case");
1494 :
1495 0 : torture_assert(tctx,
1496 : strhasupper_handle(iconv_handle, gd_upper),
1497 : "upper case name has an upper case character");
1498 0 : torture_assert(tctx,
1499 : strhaslower_handle(iconv_handle, gd_lower),
1500 : "lower case name has an lower case character");
1501 0 : torture_assert(tctx,
1502 : strhasupper_handle(iconv_handle, gd_lower) == false,
1503 : "lower case name has no upper case character");
1504 0 : torture_assert(tctx,
1505 : strhaslower_handle(iconv_handle, gd_upper) == false,
1506 : "upper case name has no lower case character");
1507 :
1508 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)gd_utf8.data,
1509 : gd_upper) == 0,
1510 : "case insensitive comparison orig/upper");
1511 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)gd_utf8.data,
1512 : gd_lower) == 0,
1513 : "case insensitive comparison orig/lower");
1514 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, gd_upper,
1515 : gd_lower) == 0,
1516 : "case insensitive comparison upper/lower");
1517 :
1518 : /* This string isn't different in length upper/lower */
1519 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, (const char *)gd_utf8.data,
1520 : gd_upper, gd_utf8.length) == 0,
1521 : "case insensitive comparison orig/upper");
1522 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, (const char *)gd_utf8.data,
1523 : gd_lower, gd_utf8.length) == 0,
1524 : "case insensitive comparison orig/lower");
1525 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, gd_upper,
1526 : gd_lower, gd_utf8.length) == 0,
1527 : "case insensitive comparison upper/lower");
1528 :
1529 0 : data_blob_free(&gd_utf8);
1530 0 : data_blob_free(&gd_utf8_upper);
1531 0 : data_blob_free(&gd_utf8_lower);
1532 :
1533 0 : return true;
1534 : }
1535 :
1536 0 : static bool test_gd_case_cp850_handle(struct torture_context *tctx)
1537 : {
1538 : struct smb_iconv_handle *iconv_handle;
1539 0 : DATA_BLOB gd_cp850 = base64_decode_data_blob(gd_cp850_base64);
1540 0 : DATA_BLOB gd_cp850_upper = base64_decode_data_blob(gd_cp850_upper_base64);
1541 0 : DATA_BLOB gd_cp850_lower = base64_decode_data_blob(gd_cp850_lower_base64);
1542 : char *gd_lower, *gd_upper;
1543 0 : talloc_steal(tctx, gd_cp850.data);
1544 :
1545 0 : iconv_handle = get_iconv_testing_handle(tctx, "ASCII", "CP850",
1546 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
1547 0 : torture_assert(tctx, iconv_handle, "getting cp850 iconv handle");
1548 :
1549 0 : torture_assert(tctx,
1550 : strhasupper_handle(iconv_handle, (const char *)gd_cp850.data),
1551 : "GD's name has an upper case character");
1552 0 : torture_assert(tctx,
1553 : strhaslower_handle(iconv_handle, (const char *)gd_cp850.data),
1554 : "GD's name has an lower case character");
1555 0 : gd_lower = strlower_talloc_handle(iconv_handle, tctx, (const char *)gd_cp850.data);
1556 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into lower case");
1557 0 : torture_assert_data_blob_equal(tctx, data_blob_string_const(gd_lower), gd_cp850_lower,
1558 : "convert GD's name into lower case");
1559 0 : gd_upper = strupper_talloc_n_handle(iconv_handle, tctx, (const char *)gd_cp850.data, gd_cp850.length);
1560 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into upper case");
1561 0 : torture_assert_data_blob_equal(tctx, data_blob_string_const(gd_upper), gd_cp850_upper,
1562 : "convert GD's name into upper case");
1563 :
1564 0 : torture_assert(tctx,
1565 : strhasupper_handle(iconv_handle, gd_upper),
1566 : "upper case name has an upper case character");
1567 0 : torture_assert(tctx,
1568 : strhaslower_handle(iconv_handle, gd_lower),
1569 : "lower case name has an lower case character");
1570 0 : torture_assert(tctx,
1571 : strhasupper_handle(iconv_handle, gd_lower) == false,
1572 : "lower case name has no upper case character");
1573 0 : torture_assert(tctx,
1574 : strhaslower_handle(iconv_handle, gd_upper) == false,
1575 : "upper case name has no lower case character");
1576 :
1577 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)gd_cp850.data,
1578 : gd_upper) == 0,
1579 : "case insensitive comparison orig/upper");
1580 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)gd_cp850.data,
1581 : gd_lower) == 0,
1582 : "case insensitive comparison orig/lower");
1583 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, gd_upper,
1584 : gd_lower) == 0,
1585 : "case insensitive comparison upper/lower");
1586 :
1587 : /* This string isn't different in length upper/lower */
1588 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, (const char *)gd_cp850.data,
1589 : gd_upper, gd_cp850.length) == 0,
1590 : "case insensitive comparison orig/upper");
1591 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, (const char *)gd_cp850.data,
1592 : gd_lower, gd_cp850.length) == 0,
1593 : "case insensitive comparison orig/lower");
1594 0 : torture_assert(tctx, strncasecmp_m_handle(iconv_handle, gd_upper,
1595 : gd_lower, gd_cp850.length) == 0,
1596 : "case insensitive comparison upper/lower");
1597 :
1598 0 : data_blob_free(&gd_cp850);
1599 0 : data_blob_free(&gd_cp850_upper);
1600 0 : data_blob_free(&gd_cp850_lower);
1601 :
1602 0 : return true;
1603 : }
1604 :
1605 0 : static bool test_plato_case_utf8_handle(struct torture_context *tctx)
1606 : {
1607 : struct smb_iconv_handle *iconv_handle;
1608 0 : DATA_BLOB plato_utf8 = base64_decode_data_blob(plato_utf8_base64);
1609 : char *plato_lower, *plato_upper;
1610 0 : talloc_steal(tctx, plato_utf8.data);
1611 :
1612 0 : iconv_handle = get_iconv_testing_handle(tctx, "ASCII", "UTF8",
1613 0 : lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "use_builtin_handlers", true));
1614 0 : torture_assert(tctx, iconv_handle, "getting utf8 iconv handle");
1615 :
1616 0 : torture_assert(tctx,
1617 : strhasupper_handle(iconv_handle, (const char *)plato_utf8.data),
1618 : "PLATO's apology has an upper case character");
1619 0 : torture_assert(tctx,
1620 : strhaslower_handle(iconv_handle, (const char *)plato_utf8.data),
1621 : "PLATO's apology has an lower case character");
1622 0 : plato_lower = strlower_talloc_handle(iconv_handle, tctx, (const char *)plato_utf8.data);
1623 0 : torture_assert(tctx, plato_lower, "failed to convert PLATO's apology into lower case");
1624 0 : plato_upper = strupper_talloc_n_handle(iconv_handle, tctx, (const char *)plato_utf8.data, plato_utf8.length);
1625 0 : torture_assert(tctx, plato_lower, "failed to convert PLATO's apology into upper case");
1626 :
1627 0 : torture_assert(tctx,
1628 : strhasupper_handle(iconv_handle, plato_upper),
1629 : "upper case string has an upper case character");
1630 0 : torture_assert(tctx,
1631 : strhaslower_handle(iconv_handle, plato_lower),
1632 : "lower case string has an lower case character");
1633 0 : torture_assert(tctx,
1634 : strhasupper_handle(iconv_handle, plato_lower) == false,
1635 : "lower case string has no upper case character");
1636 0 : torture_assert(tctx,
1637 : strhaslower_handle(iconv_handle, plato_upper) == false,
1638 : "upper case string has no lower case character");
1639 :
1640 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)plato_utf8.data,
1641 : plato_upper) == 0,
1642 : "case insensitive comparison orig/upper");
1643 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, (const char *)plato_utf8.data,
1644 : plato_lower) == 0,
1645 : "case insensitive comparison orig/lower");
1646 0 : torture_assert(tctx, strcasecmp_m_handle(iconv_handle, plato_upper,
1647 : plato_lower) == 0,
1648 : "case insensitive comparison upper/lower");
1649 0 : return true;
1650 : }
1651 :
1652 0 : static bool test_gd(struct torture_context *tctx)
1653 : {
1654 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
1655 0 : DATA_BLOB gd_cp850 = base64_decode_data_blob(gd_cp850_base64);
1656 0 : DATA_BLOB gd_iso8859_1 = base64_decode_data_blob(gd_iso8859_1_base64);
1657 0 : DATA_BLOB gd_utf16le = base64_decode_data_blob(gd_utf16le_base64);
1658 : DATA_BLOB gd_output;
1659 : size_t saved_len;
1660 :
1661 0 : talloc_steal(tctx, gd_utf8.data);
1662 0 : talloc_steal(tctx, gd_cp850.data);
1663 0 : talloc_steal(tctx, gd_iso8859_1.data);
1664 0 : talloc_steal(tctx, gd_utf16le.data);
1665 :
1666 0 : torture_assert(tctx, convert_string_talloc(tctx, CH_UTF8, CH_UTF8,
1667 : gd_utf8.data, gd_utf8.length,
1668 : (void *)&gd_output.data, &gd_output.length),
1669 : "conversion from UTF8 to utf8 charset");
1670 0 : saved_len = gd_output.length;
1671 :
1672 0 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF8,
1673 : gd_utf8.data, gd_utf8.length,
1674 : (void *)gd_output.data, gd_output.length,
1675 : &gd_output.length),
1676 : "conversion from UTF8 to utf8 charset");
1677 :
1678 : /* Short output handling confirmation */
1679 0 : gd_output.length = 1;
1680 0 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF8,
1681 : gd_utf8.data, gd_utf8.length,
1682 : (void *)gd_output.data, gd_output.length,
1683 : &gd_output.length) == false,
1684 : "conversion from UTF8 to any utf8 charset should fail due to too short");
1685 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to utf8 charset should fail E2BIG");
1686 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
1687 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "conversion from UTF8 to utf8 charset incorrect");
1688 :
1689 : #if 0 /* This currently fails as we just copy like-for-like character conversions */
1690 : /* Short output handling confirmation */
1691 : gd_output.length = 2;
1692 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF8,
1693 : gd_utf8.data, gd_utf8.length,
1694 : (void *)gd_output.data, gd_output.length,
1695 : &gd_output.length) == false,
1696 : "conversion from UTF8 to utf8 charset should fail due to too short");
1697 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF8 to utf8 charset should fail E2BIG");
1698 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
1699 :
1700 : /* Short input handling confirmation */
1701 : gd_output.length = saved_len;
1702 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF8,
1703 : gd_utf8.data, 2,
1704 : (void *)gd_output.data, gd_output.length,
1705 : &gd_output.length) == false,
1706 : "conversion from UTF8 to UTF8 should fail due to too short");
1707 : torture_assert_errno_equal(tctx, EILSEQ, "conversion from short UTF8 to UTF8 should fail EINVAL");
1708 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
1709 : #endif
1710 :
1711 : /* Short output handling confirmation */
1712 0 : gd_output.length = 1;
1713 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1714 : gd_utf16le.data, gd_utf16le.length,
1715 : (void *)gd_output.data, gd_output.length,
1716 : &gd_output.length) == false,
1717 : "conversion from UTF16 to UTF8 should fail due to too short");
1718 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16 to UTF8 should fail E2BIG");
1719 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
1720 0 : torture_assert_data_blob_equal(tctx, gd_output, data_blob_string_const("G"), "conversion from UTF16 to UTF8 incorrect");
1721 :
1722 : /* Short output handling confirmation */
1723 0 : gd_output.length = 3;
1724 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1725 : gd_utf16le.data, gd_utf16le.length,
1726 : (void *)gd_output.data, gd_output.length,
1727 : &gd_output.length) == false,
1728 : "conversion from UTF16 to UTF8 should fail due to too short");
1729 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion from UTF16 to UTF8 should fail E2BIG");
1730 0 : torture_assert_int_equal(tctx, gd_output.length, 3, "Should get 3 bytes output for UTF8");
1731 :
1732 : /* Short input handling confirmation */
1733 0 : gd_output.length = saved_len;
1734 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1735 : gd_utf16le.data, 3,
1736 : (void *)gd_output.data, gd_output.length,
1737 : &gd_output.length) == false,
1738 : "conversion from UTF16 to UTF8 should fail due to too short");
1739 0 : torture_assert_errno_equal(tctx, EINVAL, "conversion from short UTF16 to UTF8 should fail EINVAL");
1740 0 : torture_assert_int_equal(tctx, gd_output.length, 1, "Should only get 1 char of output");
1741 :
1742 0 : return true;
1743 : }
1744 :
1745 0 : static bool test_plato(struct torture_context *tctx)
1746 : {
1747 0 : DATA_BLOB plato_utf8 = base64_decode_data_blob(plato_utf8_base64);
1748 0 : DATA_BLOB plato_utf16le = base64_decode_data_blob(plato_utf16le_base64);
1749 : DATA_BLOB plato_output;
1750 : DATA_BLOB plato_output2;
1751 :
1752 0 : talloc_steal(tctx, plato_utf8.data);
1753 0 : talloc_steal(tctx, plato_utf16le.data);
1754 :
1755 0 : torture_assert(tctx, convert_string_talloc(tctx,
1756 : CH_UTF8, CH_UTF16LE,
1757 : plato_utf8.data, plato_utf8.length,
1758 : (void *)&plato_output.data, &plato_output.length),
1759 : "conversion of UTF8 ancient greek to UTF16 failed");
1760 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le, "conversion from UTF8 to UTF16LE incorrect");
1761 :
1762 0 : torture_assert_int_equal(tctx,
1763 : strlen_m_ext((const char *)plato_utf8.data,
1764 : CH_UTF8, CH_UTF16LE),
1765 : plato_output.length / 2,
1766 : "checking strlen_m_ext of conversion of UTF8 to UTF16LE");
1767 :
1768 0 : memset(plato_output.data, '\0', plato_output.length);
1769 0 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF16LE,
1770 : plato_utf8.data, plato_utf8.length,
1771 : (void *)plato_output.data, plato_output.length,
1772 : &plato_output.length),
1773 : "conversion of UTF8 ancient greek to UTF16 failed");
1774 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf16le, "conversion from UTF8 to UTF16LE incorrect");
1775 :
1776 0 : torture_assert(tctx, convert_string_talloc(tctx,
1777 : CH_UTF16LE, CH_UTF8,
1778 : plato_output.data, plato_output.length,
1779 : (void *)&plato_output2.data, &plato_output2.length),
1780 : "conversion of UTF8 ancient greek to UTF16 failed");
1781 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf8, "conversion from UTF8 to UTF16LE incorrect");
1782 :
1783 0 : memset(plato_output2.data, '\0', plato_output2.length);
1784 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1785 : plato_output.data, plato_output.length,
1786 : (void *)plato_output2.data, plato_output2.length, &plato_output2.length),
1787 : "conversion of UTF8 ancient greek to UTF16 failed");
1788 0 : torture_assert_data_blob_equal(tctx, plato_output2, plato_utf8, "conversion from UTF8 to UTF16LE incorrect");
1789 :
1790 0 : torture_assert(tctx, convert_string_talloc(tctx,
1791 : CH_UTF8, CH_UTF8,
1792 : plato_utf8.data, plato_utf8.length,
1793 : (void *)&plato_output.data, &plato_output.length),
1794 : "conversion of UTF8 to UTF8");
1795 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8,
1796 : "conversion of UTF8 to UTF8");
1797 0 : torture_assert_int_equal(tctx,
1798 : strlen_m_ext((const char *)plato_utf8.data,
1799 : CH_UTF8, CH_UTF8),
1800 : plato_output.length,
1801 : "checking strlen_m_ext of conversion of UTF8 to UTF8");
1802 0 : memset(plato_output.data, '\0', plato_output.length);
1803 0 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_UTF8,
1804 : plato_utf8.data, plato_utf8.length,
1805 : (void *)plato_output.data, plato_output.length,
1806 : &plato_output.length),
1807 : "conversion of UTF8 to UTF8");
1808 0 : torture_assert_data_blob_equal(tctx, plato_output, plato_utf8,
1809 : "conversion of UTF8 to UTF8");
1810 :
1811 0 : memset(plato_output.data, '\0', plato_output.length);
1812 0 : torture_assert(tctx, convert_string_error(CH_UTF8, CH_DOS,
1813 : plato_utf8.data, plato_utf8.length,
1814 : (void *)plato_output.data, plato_output.length,
1815 : &plato_output.length) == false,
1816 : "conversion of UTF8 to any dos charset should fail");
1817 0 : torture_assert_errno_equal(tctx, EILSEQ, "conversion of UTF16 ancient greek to any DOS charset should fail EILSEQ");
1818 :
1819 0 : torture_assert(tctx, convert_string_talloc(tctx,
1820 : CH_UTF8, CH_DOS,
1821 : plato_utf8.data, plato_utf8.length,
1822 : (void *)&plato_output.data, &plato_output.length) == false,
1823 : "conversion of UTF8 ancient greek to any DOS charset should fail");
1824 :
1825 : /* Allocate only enough space for a partial conversion */
1826 0 : plato_output = data_blob_talloc(tctx, NULL, 9);
1827 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1828 : plato_utf16le.data, plato_utf16le.length,
1829 : (void *)plato_output.data, plato_output.length,
1830 : &plato_output.length) == false,
1831 : "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1832 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1833 0 : torture_assert_int_equal(tctx, plato_output.length, 8,
1834 : "conversion of UTF16 ancient greek to UTF8 should stop on multibyte boundary");
1835 :
1836 0 : plato_output = data_blob_talloc(tctx, NULL, 2);
1837 0 : torture_assert(tctx, convert_string_error(CH_UTF16LE, CH_UTF8,
1838 : plato_utf16le.data, plato_utf16le.length,
1839 : (void *)plato_output.data, plato_output.length,
1840 : &plato_output.length) == false,
1841 : "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1842 0 : torture_assert_errno_equal(tctx, E2BIG, "conversion of UTF16 ancient greek to UTF8 should fail, not enough space");
1843 0 : torture_assert_int_equal(tctx, plato_output.length, 0,
1844 : "conversion of UTF16 ancient greek to UTF8 should stop on multibyte boundary");
1845 :
1846 :
1847 0 : return true;
1848 : }
1849 :
1850 0 : static bool test_plato_latin(struct torture_context *tctx)
1851 : {
1852 0 : DATA_BLOB plato_latin_utf8 = base64_decode_data_blob(plato_latin_utf8_base64);
1853 0 : DATA_BLOB plato_latin_utf16le = base64_decode_data_blob(plato_latin_utf16le_base64);
1854 : DATA_BLOB plato_latin_output;
1855 :
1856 0 : talloc_steal(tctx, plato_latin_utf8.data);
1857 0 : talloc_steal(tctx, plato_latin_utf16le.data);
1858 :
1859 0 : torture_assert(tctx, convert_string_talloc(tctx,
1860 : CH_UTF16LE, CH_UTF8,
1861 : plato_latin_utf16le.data, plato_latin_utf16le.length,
1862 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1863 : "conversion of UTF16 latin charset greek to unix charset UTF8 failed");
1864 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf8, "conversion from UTF16 to UTF8 incorrect");
1865 :
1866 0 : torture_assert_int_equal(tctx,
1867 : strlen_m_ext((const char *)plato_latin_output.data,
1868 : CH_UTF8, CH_UTF16LE),
1869 : plato_latin_utf16le.length / 2,
1870 : "checking strlen_m_ext UTF16 latin charset greek to UTF8");
1871 0 : torture_assert(tctx, convert_string_talloc(tctx,
1872 : CH_UTF8, CH_UTF16LE,
1873 : plato_latin_utf8.data, plato_latin_utf8.length,
1874 : (void *)&plato_latin_output.data, &plato_latin_output.length),
1875 : "conversion of UTF16 latin charset greek to UTF16LE failed");
1876 0 : torture_assert_data_blob_equal(tctx, plato_latin_output, plato_latin_utf16le, "conversion from UTF8 to UTF16LE incorrect");
1877 :
1878 0 : return true;
1879 : }
1880 :
1881 0 : static bool test_gd_case(struct torture_context *tctx)
1882 : {
1883 0 : DATA_BLOB gd_utf8 = base64_decode_data_blob(gd_utf8_base64);
1884 : char *gd_unix;
1885 : size_t gd_size;
1886 : char *gd_lower, *gd_upper;
1887 0 : talloc_steal(tctx, gd_utf8.data);
1888 :
1889 0 : torture_assert(tctx, convert_string_talloc(tctx, CH_UTF8, CH_UNIX,
1890 : gd_utf8.data, gd_utf8.length,
1891 : (void *)&gd_unix, &gd_size),
1892 : "conversion of unix charset to UTF8");
1893 :
1894 0 : gd_lower = strlower_talloc(tctx, gd_unix);
1895 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into lower case");
1896 0 : gd_upper = strupper_talloc_n(tctx, gd_unix, gd_size);
1897 0 : torture_assert(tctx, gd_lower, "failed to convert GD's name into upper case");
1898 :
1899 0 : torture_assert(tctx,
1900 : strhasupper(gd_unix),
1901 : "GD's name has an upper case character");
1902 0 : torture_assert(tctx,
1903 : strhaslower(gd_unix),
1904 : "GD's name has an lower case character");
1905 0 : torture_assert(tctx,
1906 : strhasupper(gd_upper),
1907 : "upper case name has an upper case character");
1908 0 : torture_assert(tctx,
1909 : strhaslower(gd_lower),
1910 : "lower case name has an lower case character");
1911 0 : torture_assert(tctx,
1912 : strhasupper(gd_lower) == false,
1913 : "lower case name has no upper case character");
1914 0 : torture_assert(tctx,
1915 : strhaslower(gd_upper) == false,
1916 : "upper case name has no lower case character");
1917 :
1918 0 : torture_assert(tctx, strcasecmp_m(gd_unix,
1919 : gd_upper) == 0,
1920 : "case insensitive comparison orig/upper");
1921 0 : torture_assert(tctx, strcasecmp_m(gd_unix,
1922 : gd_lower) == 0,
1923 : "case insensitive comparison orig/lower");
1924 0 : torture_assert(tctx, strcasecmp_m(gd_upper,
1925 : gd_lower) == 0,
1926 : "case insensitive comparison upper/lower");
1927 :
1928 : /* This string isn't different in length upper/lower, but just check the first 5 chars */
1929 0 : torture_assert(tctx, strncasecmp_m(gd_unix,
1930 : gd_upper, 5) == 0,
1931 : "case insensitive comparison orig/upper");
1932 0 : torture_assert(tctx, strncasecmp_m(gd_unix,
1933 : gd_lower, 5) == 0,
1934 : "case insensitive comparison orig/lower");
1935 0 : torture_assert(tctx, strncasecmp_m(gd_upper,
1936 : gd_lower, 5) == 0,
1937 : "case insensitive comparison upper/lower");
1938 0 : return true;
1939 : }
1940 :
1941 0 : static bool test_plato_case(struct torture_context *tctx)
1942 : {
1943 0 : DATA_BLOB plato_utf8 = base64_decode_data_blob(plato_utf8_base64);
1944 : char *plato_unix;
1945 : size_t plato_length;
1946 : char *plato_lower, *plato_upper;
1947 0 : talloc_steal(tctx, plato_utf8.data);
1948 :
1949 0 : torture_assert(tctx, convert_string_talloc(tctx, CH_UTF8, CH_UNIX,
1950 : plato_utf8.data, plato_utf8.length,
1951 : (void *)&plato_unix, &plato_length),
1952 : "conversion of unix charset to UTF8");
1953 :
1954 0 : torture_assert(tctx,
1955 : strhasupper(plato_unix),
1956 : "PLATO's apology has an upper case character");
1957 0 : torture_assert(tctx,
1958 : strhaslower(plato_unix),
1959 : "PLATO's apology has an lower case character");
1960 0 : plato_lower = strlower_talloc(tctx, plato_unix);
1961 0 : torture_assert(tctx, plato_lower, "failed to convert PLATO's apology into lower case");
1962 0 : plato_upper = strupper_talloc_n(tctx, plato_unix, plato_utf8.length);
1963 0 : torture_assert(tctx, plato_lower, "failed to convert PLATO's apology into upper case");
1964 :
1965 0 : torture_assert(tctx,
1966 : strhasupper(plato_upper),
1967 : "upper case string has an upper case character");
1968 0 : torture_assert(tctx,
1969 : strhaslower(plato_lower),
1970 : "lower case string has an lower case character");
1971 0 : torture_assert(tctx,
1972 : strhasupper(plato_lower) == false,
1973 : "lower case string has no upper case character");
1974 0 : torture_assert(tctx,
1975 : strhaslower(plato_upper) == false,
1976 : "upper case string has no lower case character");
1977 :
1978 0 : torture_assert(tctx, strcasecmp_m(plato_unix,
1979 : plato_upper) == 0,
1980 : "case insensitive comparison orig/upper");
1981 0 : torture_assert(tctx, strcasecmp_m(plato_unix,
1982 : plato_lower) == 0,
1983 : "case insensitive comparison orig/lower");
1984 0 : torture_assert(tctx, strcasecmp_m(plato_upper,
1985 : plato_lower) == 0,
1986 : "case insensitive comparison upper/lower");
1987 0 : return true;
1988 : }
1989 :
1990 964 : struct torture_suite *torture_local_convert_string_handle(TALLOC_CTX *mem_ctx)
1991 : {
1992 964 : struct torture_suite *suite = torture_suite_create(mem_ctx, "convert_string_handle");
1993 964 : torture_suite_add_simple_test(suite, "cp850 high points", test_cp850_high_points);
1994 :
1995 964 : torture_suite_add_simple_test(suite, "gd_ascii", test_gd_ascii_handle);
1996 964 : torture_suite_add_simple_test(suite, "gd_minus_1", test_gd_minus_1_handle);
1997 964 : torture_suite_add_simple_test(suite, "gd_iso8859_cp850", test_gd_iso8859_cp850_handle);
1998 964 : torture_suite_add_simple_test(suite, "plato_english_iso8859_cp850", test_plato_english_iso8859_cp850_handle);
1999 964 : torture_suite_add_simple_test(suite, "plato_english_minus_1", test_plato_english_minus_1_handle);
2000 964 : torture_suite_add_simple_test(suite, "plato_cp850_utf8", test_plato_cp850_utf8_handle);
2001 964 : torture_suite_add_simple_test(suite, "plato_minus_1", test_plato_minus_1_handle);
2002 964 : torture_suite_add_simple_test(suite, "plato_latin_cp850_utf8", test_plato_latin_cp850_utf8_handle);
2003 964 : torture_suite_add_simple_test(suite, "utf8-nfc-to-nfd", test_utf8_nfc_to_nfd);
2004 964 : torture_suite_add_simple_test(suite, "utf8-nfc-to-nfd-overflow", test_utf8_nfc_to_nfd_overflow);
2005 964 : torture_suite_add_simple_test(suite, "utf8-nfd-to-nfc", test_utf8_nfd_to_nfc);
2006 964 : return suite;
2007 : }
2008 :
2009 964 : struct torture_suite *torture_local_string_case_handle(TALLOC_CTX *mem_ctx)
2010 : {
2011 964 : struct torture_suite *suite = torture_suite_create(mem_ctx, "string_case_handle");
2012 :
2013 964 : torture_suite_add_simple_test(suite, "gd_case_utf8", test_gd_case_utf8_handle);
2014 964 : torture_suite_add_simple_test(suite, "gd_case_cp850", test_gd_case_cp850_handle);
2015 964 : torture_suite_add_simple_test(suite, "plato_case_utf8", test_plato_case_utf8_handle);
2016 964 : return suite;
2017 : }
2018 :
2019 964 : struct torture_suite *torture_local_convert_string(TALLOC_CTX *mem_ctx)
2020 : {
2021 964 : struct torture_suite *suite = torture_suite_create(mem_ctx, "convert_string");
2022 :
2023 964 : torture_suite_add_simple_test(suite, "gd", test_gd);
2024 964 : torture_suite_add_simple_test(suite, "plato", test_plato);
2025 964 : torture_suite_add_simple_test(suite, "plato_latin", test_plato_latin);
2026 964 : return suite;
2027 : }
2028 :
2029 964 : struct torture_suite *torture_local_string_case(TALLOC_CTX *mem_ctx)
2030 : {
2031 964 : struct torture_suite *suite = torture_suite_create(mem_ctx, "string_case_handle");
2032 :
2033 964 : torture_suite_add_simple_test(suite, "gd_case", test_gd_case);
2034 964 : torture_suite_add_simple_test(suite, "plato_case", test_plato_case);
2035 964 : return suite;
2036 : }
|