fdwalk should return 0 on an empty directory
[kopensolaris-gnu/glibc.git] / intl / tst-gettext.c
1 /* Test of the gettext functions.
2    Copyright (C) 2000, 2002, 2004 Free Software Foundation, Inc.
3    This file is part of the GNU C Library.
4    Contributed by Ulrich Drepper <drepper@cygnus.com>, 2000.
5
6    The GNU C Library is free software; you can redistribute it and/or
7    modify it under the terms of the GNU Lesser General Public
8    License as published by the Free Software Foundation; either
9    version 2.1 of the License, or (at your option) any later version.
10
11    The GNU C Library is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14    Lesser General Public License for more details.
15
16    You should have received a copy of the GNU Lesser General Public
17    License along with the GNU C Library; if not, write to the Free
18    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
19    02111-1307 USA.  */
20
21 #include <libintl.h>
22 #include <locale.h>
23 #include <mcheck.h>
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <string.h>
27 #include <error.h>
28 #include <errno.h>
29
30
31 const struct
32 {
33   const char *msgid;
34   const char *msgstr;
35 } msgs[] =
36 {
37 #define INPUT(Str) { Str,
38 #define OUTPUT(Str) Str },
39 #include TESTSTRS_H
40 };
41
42 const char *catname[] =
43 {
44   [LC_MESSAGES] = "LC_MESSAGES",
45   [LC_TIME] = "LC_TIME",
46   [LC_NUMERIC] = "LC_NUMERIC"
47 };
48
49
50 static int positive_gettext_test (void);
51 static int negative_gettext_test (void);
52 static int positive_dgettext_test (const char *domain);
53 static int positive_dcgettext_test (const char *domain, int category);
54 static int negative_dcgettext_test (const char *domain, int category);
55
56
57 #define check_setlocale(cat, name) do {                                       \
58     if (setlocale (cat, name) == NULL)                                        \
59       {                                                                       \
60         printf ("%s:%u: setlocale (%s, \"%s\"): %m\n",                        \
61                 __FILE__, __LINE__, #cat, name);                              \
62         result = 1;                                                           \
63       }                                                                       \
64   } while (0)
65
66 int
67 main (int argc, char *argv[])
68 {
69   int result = 0;
70
71   /* For debugging.  */
72   mtrace ();
73
74   /* This is the place where the .mo files are placed.  */
75   if (argc > 1)
76     {
77       bindtextdomain ("existing-domain", argv[1]);
78       bindtextdomain ("existing-time-domain", argv[1]);
79       bindtextdomain ("non-existing-domain", argv[1]);
80     }
81
82   /* The locale the catalog is created for is "existing-category".  Now
83      set the various variables in question to this value and run the
84      test.  */
85   setenv ("LANGUAGE", "existing-locale", 1);
86   setenv ("LC_ALL", "non-existing-locale", 1);
87   setenv ("LC_MESSAGES", "non-existing-locale", 1);
88   setenv ("LC_CTYPE", "non-existing-locale", 1);
89   setenv ("LANG", "non-existing-locale", 1);
90   check_setlocale (LC_CTYPE, "de_DE.UTF-8");
91   check_setlocale (LC_MESSAGES, "de_DE.UTF-8");
92   unsetenv ("OUTPUT_CHARSET");
93   /* This is the name of the existing domain with a catalog for the
94      LC_MESSAGES category.  */
95   textdomain ("existing-domain");
96   puts ("test `gettext' with LANGUAGE set");
97   if (positive_gettext_test () != 0)
98     {
99       puts ("FAILED");
100       result = 1;
101     }
102   /* This is the name of a non-existing domain with a catalog for the
103      LC_MESSAGES category.  We leave this value set for the `dgettext'
104      and `dcgettext' tests.  */
105   textdomain ("non-existing-domain");
106   puts ("test `gettext' with LANGUAGE set");
107   if (negative_gettext_test () != 0)
108     {
109       puts ("FAILED");
110       result = 1;
111     }
112   puts ("test `dgettext' with LANGUAGE set");
113   if (positive_dgettext_test ("existing-domain") != 0)
114     {
115       puts ("FAILED");
116       result = 1;
117     }
118
119   /* Now the same tests with LC_ALL deciding.  */
120   unsetenv ("LANGUAGE");
121   setenv ("LC_ALL", "existing-locale", 1);
122   check_setlocale (LC_ALL, "");
123   puts ("test `gettext' with LC_ALL set");
124   /* This is the name of the existing domain with a catalog for the
125      LC_MESSAGES category.  */
126   textdomain ("existing-domain");
127   if (positive_gettext_test () != 0)
128     {
129       puts ("FAILED");
130       result = 1;
131     }
132   /* This is the name of a non-existing domain with a catalog for the
133      LC_MESSAGES category.  We leave this value set for the `dgettext'
134      and `dcgettext' tests.  */
135   textdomain ("non-existing-domain");
136   puts ("test `gettext' with LC_ALL deciding");
137   if (negative_gettext_test () != 0)
138     {
139       puts ("FAILED");
140       result = 1;
141     }
142   puts ("test `dgettext' with LC_ALL deciding");
143   if (positive_dgettext_test ("existing-domain") != 0)
144     {
145       puts ("FAILED");
146       result = 1;
147     }
148
149   /* Now the same tests with LC_MESSAGES deciding.  */
150   unsetenv ("LC_ALL");
151   setenv ("LC_MESSAGES", "existing-locale", 1);
152   check_setlocale (LC_MESSAGES, "");
153   setenv ("LC_TIME", "existing-locale", 1);
154   check_setlocale (LC_TIME, "");
155   setenv ("LC_NUMERIC", "non-existing-locale", 1);
156   char *what = setlocale (LC_NUMERIC, "");
157   if (what != NULL)
158     {
159       printf ("setlocale succeeded (%s), expected failure\n", what);
160       result = 1;
161     }
162
163   puts ("test `gettext' with LC_MESSAGES set");
164   /* This is the name of the existing domain with a catalog for the
165      LC_MESSAGES category.  */
166   textdomain ("existing-domain");
167   if (positive_gettext_test () != 0)
168     {
169       puts ("FAILED");
170       result = 1;
171     }
172   /* This is the name of a non-existing domain with a catalog for the
173      LC_MESSAGES category.  We leave this value set for the `dgettext'
174      and `dcgettext' tests.  */
175   textdomain ("non-existing-domain");
176   puts ("test `gettext' with LC_MESSAGES deciding");
177   if (negative_gettext_test () != 0)
178     {
179       puts ("FAILED");
180       result = 1;
181     }
182   puts ("test `dgettext' with LC_MESSAGES deciding");
183   if (positive_dgettext_test ("existing-domain") != 0)
184     {
185       puts ("FAILED");
186       result = 1;
187     }
188   puts ("test `dcgettext' with category == LC_MESSAGES");
189   if (positive_dcgettext_test ("existing-domain", LC_MESSAGES) != 0)
190     {
191       puts ("FAILED");
192       result = 1;
193     }
194   /* Try a different category.  For this we also switch the domain.  */
195   puts ("test `dcgettext' with LANGUAGE == LC_TIME");
196   if (positive_dcgettext_test ("existing-time-domain", LC_TIME) != 0)
197     {
198       puts ("FAILED");
199       result = 1;
200     }
201   /* This time use a category for which there is no catalog.  */
202   puts ("test `dcgettext' with LANGUAGE == LC_NUMERIC");
203   if (negative_dcgettext_test ("existing-domain", LC_NUMERIC) != 0)
204     {
205       puts ("FAILED");
206       result = 1;
207     }
208
209   /* Now the same tests with LANG deciding.  */
210   unsetenv ("LC_MESSAGES");
211   unsetenv ("LC_CTYPE");
212   unsetenv ("LC_TIME");
213   unsetenv ("LC_NUMERIC");
214   setenv ("LANG", "existing-locale", 1);
215   check_setlocale (LC_ALL, "");
216   /* This is the name of the existing domain with a catalog for the
217      LC_MESSAGES category.  */
218   textdomain ("existing-domain");
219   puts ("test `gettext' with LANG set");
220   if (positive_gettext_test () != 0)
221     {
222       puts ("FAILED");
223       result = 1;
224     }
225   /* This is the name of a non-existing domain with a catalog for the
226      LC_MESSAGES category.  We leave this value set for the `dgettext'
227      and `dcgettext' tests.  */
228   textdomain ("non-existing-domain");
229   puts ("test `gettext' with LANG set");
230   if (negative_gettext_test () != 0)
231     {
232       puts ("FAILED");
233       result = 1;
234     }
235   puts ("test `dgettext' with LANG set");
236   if (positive_dgettext_test ("existing-domain") != 0)
237     {
238       puts ("FAILED");
239       result = 1;
240     }
241
242   check_setlocale (LC_ALL, "C");
243
244   return result;
245 }
246
247
248 static int
249 positive_gettext_test (void)
250 {
251   size_t cnt;
252   int result = 0;
253
254   for (cnt = 0; cnt < sizeof (msgs) / sizeof (msgs[0]); ++cnt)
255     {
256       const char *found = gettext (msgs[cnt].msgid);
257
258       if (found == NULL
259           || (msgs[cnt].msgstr[0] != '\0'
260               && strcmp (found, msgs[cnt].msgstr) != 0))
261         {
262           /* Oops, shouldn't happen.  */
263           printf ("\
264   gettext (\"%s\") failed, returned \"%s\", expected \"%s\"\n",
265                   msgs[cnt].msgid, found, msgs[cnt].msgstr);
266           result = 1;
267         }
268     }
269
270   return result;
271 }
272
273
274 static int
275 negative_gettext_test (void)
276 {
277   size_t cnt;
278   int result = 0;
279
280   for (cnt = 0; cnt < sizeof (msgs) / sizeof (msgs[0]); ++cnt)
281     {
282       const char *found = gettext (msgs[cnt].msgid);
283
284       if (found != msgs[cnt].msgid)
285         {
286           /* Oops, shouldn't happen.  */
287           printf ("  gettext (\"%s\") failed\n", msgs[cnt].msgid);
288           result = 1;
289         }
290     }
291
292   return result;
293 }
294
295
296 static int
297 positive_dgettext_test (const char *domain)
298 {
299   size_t cnt;
300   int result = 0;
301
302   for (cnt = 0; cnt < sizeof (msgs) / sizeof (msgs[0]); ++cnt)
303     {
304       const char *found = dgettext (domain, msgs[cnt].msgid);
305
306       if (found == NULL
307           || (msgs[cnt].msgstr[0] != '\0'
308               && strcmp (found, msgs[cnt].msgstr) != 0))
309         {
310           /* Oops, shouldn't happen.  */
311           printf ("\
312   dgettext (\"%s\", \"%s\") failed, returned \"%s\", expected \"%s\"\n",
313                   domain, msgs[cnt].msgid, found, msgs[cnt].msgstr);
314           result = 1;
315         }
316     }
317
318   return result;
319 }
320
321
322 static int
323 positive_dcgettext_test (const char *domain, int category)
324 {
325   size_t cnt;
326   int result = 0;
327
328   for (cnt = 0; cnt < sizeof (msgs) / sizeof (msgs[0]); ++cnt)
329     {
330       const char *found = dcgettext (domain, msgs[cnt].msgid, category);
331
332       if (found == NULL
333           || (msgs[cnt].msgstr[0] != '\0'
334               && strcmp (found, msgs[cnt].msgstr) != 0))
335         {
336           /* Oops, shouldn't happen.  */
337           printf ("\
338   dcgettext (\"%s\", \"%s\", %s) failed, returned \"%s\", expected \"%s\"\n",
339                   domain, msgs[cnt].msgid, catname[category], found,
340                   msgs[cnt].msgstr);
341           result = 1;
342         }
343     }
344
345   return result;
346 }
347
348
349 static int
350 negative_dcgettext_test (const char *domain, int category)
351 {
352   size_t cnt;
353   int result = 0;
354
355   for (cnt = 0; cnt < sizeof (msgs) / sizeof (msgs[0]); ++cnt)
356     {
357       const char *found = dcgettext (domain, msgs[cnt].msgid, category);
358
359       if (found != msgs[cnt].msgid)
360         {
361           /* Oops, shouldn't happen.  */
362           printf ("  dcgettext (\"%s\", \"%s\", %s) failed\n",
363                   domain, msgs[cnt].msgid, catname[category]);
364           result = 1;
365         }
366     }
367
368   return result;
369 }