Imported Upstream version 2.0.14
[platform/upstream/SDL.git] / src / core / os2 / geniconv / os2cp.c
1 /*
2   Simple DirectMedia Layer
3   Copyright (C) 1997-2020 Sam Lantinga <slouken@libsdl.org>
4
5   This software is provided 'as-is', without any express or implied
6   warranty.  In no event will the authors be held liable for any damages
7   arising from the use of this software.
8
9   Permission is granted to anyone to use this software for any purpose,
10   including commercial applications, and to alter it and redistribute it
11   freely, subject to the following restrictions:
12
13   1. The origin of this software must not be misrepresented; you must not
14      claim that you wrote the original software. If you use this software
15      in a product, an acknowledgment in the product documentation would be
16      appreciated but is not required.
17   2. Altered source versions must be plainly marked as such, and must not be
18      misrepresented as being the original software.
19   3. This notice may not be removed or altered from any source distribution.
20 */
21
22 #define INCL_DOSNLS
23 #define INCL_DOSERRORS
24 #include <os2.h>
25 #include <string.h>
26 #include <ctype.h>
27
28 #include "os2cp.h"
29
30 typedef struct _CP2NAME {
31   ULONG ulCode;
32   PSZ  pszName;
33 } CP2NAME;
34
35 typedef struct _NAME2CP {
36   PSZ  pszName;
37   ULONG ulCode;
38 } NAME2CP;
39
40 static CP2NAME aCP2Name[] = {
41   {367, "ANSI_X3.4-1968"},
42   {813, "ECMA-118"},
43   {819, "CP819"},
44   {850, "850"},
45   {862, "862"},
46   {866, "866"},
47   {874, "ISO-IR-166"},
48   {878, "KOI8-R"},
49   {896, "JISX0201-1976"},
50   {901, "ISO-8859-13"},
51   {912, "ISO-8859-2"},
52   {913, "ISO-8859-3"},
53   {914, "ISO-8859-4"},
54   {915, "CYRILLIC"},
55   {920, "ISO-8859-9"},
56   {923, "ISO-8859-15"},
57   {943, "MS_KANJI"},
58   {954, "EUC-JP"},
59   {964, "EUC-TW"},
60   {970, "EUC-KR"},
61   {1051, "HP-ROMAN8"},
62   {1089, "ARABIC"},
63   {1129, "VISCII"},
64   {1168, "KOI8-U"},
65   {1200, "ISO-10646-UCS-2"},
66   {1202, "UTF-16LE"},
67   {1204, "UCS-2BE"},
68   {1208, "UTF-8"},
69   {1232, "UTF-32BE"},
70   {1234, "UTF-32LE"},
71   {1236, "ISO-10646-UCS-4"},
72   {1250, "CP1250"},
73   {1251, "CP1251"},
74   {1252, "CP1252"},
75   {1253, "CP1253"},
76   {1254, "CP1254"},
77   {1255, "CP1255"},
78   {1256, "CP1256"},
79   {1257, "CP1257"},
80   {1275, "MAC"},
81   {1383, "CN-GB"},
82   {1386, "GBK"},
83   {1392, "GB18030"},
84   {62210, "HEBREW"}
85 };
86
87 static NAME2CP aName2CP[] = {
88   {"850", 850},
89   {"862", 862},
90   {"866", 866},
91   {"ANSI_X3.4-1968", 367},
92   {"ANSI_X3.4-1986", 367},
93   {"ARABIC", 1089},
94   {"ASCII", 367},
95   {"ASMO-708", 1089},
96   {"CN-GB", 1383},
97   {"CP1250", 1250},
98   {"CP1251", 1251},
99   {"CP1252", 1252},
100   {"CP1253", 1253},
101   {"CP1254", 1254},
102   {"CP1255", 1255},
103   {"CP1256", 1256},
104   {"CP1257", 1257},
105   {"CP367", 367},
106   {"CP819", 819},
107   {"CP850", 850},
108   {"CP862", 862},
109   {"CP866", 866},
110   {"CP936", 1386},
111   {"CSASCII", 367},
112   {"CSEUCKR", 970},
113   {"CSEUCPKDFMTJAPANESE", 954},
114   {"CSEUCTW", 964},
115   {"CSGB2312", 1383},
116   {"CSHALFWIDTHKATAKANA", 896},
117   {"CSHPROMAN8", 1051},
118   {"CSIBM866", 866},
119   {"CSISOLATIN1", 819},
120   {"CSISOLATIN2", 912},
121   {"CSISOLATIN3", 913},
122   {"CSISOLATIN4", 914},
123   {"CSISOLATIN5", 920},
124   {"CSISOLATINARABIC", 1089},
125   {"CSISOLATINCYRILLIC", 915},
126   {"CSISOLATINGREEK", 813},
127   {"CSISOLATINHEBREW", 62210},
128   {"CSKOI8R", 878},
129   {"CSKSC56011987", 970},
130   {"CSMACINTOSH", 1275},
131   {"CSPC850MULTILINGUAL", 850},
132   {"CSPC862LATINHEBREW", 862},
133   {"CSSHIFTJIS", 943},
134   {"CSUCS4", 1236},
135   {"CSUNICODE", 1200},
136   {"CSUNICODE11", 1204},
137   {"CSVISCII", 1129},
138   {"CYRILLIC", 915},
139   {"ECMA-114", 1089},
140   {"ECMA-118", 813},
141   {"ELOT_928", 813},
142   {"EUC-CN", 1383},
143   {"EUC-JP", 954},
144   {"EUC-KR", 970},
145   {"EUC-TW", 964},
146   {"EUCCN", 1383},
147   {"EUCJP", 954},
148   {"EUCKR", 970},
149   {"EUCTW", 964},
150   {"EXTENDED_UNIX_CODE_PACKED_FORMAT_FOR_JAPANESE", 954},
151   {"GB18030", 1392},
152   {"GB2312", 1383},
153   {"GBK", 1386},
154   {"GREEK", 813},
155   {"GREEK8", 813},
156   {"HEBREW", 62210},
157   {"HP-ROMAN8", 1051},
158   {"IBM367", 367},
159   {"IBM819", 819},
160   {"IBM850", 850},
161   {"IBM862", 862},
162   {"IBM866", 866},
163   {"ISO-10646-UCS-2", 1200},
164   {"ISO-10646-UCS-4", 1236},
165   {"ISO-8859-1", 819},
166   {"ISO-8859-13", 901},
167   {"ISO-8859-15", 923},
168   {"ISO-8859-2", 912},
169   {"ISO-8859-3", 913},
170   {"ISO-8859-4", 914},
171   {"ISO-8859-5", 915},
172   {"ISO-8859-6", 1089},
173   {"ISO-8859-7", 813},
174   {"ISO-8859-8", 62210},
175   {"ISO-8859-9", 920},
176   {"ISO-IR-100", 819},
177   {"ISO-IR-101", 912},
178   {"ISO-IR-109", 913},
179   {"ISO-IR-110", 914},
180   {"ISO-IR-126", 813},
181   {"ISO-IR-127", 1089},
182   {"ISO-IR-138", 62210},
183   {"ISO-IR-144", 915},
184   {"ISO-IR-148", 920},
185   {"ISO-IR-149", 970},
186   {"ISO-IR-166", 874},
187   {"ISO-IR-179", 901},
188   {"ISO-IR-203", 923},
189   {"ISO-IR-6", 367},
190   {"ISO646-US", 367},
191   {"ISO8859-1", 819},
192   {"ISO8859-13", 901},
193   {"ISO8859-15", 923},
194   {"ISO8859-2", 912},
195   {"ISO8859-3", 913},
196   {"ISO8859-4", 914},
197   {"ISO8859-5", 915},
198   {"ISO8859-6", 1089},
199   {"ISO8859-7", 813},
200   {"ISO8859-8", 62210},
201   {"ISO8859-9", 920},
202   {"ISO_646.IRV:1991", 367},
203   {"ISO_8859-1", 819},
204   {"ISO_8859-13", 901},
205   {"ISO_8859-15", 923},
206   {"ISO_8859-15:1998", 923},
207   {"ISO_8859-1:1987", 819},
208   {"ISO_8859-2", 912},
209   {"ISO_8859-2:1987", 912},
210   {"ISO_8859-3", 913},
211   {"ISO_8859-3:1988", 913},
212   {"ISO_8859-4", 914},
213   {"ISO_8859-4:1988", 914},
214   {"ISO_8859-5", 915},
215   {"ISO_8859-5:1988", 915},
216   {"ISO_8859-6", 1089},
217   {"ISO_8859-6:1987", 1089},
218   {"ISO_8859-7", 813},
219   {"ISO_8859-7:1987", 813},
220   {"ISO_8859-7:2003", 813},
221   {"ISO_8859-8", 62210},
222   {"ISO_8859-8:1988", 62210},
223   {"ISO_8859-9", 920},
224   {"ISO_8859-9:1989", 920},
225   {"JISX0201-1976", 896},
226   {"JIS_X0201", 896},
227   {"KOI8-R", 878},
228   {"KOI8-U", 1168},
229   {"KOREAN", 970},
230   {"KSC_5601", 970},
231   {"KS_C_5601-1987", 970},
232   {"KS_C_5601-1989", 970},
233   {"L1", 819},
234   {"L2", 912},
235   {"L3", 913},
236   {"L4", 914},
237   {"L5", 920},
238   {"L7", 901},
239   {"LATIN-9", 923},
240   {"LATIN1", 819},
241   {"LATIN2", 912},
242   {"LATIN3", 913},
243   {"LATIN4", 914},
244   {"LATIN5", 920},
245   {"LATIN7", 901},
246   {"MAC", 1275},
247   {"MACINTOSH", 1275},
248   {"MACROMAN", 1275},
249   {"MS-ANSI", 1252},
250   {"MS-ARAB", 1256},
251   {"MS-CYRL", 1251},
252   {"MS-EE", 1250},
253   {"MS-GREEK", 1253},
254   {"MS-HEBR", 1255},
255   {"MS-TURK", 1254},
256   {"MS936", 1386},
257   {"MS_KANJI", 943},
258   {"R8", 1051},
259   {"ROMAN8", 1051},
260   {"SHIFT-JIS", 943},
261   {"SHIFT_JIS", 943},
262   {"SJIS", 943},
263   {"TIS-620", 874},
264   {"TIS620", 874},
265   {"TIS620-0", 874},
266   {"TIS620.2529-1", 874},
267   {"TIS620.2533-0", 874},
268   {"TIS620.2533-1", 874},
269   {"UCS-2", 1200},
270   {"UCS-2BE", 1204},
271   {"UCS-4", 1236},
272   {"UNICODE-1-1", 1204},
273   {"UNICODEBIG", 1204},
274   {"US", 367},
275   {"US-ASCII", 367},
276   {"UTF-16", 1204},
277   {"UTF-16BE", 1200},
278   {"UTF-16LE", 1202},
279   {"UTF-32", 1236},
280   {"UTF-32BE", 1232},
281   {"UTF-32LE", 1234},
282   {"UTF-8", 1208},
283   {"VISCII", 1129},
284   {"VISCII1.1-1", 1129},
285   {"WINBALTRIM", 1257},
286   {"WINDOWS-1250", 1250},
287   {"WINDOWS-1251", 1251},
288   {"WINDOWS-1252", 1252},
289   {"WINDOWS-1253", 1253},
290   {"WINDOWS-1254", 1254},
291   {"WINDOWS-1255", 1255},
292   {"WINDOWS-1256", 1256},
293   {"WINDOWS-1257", 1257},
294   {"WINDOWS-936", 1386},
295   {"X0201", 896}
296 };
297
298 char *os2cpToName(unsigned long cp)
299 {
300     ULONG ulLo = 0;
301     ULONG ulHi = (sizeof(aCP2Name) / sizeof(struct _CP2NAME)) - 1;
302     ULONG ulNext;
303     LONG  lFound = -1;
304
305     if (cp == SYSTEM_CP) {
306         ULONG aulCP[3];
307         ULONG cCP;
308
309         if (DosQueryCp(sizeof(aulCP), aulCP, &cCP) != NO_ERROR)
310             return NULL;
311
312         cp = aulCP[0];
313     }
314
315     if (aCP2Name[0].ulCode > cp || aCP2Name[ulHi].ulCode < cp)
316         return NULL;
317
318     if (aCP2Name[0].ulCode == cp)
319         return aCP2Name[0].pszName;
320
321     if (aCP2Name[ulHi].ulCode == cp)
322         return aCP2Name[ulHi].pszName;
323
324     while ((ulHi - ulLo) > 1) {
325         ulNext = (ulLo + ulHi) / 2;
326
327         if (aCP2Name[ulNext].ulCode < cp)
328             ulLo = ulNext;
329         else if (aCP2Name[ulNext].ulCode > cp)
330             ulHi = ulNext;
331         else {
332             lFound = ulNext;
333             break;
334         }
335     }
336
337     return (lFound == -1)? NULL : aCP2Name[lFound].pszName;
338 }
339
340 unsigned long os2cpFromName(char *cp)
341 {
342     ULONG ulLo = 0;
343     ULONG ulHi = (sizeof(aName2CP) / sizeof(struct _NAME2CP)) - 1;
344     ULONG ulNext;
345     LONG  lFound = -1;
346     LONG  lCmp;
347     PCHAR pcEnd;
348     CHAR  acBuf[64];
349
350     if (cp == NULL) {
351         ULONG aulCP[3];
352         ULONG cCP;
353
354         return (DosQueryCp(sizeof(aulCP), aulCP, &cCP) != NO_ERROR)? 0 : aulCP[0];
355     }
356
357     while (isspace(*cp))
358         cp++;
359
360     pcEnd = strchr(cp, ' ');
361     if (pcEnd == NULL)
362         pcEnd = strchr(cp, '\0');
363
364     ulNext = pcEnd - cp;
365     if (ulNext >= sizeof(acBuf))
366         return 0;
367
368     memcpy(acBuf, cp, ulNext);
369     acBuf[ulNext] = '\0';
370     strupr(acBuf);
371
372     lCmp = strcmp(aName2CP[0].pszName, acBuf);
373     if (lCmp > 0)
374         return 0;
375     else if (lCmp == 0)
376         return aName2CP[0].ulCode;
377
378     lCmp = strcmp(aName2CP[ulHi].pszName, acBuf);
379     if (lCmp < 0)
380         return 0;
381     else if (lCmp == 0)
382         return aName2CP[ulHi].ulCode;
383
384     while ((ulHi - ulLo) > 1) {
385         ulNext = (ulLo + ulHi) / 2;
386
387         lCmp = strcmp(aName2CP[ulNext].pszName, acBuf);
388         if (lCmp < 0)
389             ulLo = ulNext;
390         else if (lCmp > 0)
391             ulHi = ulNext;
392         else {
393             lFound = ulNext;
394             break;
395         }
396     }
397
398     return (lFound == -1)? 0 : aName2CP[lFound].ulCode;
399 }
400
401 /* vi: set ts=4 sw=4 expandtab: */