2 * Copyright 1992, 1993 by TOSHIBA Corp.
4 * Permission to use, copy, modify, and distribute this software and its
5 * documentation for any purpose and without fee is hereby granted, provided
6 * that the above copyright notice appear in all copies and that both that
7 * copyright notice and this permission notice appear in supporting
8 * documentation, and that the name of TOSHIBA not be used in advertising
9 * or publicity pertaining to distribution of the software without specific,
10 * written prior permission. TOSHIBA make no representations about the
11 * suitability of this software for any purpose. It is provided "as is"
12 * without express or implied warranty.
14 * TOSHIBA DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
15 * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
16 * TOSHIBA BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
17 * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
18 * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
19 * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
22 * Author: Katsuhisa Yano TOSHIBA Corp.
23 * mopi@osa.ilab.toshiba.co.jp
33 typedef struct _XlcConverterListRec {
40 XlcOpenConverterProc converter;
41 struct _XlcConverterListRec *next;
42 } XlcConverterListRec, *XlcConverterList;
44 static XlcConverterList conv_list = NULL;
50 (*conv->methods->close)(conv);
60 XlcConverterList list, prev = NULL;
62 for (list = conv_list; list; list = list->next) {
63 if (list->from_lcd == from_lcd && list->to_lcd == to_lcd
64 && list->from_type == from_type && list->to_type == to_type) {
66 if (prev && prev != conv_list) { /* XXX */
67 prev->next = list->next;
68 list->next = conv_list;
72 return (*list->converter)(from_lcd, list->from, to_lcd, list->to);
78 return (XlcConv) NULL;
87 XlcOpenConverterProc converter)
89 XlcConverterList list;
90 XrmQuark from_type, to_type;
92 from_type = XrmStringToQuark(from);
93 to_type = XrmStringToQuark(to);
95 for (list = conv_list; list; list = list->next) {
96 if (list->from_lcd == from_lcd && list->to_lcd == to_lcd
97 && list->from_type == from_type && list->to_type == to_type) {
99 list->converter = converter;
104 list = (XlcConverterList) Xmalloc(sizeof(XlcConverterListRec));
108 list->from_lcd = from_lcd;
110 list->from_type = from_type;
111 list->to_lcd = to_lcd;
113 list->to_type = to_type;
114 list->converter = converter;
115 list->next = conv_list;
121 typedef struct _ConvRec {
136 Conv conv = (Conv) lc_conv->state;
137 XlcConv from_conv = conv->from_conv;
138 XlcConv to_conv = conv->to_conv;
140 char buf[BUFSIZ], *cs;
141 XPointer tmp_args[1];
142 int cs_left, ret, length, unconv_num = 0;
144 if (from == NULL || *from == NULL) {
145 if (from_conv->methods->reset)
146 (*from_conv->methods->reset)(from_conv);
148 if (to_conv->methods->reset)
149 (*to_conv->methods->reset)(to_conv);
154 while (*from_left > 0) {
157 tmp_args[0] = (XPointer) &charset;
159 ret = (*from_conv->methods->convert)(from_conv, from, from_left, &cs,
160 &cs_left, tmp_args, 1);
171 tmp_args[0] = (XPointer) charset;
173 ret = (*to_conv->methods->convert)(to_conv, &cs, &cs_left, to, to_left,
176 unconv_num += length / (charset->char_size > 0 ? charset->char_size : 1);
191 close_indirect_converter(
194 Conv conv = (Conv) lc_conv->state;
198 close_converter(conv->from_conv);
200 close_converter(conv->to_conv);
202 Xfree((char *) conv);
205 Xfree((char *) lc_conv);
209 reset_indirect_converter(
212 Conv conv = (Conv) lc_conv->state;
215 if (conv->from_conv && conv->from_conv->methods->reset)
216 (*conv->from_conv->methods->reset)(conv->from_conv);
217 if (conv->to_conv && conv->to_conv->methods->reset)
218 (*conv->to_conv->methods->reset)(conv->to_conv);
222 static XlcConvMethodsRec conv_methods = {
223 close_indirect_converter,
225 reset_indirect_converter
229 open_indirect_converter(
235 XlcConv lc_conv, from_conv, to_conv;
237 XrmQuark from_type, to_type;
238 static XrmQuark QChar, QCharSet, QCTCharSet = (XrmQuark) 0;
240 if (QCTCharSet == (XrmQuark) 0) {
241 QCTCharSet = XrmStringToQuark(XlcNCTCharSet);
242 QCharSet = XrmStringToQuark(XlcNCharSet);
243 QChar = XrmStringToQuark(XlcNChar);
246 from_type = XrmStringToQuark(from);
247 to_type = XrmStringToQuark(to);
249 if (from_type == QCharSet || from_type == QChar || to_type == QCharSet ||
251 return (XlcConv) NULL;
253 lc_conv = (XlcConv) Xmalloc(sizeof(XlcConvRec));
255 return (XlcConv) NULL;
257 lc_conv->methods = &conv_methods;
259 lc_conv->state = (XPointer) Xcalloc(1, sizeof(ConvRec));
260 if (lc_conv->state == NULL)
263 conv = (Conv) lc_conv->state;
265 from_conv = get_converter(from_lcd, from_type, from_lcd, QCTCharSet);
266 if (from_conv == NULL)
267 from_conv = get_converter(from_lcd, from_type, from_lcd, QCharSet);
268 if (from_conv == NULL)
269 from_conv = get_converter((XLCd)NULL, from_type, (XLCd)NULL, QCharSet);
270 if (from_conv == NULL)
271 from_conv = get_converter(from_lcd, from_type, from_lcd, QChar);
272 if (from_conv == NULL)
274 conv->from_conv = from_conv;
276 to_conv = get_converter(to_lcd, QCTCharSet, to_lcd, to_type);
278 to_conv = get_converter(to_lcd, QCharSet, to_lcd, to_type);
280 to_conv = get_converter((XLCd) NULL, QCharSet, (XLCd) NULL, to_type);
283 conv->to_conv = to_conv;
288 close_indirect_converter(lc_conv);
290 return (XlcConv) NULL;
301 XrmQuark from_type, to_type;
303 from_type = XrmStringToQuark(from);
304 to_type = XrmStringToQuark(to);
306 if ((conv = get_converter(from_lcd, from_type, to_lcd, to_type)))
309 return open_indirect_converter(from_lcd, from, to_lcd, to);
316 close_converter(conv);
329 return (*conv->methods->convert)(conv, from, from_left, to, to_left, args,
337 if (conv->methods->reset)
338 (*conv->methods->reset)(conv);