Add new country to makecountry
[AROS.git] / workbench / locale / countries / makecountry / makecountry.c
blob155bd980c9ca6292e86425b9de134a661d1f965e
1 /*
2 Copyright © 1995-2013, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc: Program that makes country files
6 Lang: english
7 */
9 #include <locale.h>
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <string.h>
13 #include <iconv.h>
15 #define D(x)
17 struct CountryEntry
19 char *ca_Name;
20 struct IntCountryPrefs *ca_Data;
23 extern struct IntCountryPrefs
24 andorraPrefs,
25 angolaPrefs,
26 argentinaPrefs,
27 australiaPrefs,
28 austriaPrefs,
29 belgiumPrefs,
30 bosnia_herzegovinaPrefs,
31 brazilPrefs,
32 bulgariaPrefs,
33 canadaPrefs,
34 cape_verdePrefs,
35 chinaPrefs,
36 costa_ricaPrefs,
37 croatiaPrefs,
38 czech_republicPrefs,
39 denmarkPrefs,
40 east_timorPrefs,
41 estoniaPrefs,
42 finlandPrefs,
43 francePrefs,
44 germanyPrefs,
45 great_britainPrefs,
46 greecePrefs,
47 haitiPrefs,
48 hungaryPrefs,
49 icelandPrefs,
50 indonesiaPrefs,
51 iranPrefs,
52 irelandPrefs,
53 italyPrefs,
54 japanPrefs,
55 latviaPrefs,
56 liechtensteinPrefs,
57 lithuaniaPrefs,
58 luxembourgPrefs,
59 maltaPrefs,
60 moldovaPrefs,
61 monacoPrefs,
62 montenegroPrefs,
63 new_zealandPrefs,
64 netherlandsPrefs,
65 norwayPrefs,
66 polandPrefs,
67 portugalPrefs,
68 romaniaPrefs,
69 russiaPrefs,
70 san_marinoPrefs,
71 slovakiaPrefs,
72 sloveniaPrefs,
73 south_koreaPrefs,
74 spainPrefs,
75 swedenPrefs,
76 switzerlandPrefs,
77 turkeyPrefs,
78 ukrainePrefs,
79 united_kingdomPrefs,
80 united_statesPrefs,
81 vatican_cityPrefs,
82 yugoslaviaPrefs;
84 /* Please keep this in alphabetical order, ie the order of Latin 1.
85 Character set of this file is also Latin 1 */
87 struct CountryEntry CountryArray[] =
89 { "andorra" , &andorraPrefs },
90 { "angola" , &angolaPrefs },
91 { "argentina" , &argentinaPrefs },
92 { "australia" , &australiaPrefs },
93 { "austria" , &austriaPrefs },
94 { "belgium" , &belgiumPrefs },
95 { "bosnia_herzegovina", &bosnia_herzegovinaPrefs},
96 { "brazil" , &brazilPrefs },
97 { "bulgaria" , &bulgariaPrefs },
98 { "canada" , &canadaPrefs },
99 { "cape_verde" , &cape_verdePrefs },
100 { "china" , &chinaPrefs },
101 { "costa_rica" , &costa_ricaPrefs },
102 { "croatia" , &croatiaPrefs },
103 { "czech_republic" , &czech_republicPrefs },
104 { "denmark" , &denmarkPrefs },
105 { "east_timor" , &east_timorPrefs },
106 { "estonia" , &estoniaPrefs },
107 { "finland" , &finlandPrefs },
108 { "france" , &francePrefs },
109 { "germany" , &germanyPrefs },
110 { "great_britain" , &great_britainPrefs },
111 { "greece" , &greecePrefs },
112 { "haiti" , &haitiPrefs },
113 { "hungary" , &hungaryPrefs },
114 { "iceland" , &icelandPrefs },
115 { "indonesia" , &indonesiaPrefs },
116 { "iran" , &iranPrefs },
117 { "ireland" , &irelandPrefs },
118 { "italy" , &italyPrefs },
119 { "japan" , &japanPrefs },
120 { "latvia" , &latviaPrefs },
121 { "liechtenstein" , &liechtensteinPrefs },
122 { "lithuania" , &lithuaniaPrefs },
123 { "luxembourg" , &luxembourgPrefs },
124 { "malta" , &maltaPrefs },
125 { "moldova" , &moldovaPrefs },
126 { "monaco" , &monacoPrefs },
127 { "montenegro" , &montenegroPrefs },
128 { "new_zealand" , &new_zealandPrefs },
129 { "netherlands" , &netherlandsPrefs },
130 { "norway" , &norwayPrefs },
131 { "poland" , &polandPrefs },
132 { "portugal" , &portugalPrefs },
133 { "romania" , &romaniaPrefs },
134 { "russia" , &russiaPrefs },
135 { "san_marino" , &san_marinoPrefs },
136 { "slovakia" , &slovakiaPrefs },
137 { "slovenia" , &sloveniaPrefs },
138 { "south_korea" , &south_koreaPrefs },
139 { "spain" , &spainPrefs },
140 { "sweden" , &swedenPrefs },
141 { "switzerland" , &switzerlandPrefs },
142 { "turkey" , &turkeyPrefs },
143 { "ukraine" , &ukrainePrefs },
144 { "united_kingdom" , &united_kingdomPrefs },
145 { "united_states" , &united_statesPrefs },
146 { "vatican_city" , &vatican_cityPrefs },
147 { "yugoslavia" , &yugoslaviaPrefs },
148 { NULL , NULL }
151 /* This is equivalent to the start of the catalog file.
152 It is a series of strings, so that the endianness is
153 correct either way
155 char iffheader[] =
157 "FORM" "\x00\x00\x00\x00" "PREF"
159 "PRHD" "\x00\x00\x00\x06"
160 "\x00\x00\x00\x00\x00\x00"
163 char ctryheader[] =
165 "CTRY" "\x00\x00\x00\x00"
168 char versheader[] =
170 "FVER" "\x00\x00\x00\x00"
173 char nnameheader[] =
175 "NNAM" "\x00\x00\x00\x00"
178 char flagheader[] =
180 "FLAG" "\x00\x00\x00\x00"
184 char iffpad[] = "\x00";
186 void convertEndianness(struct CountryPrefs *cp);
187 unsigned long getCountryPrefsSize(void);
188 unsigned long getCountryPrefsVers(struct IntCountryPrefs *cp);
189 unsigned long getCountryPrefsFlag(struct IntCountryPrefs *cp);
190 unsigned long getCountryNames(struct IntCountryPrefs *cp);
192 int writeChunk(FILE *fp, char *header, void *buffer, int len,
193 char *progname, char *filename)
195 header[4] = (len & (0xFF000000)) >> 24;
196 header[5] = (len & (0x00FF0000)) >> 16;
197 header[6] = (len & (0x0000FF00)) >> 8;
198 header[7] = (len & (0x000000FF));
200 /* Write out the IFF header... */
201 if(fwrite(header, 8, 1, fp) < 1)
203 printf("%s: Error writing chunk header for %s.\n", progname, filename);
204 fclose(fp);
205 return 20;
208 if(fwrite(buffer, len, 1, fp) < 1)
210 printf("%s: Error writing chunk data for %s.\n", progname, filename);
211 fclose(fp);
212 return 20;
214 if ((len & 1) && (fwrite(iffpad, 1, 1, fp) < 1))
216 printf("%s: Error padding chunk for %s.\n", progname, filename);
217 fclose(fp);
218 return 20;
220 return 0;
223 int doCountry(struct IntCountryPrefs *cp, char *progname, char *filename)
225 FILE *fp;
226 int size = 530;
227 char *cpVers, *cpFlag, *cpNames;
229 fp = fopen(filename, "w");
230 if(fp == NULL)
232 printf("%s: Could not open file %s\n", progname, filename);
233 return 20;
236 /* Adjust the size of the IFF file if necessary ... */
237 if ((cpVers = getCountryPrefsVers(cp)) != NULL)
239 size += strlen(cpVers);
240 size += 8;
242 if ((cpFlag = getCountryPrefsFlag(cp)) != NULL)
244 size += strlen(cpFlag);
245 size += 8;
247 if ((cpNames = getCountryNames(cp)) != NULL)
249 size += strlen(cpNames);
250 size += 8;
253 iffheader[4] = (size & (0xFF000000)) >> 24;
254 iffheader[5] = (size & (0x00FF0000)) >> 16;
255 iffheader[6] = (size & (0x0000FF00)) >> 8;
256 iffheader[7] = (size & (0x000000FF));
258 /* Write out the IFF header... */
259 if(fwrite(iffheader, 26, 1, fp) < 1)
261 printf("%s: Error writing IFF header for %s.\n", progname, filename);
262 fclose(fp);
263 return 20;
266 /* Write out the main Country Prefs Chunk ... */
267 convertEndianness((struct CountryPrefs *)cp);
269 if(writeChunk(fp, ctryheader, cp, getCountryPrefsSize(), progname, filename))
271 printf("%s: Error writing country data chunk %s.\n", progname, filename);
272 return 20;
275 /* Write out the Version String Chunk if appropriate ... */
276 if (cpVers)
278 if(writeChunk(fp, versheader, cpVers, strlen(cpVers) + 1, progname, filename))
280 printf("%s: Error writing country version string chunk %s.\n", progname, filename);
281 return 20;
285 /* Write out the NativeNames Chunk if appropriate ... */
286 if (cpNames)
288 if(writeChunk(fp, nnameheader, cpNames, strlen(cpNames) + 1, progname, filename))
290 printf("%s: Error writing country native-names string chunk %s.\n", progname, filename);
291 return 20;
295 /* Write out the Flag Chunk if appropriate ... */
296 if (cpFlag)
298 if(writeChunk(fp, flagheader, cpFlag, strlen(cpFlag) + 1, progname, filename))
300 printf("%s: Error writing country flag string chunk %s.\n", progname, filename);
301 return 20;
305 fclose(fp);
306 return 0;
309 int main(int argc, char **argv)
311 int i, j, skipCountry = 0;
312 int do_specific;
313 char buffer[64];
314 char *name;
315 iconv_t cd = (iconv_t)-1;
317 if(argc < 3)
319 printf("%s: Wrong number of arguments\n", argv[0]);
320 return 20;
323 do_specific = strcmp("--all", argv[2]);
325 /* Check host OS locale. If it's UTF-8, use UTF-8 file names. Otherwise use Latin-1 names. */
326 name = setlocale(LC_CTYPE, "");
327 D(printf("System locale: %s\n", name));
329 if (!name)
331 printf("%s: System locale is invalid\n",argv[0]);
332 return 20;
335 /* Use strstr() because for example on Linux this will be "en_US.UTF-8" while on MacOS it's just "UTF-8" */
336 if ((strstr(name, "UTF-8")) || (strstr(name, "utf8")))
338 cd = iconv_open("UTF-8", "ISO-8859-1");
339 if (cd == (iconv_t)(-1))
341 printf("%s: Error converting character sets\n", argv[0]);
342 return 20;
346 for(j=0; CountryArray[j].ca_Name != NULL; j++)
348 name = CountryArray[j].ca_Name;
350 if (cd != (iconv_t)-1)
352 char *out = buffer;
353 size_t inbytes, outbytes;
355 /* Convert country name to local character set */
356 inbytes = strlen(name) + 1;
357 outbytes = sizeof(buffer);
358 iconv(cd, &name, &inbytes, &out, &outbytes);
359 name = buffer;
362 if (do_specific)
364 /* locate the specified country */
365 for(i=2; i < argc; i++)
367 skipCountry = strcmp(name, argv[i]);
368 if (!skipCountry)
369 break;
373 if (!skipCountry)
375 char path[1024];
377 printf("Generating %s.country\n", name);
379 strcpy(path, argv[1]);
380 strcat(path, name);
381 strcat(path, ".country");
382 doCountry(CountryArray[j].ca_Data, argv[0], path);
386 return 0;