Annotation of embedaddon/libiconv/lib/iso2022_jp1.h, revision 1.1.1.1
1.1 misho 1: /*
2: * Copyright (C) 1999-2001, 2008 Free Software Foundation, Inc.
3: * This file is part of the GNU LIBICONV Library.
4: *
5: * The GNU LIBICONV Library is free software; you can redistribute it
6: * and/or modify it under the terms of the GNU Library General Public
7: * License as published by the Free Software Foundation; either version 2
8: * of the License, or (at your option) any later version.
9: *
10: * The GNU LIBICONV Library is distributed in the hope that it will be
11: * useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
12: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13: * Library General Public License for more details.
14: *
15: * You should have received a copy of the GNU Library General Public
16: * License along with the GNU LIBICONV Library; see the file COPYING.LIB.
17: * If not, write to the Free Software Foundation, Inc., 51 Franklin Street,
18: * Fifth Floor, Boston, MA 02110-1301, USA.
19: */
20:
21: /*
22: * ISO-2022-JP-1
23: */
24:
25: /* Specification: RFC 2237 */
26:
27: #define ESC 0x1b
28:
29: /*
30: * The state can be one of the following values.
31: */
32: #define STATE_ASCII 0
33: #define STATE_JISX0201ROMAN 1
34: #define STATE_JISX0208 2
35: #define STATE_JISX0212 3
36:
37: static int
38: iso2022_jp1_mbtowc (conv_t conv, ucs4_t *pwc, const unsigned char *s, int n)
39: {
40: state_t state = conv->istate;
41: int count = 0;
42: unsigned char c;
43: for (;;) {
44: c = *s;
45: if (c == ESC) {
46: if (n < count+3)
47: goto none;
48: if (s[1] == '(') {
49: if (s[2] == 'B') {
50: state = STATE_ASCII;
51: s += 3; count += 3;
52: if (n < count+1)
53: goto none;
54: continue;
55: }
56: if (s[2] == 'J') {
57: state = STATE_JISX0201ROMAN;
58: s += 3; count += 3;
59: if (n < count+1)
60: goto none;
61: continue;
62: }
63: goto ilseq;
64: }
65: if (s[1] == '$') {
66: if (s[2] == '@' || s[2] == 'B') {
67: /* We don't distinguish JIS X 0208-1978 and JIS X 0208-1983. */
68: state = STATE_JISX0208;
69: s += 3; count += 3;
70: if (n < count+1)
71: goto none;
72: continue;
73: }
74: if (s[2] == '(') {
75: if (n < count+4)
76: goto none;
77: if (s[3] == 'D') {
78: state = STATE_JISX0212;
79: s += 4; count += 4;
80: if (n < count+1)
81: goto none;
82: continue;
83: }
84: }
85: goto ilseq;
86: }
87: goto ilseq;
88: }
89: break;
90: }
91: switch (state) {
92: case STATE_ASCII:
93: if (c < 0x80) {
94: int ret = ascii_mbtowc(conv,pwc,s,1);
95: if (ret == RET_ILSEQ)
96: goto ilseq;
97: if (ret != 1) abort();
98: conv->istate = state;
99: return count+1;
100: } else
101: goto ilseq;
102: case STATE_JISX0201ROMAN:
103: if (c < 0x80) {
104: int ret = jisx0201_mbtowc(conv,pwc,s,1);
105: if (ret == RET_ILSEQ)
106: goto ilseq;
107: if (ret != 1) abort();
108: conv->istate = state;
109: return count+1;
110: } else
111: goto ilseq;
112: case STATE_JISX0208:
113: if (n < count+2)
114: goto none;
115: if (s[0] < 0x80 && s[1] < 0x80) {
116: int ret = jisx0208_mbtowc(conv,pwc,s,2);
117: if (ret == RET_ILSEQ)
118: goto ilseq;
119: if (ret != 2) abort();
120: conv->istate = state;
121: return count+2;
122: } else
123: goto ilseq;
124: case STATE_JISX0212:
125: if (n < count+2)
126: goto none;
127: if (s[0] < 0x80 && s[1] < 0x80) {
128: int ret = jisx0212_mbtowc(conv,pwc,s,2);
129: if (ret == RET_ILSEQ)
130: goto ilseq;
131: if (ret != 2) abort();
132: conv->istate = state;
133: return count+2;
134: } else
135: goto ilseq;
136: default: abort();
137: }
138:
139: none:
140: conv->istate = state;
141: return RET_TOOFEW(count);
142:
143: ilseq:
144: conv->istate = state;
145: return RET_SHIFT_ILSEQ(count);
146: }
147:
148: static int
149: iso2022_jp1_wctomb (conv_t conv, unsigned char *r, ucs4_t wc, int n)
150: {
151: state_t state = conv->ostate;
152: unsigned char buf[2];
153: int ret;
154:
155: /* Try ASCII. */
156: ret = ascii_wctomb(conv,buf,wc,1);
157: if (ret != RET_ILUNI) {
158: if (ret != 1) abort();
159: if (buf[0] < 0x80) {
160: int count = (state == STATE_ASCII ? 1 : 4);
161: if (n < count)
162: return RET_TOOSMALL;
163: if (state != STATE_ASCII) {
164: r[0] = ESC;
165: r[1] = '(';
166: r[2] = 'B';
167: r += 3;
168: state = STATE_ASCII;
169: }
170: r[0] = buf[0];
171: conv->ostate = state;
172: return count;
173: }
174: }
175:
176: /* Try JIS X 0201-1976 Roman. */
177: ret = jisx0201_wctomb(conv,buf,wc,1);
178: if (ret != RET_ILUNI) {
179: if (ret != 1) abort();
180: if (buf[0] < 0x80) {
181: int count = (state == STATE_JISX0201ROMAN ? 1 : 4);
182: if (n < count)
183: return RET_TOOSMALL;
184: if (state != STATE_JISX0201ROMAN) {
185: r[0] = ESC;
186: r[1] = '(';
187: r[2] = 'J';
188: r += 3;
189: state = STATE_JISX0201ROMAN;
190: }
191: r[0] = buf[0];
192: conv->ostate = state;
193: return count;
194: }
195: }
196:
197: /* Try JIS X 0208-1990 in place of JIS X 0208-1978 and JIS X 0208-1983. */
198: ret = jisx0208_wctomb(conv,buf,wc,2);
199: if (ret != RET_ILUNI) {
200: if (ret != 2) abort();
201: if (buf[0] < 0x80 && buf[1] < 0x80) {
202: int count = (state == STATE_JISX0208 ? 2 : 5);
203: if (n < count)
204: return RET_TOOSMALL;
205: if (state != STATE_JISX0208) {
206: r[0] = ESC;
207: r[1] = '$';
208: r[2] = 'B';
209: r += 3;
210: state = STATE_JISX0208;
211: }
212: r[0] = buf[0];
213: r[1] = buf[1];
214: conv->ostate = state;
215: return count;
216: }
217: }
218:
219: /* Try JIS X 0212-1990. */
220: ret = jisx0212_wctomb(conv,buf,wc,2);
221: if (ret != RET_ILUNI) {
222: if (ret != 2) abort();
223: if (buf[0] < 0x80 && buf[1] < 0x80) {
224: int count = (state == STATE_JISX0212 ? 2 : 6);
225: if (n < count)
226: return RET_TOOSMALL;
227: if (state != STATE_JISX0212) {
228: r[0] = ESC;
229: r[1] = '$';
230: r[2] = '(';
231: r[3] = 'D';
232: r += 4;
233: state = STATE_JISX0212;
234: }
235: r[0] = buf[0];
236: r[1] = buf[1];
237: conv->ostate = state;
238: return count;
239: }
240: }
241:
242: return RET_ILUNI;
243: }
244:
245: static int
246: iso2022_jp1_reset (conv_t conv, unsigned char *r, int n)
247: {
248: state_t state = conv->ostate;
249: if (state != STATE_ASCII) {
250: if (n < 3)
251: return RET_TOOSMALL;
252: r[0] = ESC;
253: r[1] = '(';
254: r[2] = 'B';
255: /* conv->ostate = 0; will be done by the caller */
256: return 3;
257: } else
258: return 0;
259: }
260:
261: #undef STATE_JISX0212
262: #undef STATE_JISX0208
263: #undef STATE_JISX0201ROMAN
264: #undef STATE_ASCII
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>