2 *******************************************************************************
4 * Copyright (C) 1999-2007, International Business Machines
5 * Corporation and others. All Rights Reserved.
7 *******************************************************************************
10 * tab size: 8 (not used)
13 * created on: 2000sep6
14 * created by: Vladimir Weinstein
17 /******************************************************************************
18 * This program prints out resource bundles - example for
20 * TODO: make a complete i18n layout for this program.
21 ******************************************************************************/
23 #include "unicode/putil.h"
24 #include "unicode/ures.h"
25 #include "unicode/ustdio.h"
26 #include "unicode/uloc.h"
27 #include "unicode/ustring.h"
39 #define URESB_DEFAULTTRUNC 40
41 static char *currdir
= NULL
;
42 /*--locale sr_YU and --encoding cp855
43 * are interesting on Win32
46 static const char *locale
= NULL
;
47 static const char *encoding
= NULL
;
48 static const char *resPath
= NULL
;
49 static const int32_t indentsize
= 4;
50 static UFILE
*outerr
= NULL
;
51 static int32_t truncsize
= URESB_DEFAULTTRUNC
;
52 static UBool trunc
= FALSE
;
54 const UChar baderror
[] = { 0x0042, 0x0041, 0x0044, 0x0000 };
56 const UChar
*getErrorName(UErrorCode errorNumber
);
57 void reportError(UErrorCode
*status
);
58 static UChar
*quotedString(const UChar
*string
);
59 void printOutBundle(UFILE
*out
, UResourceBundle
*resource
, int32_t indent
, UErrorCode
*status
);
60 void printIndent(UFILE
*out
, int32_t indent
);
61 void printHex(UFILE
*out
, const int8_t *what
);
63 static UOption options
[]={
65 UOPTION_HELP_QUESTION_MARK
,
66 { "locale", NULL
, NULL
, NULL
, 'l', UOPT_REQUIRES_ARG
, 0 },
68 { "path", NULL
, NULL
, NULL
, 'p', UOPT_OPTIONAL_ARG
, 0 },
69 { "truncate", NULL
, NULL
, NULL
, 't', UOPT_OPTIONAL_ARG
, 0 },
73 static UBool VERBOSE
= FALSE
;
76 main(int argc
, char* argv
[]) {
78 UResourceBundle
*bundle
= NULL
;
79 UErrorCode status
= U_ZERO_ERROR
;
83 char resPathBuffer
[1024];
85 currdir
= _getcwd(NULL
, 0);
87 currdir
= getcwd(NULL
, 0);
90 argc
=u_parseArgs(argc
, argv
, sizeof(options
)/sizeof(options
[0]), options
);
92 /* error handling, printing usage message */
95 "error in command line argument \"%s\"\n",
98 if(argc
<2 || options
[0].doesOccur
|| options
[1].doesOccur
) {
100 "usage: %s [-options] locale(s)\n",
102 return argc
<0 ? U_ILLEGAL_ARGUMENT_ERROR
: U_ZERO_ERROR
;
105 if(options
[2].doesOccur
) {
106 locale
= options
[2].value
;
111 if(options
[3].doesOccur
) {
112 encoding
= options
[3].value
;
117 if(options
[4].doesOccur
) {
118 if(options
[4].value
!= NULL
) {
119 resPath
= options
[4].value
; /* we'll use users resources */
121 resPath
= NULL
; /* we'll use ICU system resources for dumping */
124 strcpy(resPathBuffer
, currdir
);
125 /*strcat(resPathBuffer, U_FILE_SEP_STRING);
126 strcat(resPathBuffer, "uresb");*/
127 resPath
= resPathBuffer
; /* we'll just dump uresb samples resources */
130 if(options
[5].doesOccur
) {
132 if(options
[5].value
!= NULL
) {
133 truncsize
= atoi(options
[5].value
); /* user defined printable size */
135 truncsize
= URESB_DEFAULTTRUNC
; /* we'll use default omitting size */
141 if(options
[6].doesOccur
) {
145 outerr
= u_finit(stderr
, locale
, encoding
);
146 out
= u_finit(stdout
, locale
, encoding
);
148 for(i
= 1; i
< argc
; ++i
) {
149 status
= U_ZERO_ERROR
;
150 arg
= getLongPathname(argv
[i
]);
152 u_fprintf(out
, "uresb: processing file \"%s\" in path \"%s\"\n", arg
, resPath
);
153 bundle
= ures_open(resPath
, arg
, &status
);
154 if(U_SUCCESS(status
)) {
155 u_fprintf(out
, "%s\n", arg
);
156 printOutBundle(out
, bundle
, 0, &status
);
158 reportError(&status
);
171 void printIndent(UFILE
*out
, int32_t indent
) {
174 for(i
= 0; i
<indent
; i
++) {
177 inchar
[indent
] = '\0';
178 u_fprintf(out
, "%s", inchar
);
181 void printHex(UFILE
*out
, const int8_t *what
) {
182 u_fprintf(out
, "%02X", (uint8_t)*what
);
185 static UChar
*quotedString(const UChar
*string
) {
186 int len
= u_strlen(string
);
191 for (sp
= string
; *sp
; ++sp
) {
200 newstr
= (UChar
*) malloc((1 + alen
) * sizeof(*newstr
));
201 for (sp
= string
, np
= newstr
; *sp
; ++sp
) {
221 void printOutBundle(UFILE
*out
, UResourceBundle
*resource
, int32_t indent
, UErrorCode
*status
) {
223 const char *key
= ures_getKey(resource
);
225 switch(ures_getType(resource
)) {
229 const UChar
*thestr
= ures_getString(resource
, &len
, status
);
230 UChar
*string
= quotedString(thestr
);
232 /* TODO: String truncation */
234 if(trunc && len > truncsize) {
235 printIndent(out, indent);
236 u_fprintf(out, "// WARNING: this string, size %d is truncated to %d\n", len, truncsize/2);
240 printIndent(out
, indent
);
242 u_fprintf(out
, "%s { \"%S\" } ", key
, string
);
244 u_fprintf(out
, "\"%S\",", string
);
247 u_fprintf(out
, " // STRING");
249 u_fprintf(out
, "\n");
254 printIndent(out
, indent
);
256 u_fprintf(out
, "%s", key
);
258 u_fprintf(out
, ":int { %li } ", ures_getInt(resource
, status
));
261 u_fprintf(out
, " // INT");
263 u_fprintf(out
, "\n");
268 const int8_t *data
= (const int8_t *)ures_getBinary(resource
, &len
, status
);
269 if(trunc
&& len
> truncsize
) {
270 printIndent(out
, indent
);
271 u_fprintf(out
, "// WARNING: this resource, size %li is truncated to %li\n", len
, truncsize
/2);
274 if(U_SUCCESS(*status
)) {
275 printIndent(out
, indent
);
277 u_fprintf(out
, "%s", key
);
279 u_fprintf(out
, ":binary { ");
280 for(i
= 0; i
<len
; i
++) {
281 printHex(out
, data
++);
283 u_fprintf(out
, " }");
285 u_fprintf(out
, " // BINARY");
287 u_fprintf(out
, "\n");
294 case URES_INT_VECTOR
:
297 const int32_t *data
= ures_getIntVector(resource
, &len
, status
);
298 if(U_SUCCESS(*status
)) {
299 printIndent(out
, indent
);
301 u_fprintf(out
, "%s", key
);
303 u_fprintf(out
, ":intvector { ");
304 for(i
= 0; i
<len
-1; i
++) {
305 u_fprintf(out
, "%d, ", data
[i
]);
308 u_fprintf(out
, "%d ", data
[len
-1]);
312 u_fprintf(out
, " // INTVECTOR");
314 u_fprintf(out
, "\n");
324 UResourceBundle
*t
= NULL
;
325 ures_resetIterator(resource
);
326 printIndent(out
, indent
);
328 u_fprintf(out
, "%s ", key
);
332 if(ures_getType(resource
) == URES_TABLE
) {
333 u_fprintf(out
, " // TABLE");
335 u_fprintf(out
, " // ARRAY");
338 u_fprintf(out
, "\n");
340 while(ures_hasNext(resource
)) {
341 t
= ures_getNextResource(resource
, t
, status
);
342 printOutBundle(out
, t
, indent
+indentsize
, status
);
345 printIndent(out
, indent
);
346 u_fprintf(out
, "}\n");
356 void reportError(UErrorCode
*status
) {
357 u_fprintf(outerr
, "Error %d(%s) : %U happened!\n", *status
, u_errorName(*status
), getErrorName(*status
));
361 const UChar
*getErrorName(UErrorCode errorNumber
) {
362 UErrorCode status
= U_ZERO_ERROR
;
365 UResourceBundle
*error
= ures_open(currdir
, locale
, &status
);
367 UResourceBundle
*errorcodes
= ures_getByKey(error
, "errorcodes", NULL
, &status
);
369 const UChar
*result
= ures_getStringByIndex(errorcodes
, errorNumber
, &len
, &status
);
371 ures_close(errorcodes
);
374 if(U_SUCCESS(status
)) {