Remove pre-2.4 Linux kernel support.
[platform/upstream/glibc.git] / iconvdata / euc-tw.c
1 /* Mapping tables for EUC-TW handling.
2    Copyright (C) 1998, 1999, 2000-2002, 2003, 2007
3    Free Software Foundation, Inc.
4    This file is part of the GNU C Library.
5    Contributed by Ulrich Drepper <drepper@cygnus.com>, 1998.
6
7    The GNU C Library is free software; you can redistribute it and/or
8    modify it under the terms of the GNU Lesser General Public
9    License as published by the Free Software Foundation; either
10    version 2.1 of the License, or (at your option) any later version.
11
12    The GNU C Library 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 GNU
15    Lesser General Public License for more details.
16
17    You should have received a copy of the GNU Lesser General Public
18    License along with the GNU C Library; if not, see
19    <http://www.gnu.org/licenses/>.  */
20
21 #include <dlfcn.h>
22 #include <stdint.h>
23 #include <cns11643l1.h>
24 #include <cns11643.h>
25
26 /* Definitions used in the body of the `gconv' function.  */
27 #define CHARSET_NAME            "EUC-TW//"
28 #define FROM_LOOP               from_euc_tw
29 #define TO_LOOP                 to_euc_tw
30 #define DEFINE_INIT             1
31 #define DEFINE_FINI             1
32 #define MIN_NEEDED_FROM         1
33 #define MAX_NEEDED_FROM         4
34 #define MIN_NEEDED_TO           4
35
36
37 /* First define the conversion function from EUC-TW to UCS4.  */
38 #define MIN_NEEDED_INPUT        MIN_NEEDED_FROM
39 #define MAX_NEEDED_INPUT        MAX_NEEDED_FROM
40 #define MIN_NEEDED_OUTPUT       MIN_NEEDED_TO
41 #define LOOPFCT                 FROM_LOOP
42 #define BODY \
43   {                                                                           \
44     uint32_t ch = *inptr;                                                     \
45                                                                               \
46     if (ch <= 0x7f)                                                           \
47       /* Plain ASCII.  */                                                     \
48       ++inptr;                                                                \
49     else if ((ch <= 0xa0 || ch > 0xfe) && ch != 0x8e)                         \
50       {                                                                       \
51         /* This is illegal.  */                                               \
52         STANDARD_FROM_LOOP_ERR_HANDLER (1);                                   \
53       }                                                                       \
54     else                                                                      \
55       {                                                                       \
56         /* Two or more byte character.  First test whether the next byte      \
57            is also available.  */                                             \
58         uint32_t ch2;                                                         \
59                                                                               \
60         if (inptr + 1 >= inend)                                               \
61           {                                                                   \
62             /* The second byte is not available.  Store the intermediate      \
63                result.  */                                                    \
64             result = __GCONV_INCOMPLETE_INPUT;                                \
65             break;                                                            \
66           }                                                                   \
67                                                                               \
68         ch2 = *(inptr + 1);                                                   \
69                                                                               \
70         /* All second bytes of a multibyte character must be >= 0xa1. */      \
71         if (ch2 < 0xa1 || ch2 == 0xff)                                        \
72           STANDARD_FROM_LOOP_ERR_HANDLER (1);                                 \
73                                                                               \
74         if (ch == 0x8e)                                                       \
75           {                                                                   \
76             /* This is code set 2: CNS 11643, planes 1 to 16.  */             \
77             const unsigned char *endp = inptr + 1;                            \
78                                                                               \
79             ch = cns11643_to_ucs4 (&endp, inend - inptr - 1, 0x80);           \
80                                                                               \
81             if (ch == 0)                                                      \
82               {                                                               \
83                 /* The third or fourth byte is not available.  Store          \
84                    the intermediate result.  */                               \
85                 result = __GCONV_INCOMPLETE_INPUT;                            \
86                 break;                                                        \
87               }                                                               \
88                                                                               \
89             if (ch == __UNKNOWN_10646_CHAR)                                   \
90               /* Illegal input.  */                                           \
91               STANDARD_FROM_LOOP_ERR_HANDLER (1);                             \
92                                                                               \
93             inptr += 4;                                                       \
94           }                                                                   \
95         else                                                                  \
96           {                                                                   \
97             /* This is code set 1: CNS 11643, plane 1.  */                    \
98             const unsigned char *endp = inptr;                                \
99                                                                               \
100             ch = cns11643l1_to_ucs4 (&endp, inend - inptr, 0x80);             \
101             /* Please note that we need not test for the missing input        \
102                characters here anymore.  */                                   \
103             if (ch == __UNKNOWN_10646_CHAR)                                   \
104               /* Illegal input.  */                                           \
105               STANDARD_FROM_LOOP_ERR_HANDLER (2);                             \
106                                                                               \
107             inptr += 2;                                                       \
108           }                                                                   \
109       }                                                                       \
110                                                                               \
111     put32 (outptr, ch);                                                       \
112     outptr += 4;                                                              \
113   }
114 #define LOOP_NEED_FLAGS
115 #define ONEBYTE_BODY \
116   {                                                                           \
117     if (c < 0x80)                                                             \
118       return c;                                                               \
119     else                                                                      \
120       return WEOF;                                                            \
121   }
122 #include <iconv/loop.c>
123
124
125 /* Next, define the other direction.  */
126 #define MIN_NEEDED_INPUT        MIN_NEEDED_TO
127 #define MIN_NEEDED_OUTPUT       MIN_NEEDED_FROM
128 #define MAX_NEEDED_OUTPUT       MAX_NEEDED_FROM
129 #define LOOPFCT                 TO_LOOP
130 #define BODY \
131   {                                                                           \
132     uint32_t ch = get32 (inptr);                                              \
133                                                                               \
134     if (ch <= 0x7f)                                                           \
135       /* It's plain ASCII.  */                                                \
136       *outptr++ = ch;                                                         \
137     else                                                                      \
138       {                                                                       \
139         /* Try the CNS 11643 planes.  */                                      \
140         size_t found;                                                         \
141                                                                               \
142         found = ucs4_to_cns11643l1 (ch, outptr, outend - outptr);             \
143         if (__builtin_expect (found, 1) == 0)                                 \
144           {                                                                   \
145             /* We ran out of space.  */                                       \
146             result = __GCONV_FULL_OUTPUT;                                     \
147             break;                                                            \
148           }                                                                   \
149         if (__builtin_expect (found, 1) != __UNKNOWN_10646_CHAR)              \
150           {                                                                   \
151             /* It's a CNS 11643, plane 1 character, adjust it for EUC-TW.  */ \
152             *outptr++ += 0x80;                                                \
153             *outptr++ += 0x80;                                                \
154           }                                                                   \
155         else                                                                  \
156           {                                                                   \
157             /* No CNS 11643, plane 1 character.  */                           \
158                                                                               \
159             found = ucs4_to_cns11643 (ch, outptr + 1, outend - outptr - 1);   \
160             if (__builtin_expect (found, 1) == 0)                             \
161               {                                                               \
162                 /* We ran out of space.  */                                   \
163                 result = __GCONV_FULL_OUTPUT;                                 \
164                 break;                                                        \
165               }                                                               \
166             if (__builtin_expect (found, 0) == __UNKNOWN_10646_CHAR)          \
167               {                                                               \
168                 UNICODE_TAG_HANDLER (ch, 4);                                  \
169                                                                               \
170                 /* Illegal character.  */                                     \
171                 STANDARD_TO_LOOP_ERR_HANDLER (4);                             \
172               }                                                               \
173                                                                               \
174             /* It's a CNS 11643 character, adjust it for EUC-TW.  */          \
175             *outptr++ = '\x8e';                                               \
176             *outptr++ += 0xa0;                                                \
177             *outptr++ += 0x80;                                                \
178             *outptr++ += 0x80;                                                \
179           }                                                                   \
180       }                                                                       \
181                                                                               \
182     inptr += 4;                                                               \
183   }
184 #define LOOP_NEED_FLAGS
185 #include <iconv/loop.c>
186
187
188 /* Now define the toplevel functions.  */
189 #include <iconv/skeleton.c>