1 /* Conversion to and from the various ISO 646 CCS.
2 Copyright (C) 1998-2022 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
4
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
9
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library; if not, see
17 <https://www.gnu.org/licenses/>. */
18
19 /* The implementation of the conversion which can be performed by this
20 module are not very sophisticated and not tuned at all. There are
21 zillions of ISO 646 derivates and supporting them all in a separate
22 module is overkill since these coded character sets are hardly ever
23 used anymore (except ANSI_X3.4-1968 == ASCII, which is compatible
24 with ISO 8859-1). The European variants are superceded by the
25 various ISO 8859-? standards and the Asian variants are embedded in
26 larger character sets. Therefore this implementation is simply
27 here to make it possible to do the conversion if it is necessary.
28 The cost in the gconv-modules file is set to `2' and therefore
29 allows one to easily provide a tuned implementation in case this
30 proofs to be necessary. */
31
32 #include <dlfcn.h>
33 #include <gconv.h>
34 #include <stdint.h>
35 #include <stdlib.h>
36 #include <string.h>
37
38 /* Definitions used in the body of the `gconv' function. */
39 #define FROM_LOOP from_ascii
40 #define TO_LOOP to_ascii
41 #define DEFINE_INIT 0
42 #define DEFINE_FINI 0
43 #define MIN_NEEDED_FROM 1
44 #define MIN_NEEDED_TO 4
45 #define ONE_DIRECTION 0
46
47 #define FROM_DIRECTION (dir == from_iso646)
48 #define PREPARE_LOOP \
49 enum direction dir = ((struct iso646_data *) step->__data)->dir; \
50 enum variant var = ((struct iso646_data *) step->__data)->var;
51 #define EXTRA_LOOP_ARGS , var
52
53
54 /* Direction of the transformation. */
55 enum direction
56 {
57 illegal_dir,
58 to_iso646,
59 from_iso646
60 };
61
62 /* See names below, must be in the same order. */
63 enum variant
64 {
65 GB, /* BS_4730 */
66 CA, /* CSA_Z243.4-1985-1 */
67 CA2, /* CSA_Z243.4-1985-2 */
68 DE, /* DIN_66003 */
69 DK, /* DS_2089 */
70 ES, /* ES */
71 ES2, /* ES2 */
72 CN, /* GB_1988-80 */
73 IT, /* IT */
74 JP, /* JIS_C6220-1969-RO */
75 JP_OCR_B, /* JIS_C6229-1984-B */
76 YU, /* JUS_I.B1.002 */
77 KR, /* KSC5636 */
78 HU, /* MSZ_7795.3 */
79 CU, /* NC_NC00-10 */
80 FR, /* NF_Z_62-010 */
81 FR1, /* NF_Z_62-010_(1973) */
82 NO, /* NS_4551-1 */
83 NO2, /* NS_4551-2 */
84 PT, /* PT */
85 PT2, /* PT2 */
86 SE, /* SEN_850200_B */
87 SE2 /* SEN_850200_C */
88 };
89
90 /* Must be in the same order as enum variant above. */
91 static const char names[] =
92 "BS_4730//\0"
93 "CSA_Z243.4-1985-1//\0"
94 "CSA_Z243.4-1985-2//\0"
95 "DIN_66003//\0"
96 "DS_2089//\0"
97 "ES//\0"
98 "ES2//\0"
99 "GB_1988-80//\0"
100 "IT//\0"
101 "JIS_C6220-1969-RO//\0"
102 "JIS_C6229-1984-B//\0"
103 "JUS_I.B1.002//\0"
104 "KSC5636//\0"
105 "MSZ_7795.3//\0"
106 "NC_NC00-10//\0"
107 "NF_Z_62-010//\0"
108 "NF_Z_62-010_1973//\0" /* Note that we don't have the parenthesis in
109 the name. */
110 "NS_4551-1//\0"
111 "NS_4551-2//\0"
112 "PT//\0"
113 "PT2//\0"
114 "SEN_850200_B//\0"
115 "SEN_850200_C//\0"
116 "\0";
117
118 struct iso646_data
119 {
120 enum direction dir;
121 enum variant var;
122 };
123
124
125 extern int gconv_init (struct __gconv_step *step);
126 int
gconv_init(struct __gconv_step * step)127 gconv_init (struct __gconv_step *step)
128 {
129 /* Determine which direction. */
130 struct iso646_data *new_data;
131 enum direction dir = illegal_dir;
132 int result;
133
134 enum variant var = 0;
135 for (const char *name = names; *name != '\0';
136 name = __rawmemchr (name, '\0') + 1)
137 {
138 if (__strcasecmp (step->__from_name, name) == 0)
139 {
140 dir = from_iso646;
141 break;
142 }
143 else if (__strcasecmp (step->__to_name, name) == 0)
144 {
145 dir = to_iso646;
146 break;
147 }
148 ++var;
149 }
150
151 result = __GCONV_NOCONV;
152 if (__builtin_expect (dir, from_iso646) != illegal_dir)
153 {
154 new_data = (struct iso646_data *) malloc (sizeof (struct iso646_data));
155
156 result = __GCONV_NOMEM;
157 if (new_data != NULL)
158 {
159 new_data->dir = dir;
160 new_data->var = var;
161 step->__data = new_data;
162
163 if (dir == from_iso646)
164 {
165 step->__min_needed_from = MIN_NEEDED_FROM;
166 step->__max_needed_from = MIN_NEEDED_FROM;
167 step->__min_needed_to = MIN_NEEDED_TO;
168 step->__max_needed_to = MIN_NEEDED_TO;
169 }
170 else
171 {
172 step->__min_needed_from = MIN_NEEDED_TO;
173 step->__max_needed_from = MIN_NEEDED_TO;
174 step->__min_needed_to = MIN_NEEDED_FROM;
175 step->__max_needed_to = MIN_NEEDED_FROM;
176 }
177
178 step->__stateful = 0;
179
180 result = __GCONV_OK;
181 }
182 }
183
184 return result;
185 }
186
187
188 extern void gconv_end (struct __gconv_step *data);
189 void
gconv_end(struct __gconv_step * data)190 gconv_end (struct __gconv_step *data)
191 {
192 free (data->__data);
193 }
194
195
196 /* First define the conversion function from ASCII to UCS4. */
197 #define MIN_NEEDED_INPUT MIN_NEEDED_FROM
198 #define MIN_NEEDED_OUTPUT MIN_NEEDED_TO
199 #define LOOPFCT FROM_LOOP
200 #define BODY \
201 { \
202 uint32_t ch; \
203 int failure = __GCONV_OK; \
204 \
205 ch = *inptr; \
206 switch (ch) \
207 { \
208 case 0x23: \
209 if (var == GB || var == ES || var == IT || var == FR || var == FR1) \
210 ch = 0xa3; \
211 else if (var == NO2) \
212 ch = 0xa7; \
213 break; \
214 case 0x24: \
215 if (var == CN) \
216 ch = 0xa5; \
217 else if (var == HU || var == CU || var == SE || var == SE2) \
218 ch = 0xa4; \
219 break; \
220 case 0x40: \
221 if (var == CA || var == CA2 || var == FR || var == FR1) \
222 ch = 0xe0; \
223 else if (var == DE || var == ES || var == IT || var == PT) \
224 ch = 0xa7; \
225 else if (var == ES2) \
226 ch = 0x2022; \
227 else if (var == YU) \
228 ch = 0x17d; \
229 else if (var == HU) \
230 ch = 0xc1; \
231 else if (var == PT2) \
232 ch = 0xb4; \
233 else if (var == SE2) \
234 ch = 0xc9; \
235 break; \
236 case 0x5b: \
237 if (var == CA || var == CA2) \
238 ch = 0xe2; \
239 else if (var == DE || var == SE || var == SE2) \
240 ch = 0xc4; \
241 else if (var == DK || var == NO || var == NO2) \
242 ch = 0xc6; \
243 else if (var == ES || var == ES2 || var == CU) \
244 ch = 0xa1; \
245 else if (var == IT || var == FR || var == FR1) \
246 ch = 0xb0; \
247 else if (var == JP_OCR_B) \
248 ch = 0x2329; \
249 else if (var == YU) \
250 ch = 0x160; \
251 else if (var == HU) \
252 ch = 0xc9; \
253 else if (var == PT || var == PT2) \
254 ch = 0xc3; \
255 break; \
256 case 0x5c: \
257 if (var == CA || var == CA2 || var == IT || var == FR || var == FR1) \
258 ch = 0xe7; \
259 else if (var == DE || var == HU || var == SE || var == SE2) \
260 ch = 0xd6; \
261 else if (var == DK || var == NO || var == NO2) \
262 ch = 0xd8; \
263 else if (var == ES || var == ES2 || var == CU) \
264 ch = 0xd1; \
265 else if (var == JP || var == JP_OCR_B) \
266 ch = 0xa5; \
267 else if (var == YU) \
268 ch = 0x110; \
269 else if (var == KR) \
270 ch = 0x20a9; \
271 else if (var == PT || var == PT2) \
272 ch = 0xc7; \
273 break; \
274 case 0x5d: \
275 if (var == CA || var == CA2) \
276 ch = 0xea; \
277 else if (var == DE || var == HU) \
278 ch = 0xdc; \
279 else if (var == DK || var == NO || var == NO2 || var == SE \
280 || var == SE2) \
281 ch = 0xc5; \
282 else if (var == ES) \
283 ch = 0xbf; \
284 else if (var == ES2) \
285 ch = 0xc7; \
286 else if (var == IT) \
287 ch = 0xe9; \
288 else if (var == JP_OCR_B) \
289 ch = 0x232a; \
290 else if (var == YU) \
291 ch = 0x106; \
292 else if (var == FR || var == FR1) \
293 ch = 0xa7; \
294 else if (var == PT || var == PT2) \
295 ch = 0xd5; \
296 break; \
297 case 0x5e: \
298 if (var == CA) \
299 ch = 0xee; \
300 else if (var == CA2) \
301 ch = 0xc9; \
302 else if (var == ES2 || var == CU) \
303 ch = 0xbf; \
304 else if (var == YU) \
305 ch = 0x10c; \
306 else if (var == SE2) \
307 ch = 0xdc; \
308 break; \
309 case 0x60: \
310 if (var == CA || var == CA2) \
311 ch = 0xf4; \
312 else if (var == IT) \
313 ch = 0xf9; \
314 else if (var == JP_OCR_B) \
315 /* Illegal character. */ \
316 failure = __GCONV_ILLEGAL_INPUT; \
317 else if (var == YU) \
318 ch = 0x17e; \
319 else if (var == HU) \
320 ch = 0xe1; \
321 else if (var == FR) \
322 ch = 0xb5; \
323 else if (var == SE2) \
324 ch = 0xe9; \
325 break; \
326 case 0x7b: \
327 if (var == CA || var == CA2 || var == HU || var == FR || var == FR1) \
328 ch = 0xe9; \
329 else if (var == DE || var == SE || var == SE2) \
330 ch = 0xe4; \
331 else if (var == DK || var == NO || var == NO2) \
332 ch = 0xe6; \
333 else if (var == ES) \
334 ch = 0xb0; \
335 else if (var == ES2 || var == CU) \
336 ch = 0xb4; \
337 else if (var == IT) \
338 ch = 0xe0; \
339 else if (var == YU) \
340 ch = 0x161; \
341 else if (var == PT || var == PT2) \
342 ch = 0xe3; \
343 break; \
344 case 0x7c: \
345 if (var == CA || var == CA2 || var == FR || var == FR1) \
346 ch = 0xf9; \
347 else if (var == DE || var == HU || var == SE || var == SE2) \
348 ch = 0xf6; \
349 else if (var == DK || var == NO || var == NO2) \
350 ch = 0xf8; \
351 else if (var == ES || var == ES2 || var == CU) \
352 ch = 0xf1; \
353 else if (var == IT) \
354 ch = 0xf2; \
355 else if (var == YU) \
356 ch = 0x111; \
357 else if (var == PT || var == PT2) \
358 ch = 0xe7; \
359 break; \
360 case 0x7d: \
361 if (var == CA || var == CA2 || var == IT || var == FR || var == FR1) \
362 ch = 0xe8; \
363 else if (var == DE || var == HU) \
364 ch = 0xfc; \
365 else if (var == DK || var == NO || var == NO2 || var == SE \
366 || var == SE2) \
367 ch = 0xe5; \
368 else if (var == ES || var == ES2) \
369 ch = 0xe7; \
370 else if (var == YU) \
371 ch = 0x107; \
372 else if (var == CU) \
373 ch = 0x5b; \
374 else if (var == PT || var == PT2) \
375 ch = 0xf5; \
376 break; \
377 case 0x7e: \
378 if (var == GB || var == CN || var == JP || var == NO || var == SE) \
379 ch = 0x203e; \
380 else if (var == CA || var == CA2) \
381 ch = 0xfb; \
382 else if (var == DE) \
383 ch = 0xdf; \
384 else if (var == ES2 || var == CU || var == FR || var == FR1) \
385 ch = 0xa8; \
386 else if (var == IT) \
387 ch = 0xec; \
388 else if (var == JP_OCR_B) \
389 /* Illegal character. */ \
390 failure = __GCONV_ILLEGAL_INPUT; \
391 else if (var == YU) \
392 ch = 0x10d; \
393 else if (var == HU) \
394 ch = 0x2dd; \
395 else if (var == NO2) \
396 ch = 0x7c; \
397 else if (var == PT) \
398 ch = 0xb0; \
399 else if (var == SE2) \
400 ch = 0xfc; \
401 break; \
402 default: \
403 break; \
404 case 0x80 ... 0xff: \
405 /* Illegal character. */ \
406 failure = __GCONV_ILLEGAL_INPUT; \
407 break; \
408 } \
409 \
410 /* Hopefully gcc can recognize that the following `if' is only true \
411 when we reach the default case in the `switch' statement. */ \
412 if (__builtin_expect (failure, __GCONV_OK) == __GCONV_ILLEGAL_INPUT) \
413 { \
414 STANDARD_FROM_LOOP_ERR_HANDLER (1); \
415 } \
416 else \
417 { \
418 put32 (outptr, ch); \
419 outptr += 4; \
420 } \
421 ++inptr; \
422 }
423 #define LOOP_NEED_FLAGS
424 #define EXTRA_LOOP_DECLS , enum variant var
425 #include <iconv/loop.c>
426
427
428 /* Next, define the other direction. */
429 #define MIN_NEEDED_INPUT MIN_NEEDED_TO
430 #define MIN_NEEDED_OUTPUT MIN_NEEDED_FROM
431 #define LOOPFCT TO_LOOP
432 #define BODY \
433 { \
434 unsigned int ch; \
435 int failure = __GCONV_OK; \
436 \
437 ch = get32 (inptr); \
438 switch (ch) \
439 { \
440 case 0x23: \
441 if (var == GB || var == ES || var == IT || var == FR || var == FR1 \
442 || var == NO2) \
443 failure = __GCONV_ILLEGAL_INPUT; \
444 break; \
445 case 0x24: \
446 if (var == CN || var == HU || var == CU || var == SE || var == SE2) \
447 failure = __GCONV_ILLEGAL_INPUT; \
448 break; \
449 case 0x40: \
450 if (var == CA || var == CA2 || var == DE || var == ES || var == ES2 \
451 || var == IT || var == YU || var == HU || var == FR || var == FR1 \
452 || var == PT || var == PT2 || var == SE2) \
453 failure = __GCONV_ILLEGAL_INPUT; \
454 break; \
455 case 0x5b: \
456 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
457 || var == ES2 || var == IT || var == JP_OCR_B || var == YU \
458 || var == HU || var == FR || var == FR1 || var == NO \
459 || var == NO2 || var == PT || var == PT2 || var == SE \
460 || var == SE2) \
461 failure = __GCONV_ILLEGAL_INPUT; \
462 else if (var == CU) \
463 ch = 0x7d; \
464 break; \
465 case 0x5c: \
466 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
467 || var == ES2 || var == IT || var == JP || var == JP_OCR_B \
468 || var == YU || var == KR || var == HU || var == CU || var == FR \
469 || var == FR1 || var == NO || var == NO2 || var == PT \
470 || var == PT2 || var == SE || var == SE2) \
471 failure = __GCONV_ILLEGAL_INPUT; \
472 break; \
473 case 0x5d: \
474 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
475 || var == ES2 || var == IT || var == JP_OCR_B || var == YU \
476 || var == HU || var == FR || var == FR1 || var == NO \
477 || var == NO2 || var == PT || var == PT2 || var == SE \
478 || var == SE2) \
479 failure = __GCONV_ILLEGAL_INPUT; \
480 break; \
481 case 0x5e: \
482 if (var == CA || var == CA2 || var == ES2 || var == YU || var == CU \
483 || var == SE2) \
484 failure = __GCONV_ILLEGAL_INPUT; \
485 break; \
486 case 0x60: \
487 if (var == CA || var == CA2 || var == IT || var == JP_OCR_B \
488 || var == YU || var == HU || var == FR || var == SE2) \
489 failure = __GCONV_ILLEGAL_INPUT; \
490 break; \
491 case 0x7b: \
492 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
493 || var == ES2 || var == IT || var == YU || var == HU \
494 || var == CU || var == FR || var == FR1 || var == NO \
495 || var == NO2 || var == PT || var == PT2 || var == SE \
496 || var == SE2) \
497 failure = __GCONV_ILLEGAL_INPUT; \
498 break; \
499 case 0x7c: \
500 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
501 || var == ES2 || var == IT || var == YU || var == HU || var == CU \
502 || var == FR || var == FR1 || var == NO || var == PT \
503 || var == PT2 || var == SE || var == SE2) \
504 failure = __GCONV_ILLEGAL_INPUT; \
505 else if (var == NO2) \
506 ch = 0x7e; \
507 break; \
508 case 0x7d: \
509 if (var == CA || var == CA2 || var == DE || var == DK || var == ES \
510 || var == ES2 || var == IT || var == YU || var == HU || var == CU \
511 || var == FR || var == FR1 || var == NO || var == NO2 \
512 || var == PT || var == PT2 || var == SE || var == SE2) \
513 failure = __GCONV_ILLEGAL_INPUT; \
514 break; \
515 case 0x7e: \
516 if (var == GB || var == CA || var == CA2 || var == DE || var == ES2 \
517 || var == CN || var == IT || var == JP || var == JP_OCR_B \
518 || var == YU || var == HU || var == CU || var == FR || var == FR1 \
519 || var == NO || var == NO2 || var == PT || var == SE \
520 || var == SE2) \
521 failure = __GCONV_ILLEGAL_INPUT; \
522 break; \
523 case 0xa1: \
524 if (var != ES && var != ES2 && var != CU) \
525 failure = __GCONV_ILLEGAL_INPUT; \
526 ch = 0x5b; \
527 break; \
528 case 0xa3: \
529 if (var != GB && var != ES && var != IT && var != FR && var != FR1) \
530 failure = __GCONV_ILLEGAL_INPUT; \
531 ch = 0x23; \
532 break; \
533 case 0xa4: \
534 if (var != HU && var != CU && var != SE && var != SE2) \
535 failure = __GCONV_ILLEGAL_INPUT; \
536 ch = 0x24; \
537 break; \
538 case 0xa5: \
539 if (var == CN) \
540 ch = 0x24; \
541 else if (var == JP || var == JP_OCR_B) \
542 ch = 0x5c; \
543 else \
544 failure = __GCONV_ILLEGAL_INPUT; \
545 break; \
546 case 0xa7: \
547 if (var == DE || var == ES || var == IT || var == PT) \
548 ch = 0x40; \
549 else if (var == FR || var == FR1) \
550 ch = 0x5d; \
551 else if (var == NO2) \
552 ch = 0x23; \
553 else \
554 failure = __GCONV_ILLEGAL_INPUT; \
555 break; \
556 case 0xa8: \
557 if (var != ES2 && var != CU && var != FR && var != FR1) \
558 failure = __GCONV_ILLEGAL_INPUT; \
559 ch = 0x7e; \
560 break; \
561 case 0xb0: \
562 if (var == ES) \
563 ch = 0x7b; \
564 else if (var == IT || var == FR || var == FR1) \
565 ch = 0x5b; \
566 else if (var == PT) \
567 ch = 0x7e; \
568 else \
569 failure = __GCONV_ILLEGAL_INPUT; \
570 break; \
571 case 0xb4: \
572 if (var == ES2 || var == CU) \
573 ch = 0x7b; \
574 else if (var == PT2) \
575 ch = 0x40; \
576 else \
577 failure = __GCONV_ILLEGAL_INPUT; \
578 break; \
579 case 0xb5: \
580 if (var != FR) \
581 failure = __GCONV_ILLEGAL_INPUT; \
582 ch = 0x60; \
583 break; \
584 case 0xbf: \
585 if (var == ES) \
586 ch = 0x5d; \
587 else if (var == ES2 || var == CU) \
588 ch = 0x5e; \
589 else \
590 failure = __GCONV_ILLEGAL_INPUT; \
591 break; \
592 case 0xc1: \
593 if (var != HU) \
594 failure = __GCONV_ILLEGAL_INPUT; \
595 ch = 0x40; \
596 break; \
597 case 0xc3: \
598 if (var != PT && var != PT2) \
599 failure = __GCONV_ILLEGAL_INPUT; \
600 ch = 0x5b; \
601 break; \
602 case 0xc4: \
603 if (var != DE && var != SE && var != SE2) \
604 failure = __GCONV_ILLEGAL_INPUT; \
605 ch = 0x5b; \
606 break; \
607 case 0xc5: \
608 if (var != DK && var != NO && var != NO2 && var != SE && var != SE2) \
609 failure = __GCONV_ILLEGAL_INPUT; \
610 ch = 0x5d; \
611 break; \
612 case 0xc6: \
613 if (var != DK && var != NO && var != NO2) \
614 failure = __GCONV_ILLEGAL_INPUT; \
615 ch = 0x5b; \
616 break; \
617 case 0xc7: \
618 if (var == ES2) \
619 ch = 0x5d; \
620 else if (var == PT || var == PT2) \
621 ch = 0x5c; \
622 else \
623 failure = __GCONV_ILLEGAL_INPUT; \
624 break; \
625 case 0xc9: \
626 if (var == CA2) \
627 ch = 0x5e; \
628 else if (var == HU) \
629 ch = 0x5b; \
630 else if (var == SE2) \
631 ch = 0x40; \
632 else \
633 failure = __GCONV_ILLEGAL_INPUT; \
634 break; \
635 case 0xd1: \
636 if (var != ES && var != ES2 && var != CU) \
637 failure = __GCONV_ILLEGAL_INPUT; \
638 ch = 0x5c; \
639 break; \
640 case 0xd5: \
641 if (var != PT && var != PT2) \
642 failure = __GCONV_ILLEGAL_INPUT; \
643 ch = 0x5d; \
644 break; \
645 case 0xd6: \
646 if (var != DE && var != HU && var != SE && var != SE2) \
647 failure = __GCONV_ILLEGAL_INPUT; \
648 ch = 0x5c; \
649 break; \
650 case 0xd8: \
651 if (var != DK && var != NO && var != NO2) \
652 failure = __GCONV_ILLEGAL_INPUT; \
653 ch = 0x5c; \
654 break; \
655 case 0xdc: \
656 if (var == DE || var == HU) \
657 ch = 0x5d; \
658 else if (var == SE2) \
659 ch = 0x5e; \
660 else \
661 failure = __GCONV_ILLEGAL_INPUT; \
662 break; \
663 case 0xdf: \
664 if (var != DE) \
665 failure = __GCONV_ILLEGAL_INPUT; \
666 ch = 0x7e; \
667 break; \
668 case 0xe0: \
669 if (var == CA || var == CA2 || var == FR || var == FR1) \
670 ch = 0x40; \
671 else if (var == IT) \
672 ch = 0x7b; \
673 else \
674 failure = __GCONV_ILLEGAL_INPUT; \
675 break; \
676 case 0xe1: \
677 if (var != HU) \
678 failure = __GCONV_ILLEGAL_INPUT; \
679 ch = 0x60; \
680 break; \
681 case 0xe2: \
682 if (var != CA && var != CA2) \
683 failure = __GCONV_ILLEGAL_INPUT; \
684 ch = 0x5b; \
685 break; \
686 case 0xe3: \
687 if (var != PT && var != PT2) \
688 failure = __GCONV_ILLEGAL_INPUT; \
689 ch = 0x7b; \
690 break; \
691 case 0xe4: \
692 if (var != DE && var != SE && var != SE2) \
693 failure = __GCONV_ILLEGAL_INPUT; \
694 ch = 0x7b; \
695 break; \
696 case 0xe5: \
697 if (var != DK && var != NO && var != NO2 && var != SE && var != SE2) \
698 failure = __GCONV_ILLEGAL_INPUT; \
699 ch = 0x7d; \
700 break; \
701 case 0xe6: \
702 if (var != DK && var != NO && var != NO2) \
703 failure = __GCONV_ILLEGAL_INPUT; \
704 ch = 0x7b; \
705 break; \
706 case 0xe7: \
707 if (var == CA || var == CA2 || var == IT || var == FR || var == FR1) \
708 ch = 0x5c; \
709 else if (var == ES || var == ES2) \
710 ch = 0x7d; \
711 else if (var == PT || var == PT2) \
712 ch = 0x7c; \
713 else \
714 failure = __GCONV_ILLEGAL_INPUT; \
715 break; \
716 case 0xe8: \
717 if (var != CA && var != CA2 && var != IT && var != FR && var != FR1) \
718 failure = __GCONV_ILLEGAL_INPUT; \
719 ch = 0x7d; \
720 break; \
721 case 0xe9: \
722 if (var == CA || var == CA2 || var == HU || var == FR || var == FR1) \
723 ch = 0x7b; \
724 else if (var == IT) \
725 ch = 0x5d; \
726 else if (var == SE2) \
727 ch = 0x60; \
728 else \
729 failure = __GCONV_ILLEGAL_INPUT; \
730 break; \
731 case 0xea: \
732 if (var != CA && var != CA2) \
733 failure = __GCONV_ILLEGAL_INPUT; \
734 ch = 0x5d; \
735 break; \
736 case 0xec: \
737 if (var != IT) \
738 failure = __GCONV_ILLEGAL_INPUT; \
739 ch = 0x7e; \
740 break; \
741 case 0xee: \
742 if (var != CA) \
743 failure = __GCONV_ILLEGAL_INPUT; \
744 ch = 0x5e; \
745 break; \
746 case 0xf1: \
747 if (var != ES && var != ES2 && var != CU) \
748 failure = __GCONV_ILLEGAL_INPUT; \
749 ch = 0x7c; \
750 break; \
751 case 0xf2: \
752 if (var != IT) \
753 failure = __GCONV_ILLEGAL_INPUT; \
754 ch = 0x7c; \
755 break; \
756 case 0xf4: \
757 if (var != CA && var != CA2) \
758 failure = __GCONV_ILLEGAL_INPUT; \
759 ch = 0x60; \
760 break; \
761 case 0xf5: \
762 if (var != PT && var != PT2) \
763 failure = __GCONV_ILLEGAL_INPUT; \
764 ch = 0x7d; \
765 break; \
766 case 0xf6: \
767 if (var != DE && var != HU && var != SE && var != SE2) \
768 failure = __GCONV_ILLEGAL_INPUT; \
769 ch = 0x7c; \
770 break; \
771 case 0xf8: \
772 if (var != DK && var != NO && var != NO2) \
773 failure = __GCONV_ILLEGAL_INPUT; \
774 ch = 0x7c; \
775 break; \
776 case 0xf9: \
777 if (var == CA || var == CA2 || var == FR || var == FR1) \
778 ch = 0x7c; \
779 else if (var == IT) \
780 ch = 0x60; \
781 else \
782 failure = __GCONV_ILLEGAL_INPUT; \
783 break; \
784 case 0xfb: \
785 if (var != CA && var != CA2) \
786 failure = __GCONV_ILLEGAL_INPUT; \
787 ch = 0x7e; \
788 break; \
789 case 0xfc: \
790 if (var == DE || var == HU) \
791 ch = 0x7d; \
792 else if (var == SE2) \
793 ch = 0x7e; \
794 else \
795 failure = __GCONV_ILLEGAL_INPUT; \
796 break; \
797 case 0x160: \
798 if (var != YU) \
799 failure = __GCONV_ILLEGAL_INPUT; \
800 ch = 0x5b; \
801 break; \
802 case 0x106: \
803 if (var != YU) \
804 failure = __GCONV_ILLEGAL_INPUT; \
805 ch = 0x5d; \
806 break; \
807 case 0x107: \
808 if (var != YU) \
809 failure = __GCONV_ILLEGAL_INPUT; \
810 ch = 0x7d; \
811 break; \
812 case 0x10c: \
813 if (var != YU) \
814 failure = __GCONV_ILLEGAL_INPUT; \
815 ch = 0x5e; \
816 break; \
817 case 0x10d: \
818 if (var != YU) \
819 failure = __GCONV_ILLEGAL_INPUT; \
820 ch = 0x7e; \
821 break; \
822 case 0x110: \
823 if (var != YU) \
824 failure = __GCONV_ILLEGAL_INPUT; \
825 ch = 0x5c; \
826 break; \
827 case 0x111: \
828 if (var != YU) \
829 failure = __GCONV_ILLEGAL_INPUT; \
830 ch = 0x7c; \
831 break; \
832 case 0x161: \
833 if (var != YU) \
834 failure = __GCONV_ILLEGAL_INPUT; \
835 ch = 0x7b; \
836 break; \
837 case 0x17d: \
838 if (var != YU) \
839 failure = __GCONV_ILLEGAL_INPUT; \
840 ch = 0x40; \
841 break; \
842 case 0x17e: \
843 if (var != YU) \
844 failure = __GCONV_ILLEGAL_INPUT; \
845 ch = 0x60; \
846 break; \
847 case 0x2dd: \
848 if (var != HU) \
849 failure = __GCONV_ILLEGAL_INPUT; \
850 ch = 0x7e; \
851 break; \
852 case 0x2022: \
853 if (var != ES2) \
854 failure = __GCONV_ILLEGAL_INPUT; \
855 ch = 0x40; \
856 break; \
857 case 0x203e: \
858 if (var != GB && var != CN && var != JP && var != NO && var != SE) \
859 failure = __GCONV_ILLEGAL_INPUT; \
860 ch = 0x7e; \
861 break; \
862 case 0x20a9: \
863 if (var != KR) \
864 failure = __GCONV_ILLEGAL_INPUT; \
865 ch = 0x5c; \
866 break; \
867 case 0x2329: \
868 if (var != JP_OCR_B) \
869 failure = __GCONV_ILLEGAL_INPUT; \
870 ch = 0x5b; \
871 break; \
872 case 0x232a: \
873 if (var != JP_OCR_B) \
874 failure = __GCONV_ILLEGAL_INPUT; \
875 ch = 0x5d; \
876 break; \
877 default: \
878 if (__glibc_unlikely (ch > 0x7f)) \
879 { \
880 UNICODE_TAG_HANDLER (ch, 4); \
881 failure = __GCONV_ILLEGAL_INPUT; \
882 } \
883 break; \
884 } \
885 \
886 if (__builtin_expect (failure, __GCONV_OK) == __GCONV_ILLEGAL_INPUT) \
887 { \
888 STANDARD_TO_LOOP_ERR_HANDLER (4); \
889 } \
890 \
891 *outptr++ = (unsigned char) ch; \
892 inptr += 4; \
893 }
894 #define LOOP_NEED_FLAGS
895 #define EXTRA_LOOP_DECLS , enum variant var
896 #include <iconv/loop.c>
897
898
899 /* Now define the toplevel functions. */
900 #include <iconv/skeleton.c>
901