SetLocale.c revision 6cc2b21f
1
2/*
3 * Copyright 1990, 1991 by OMRON Corporation, NTT Software Corporation,
4 *                      and Nippon Telegraph and Telephone Corporation
5 *
6 * Permission to use, copy, modify, distribute, and sell this software and its
7 * documentation for any purpose is hereby granted without fee, provided that
8 * the above copyright notice appear in all copies and that both that
9 * copyright notice and this permission notice appear in supporting
10 * documentation, and that the names of OMRON, NTT Software, and NTT
11 * not be used in advertising or publicity pertaining to distribution of the
12 * software without specific, written prior permission. OMRON, NTT Software,
13 * and NTT make no representations about the suitability of this
14 * software for any purpose.  It is provided "as is" without express or
15 * implied warranty.
16 *
17 * OMRON, NTT SOFTWARE, AND NTT, DISCLAIM ALL WARRANTIES WITH REGARD
18 * TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
19 * AND FITNESS, IN NO EVENT SHALL OMRON, NTT SOFTWARE, OR NTT, BE
20 * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
21 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
22 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
23 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
24 *
25 *	Authors: Li Yuhong		OMRON Corporation
26 *		 Tetsuya Kato		NTT Software Corporation
27 *		 Hiroshi Kuribayashi	OMRON Corporation
28 *
29 */
30/*
31
32Copyright 1987,1998  The Open Group
33
34Permission to use, copy, modify, distribute, and sell this software and its
35documentation for any purpose is hereby granted without fee, provided that
36the above copyright notice appear in all copies and that both that
37copyright notice and this permission notice appear in supporting
38documentation.
39
40The above copyright notice and this permission notice shall be included
41in all copies or substantial portions of the Software.
42
43THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
44OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
45MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
46IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR
47OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
48ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
49OTHER DEALINGS IN THE SOFTWARE.
50
51Except as contained in this notice, the name of The Open Group shall
52not be used in advertising or otherwise to promote the sale, use or
53other dealings in this Software without prior written authorization
54from The Open Group.
55
56*/
57
58#ifdef HAVE_CONFIG_H
59#include <config.h>
60#endif
61#include "Xlibint.h"
62#include "Xlcint.h"
63#include <X11/Xlocale.h>
64#include <X11/Xos.h>
65#include "XlcPubI.h"
66
67#define MAXLOCALE	64	/* buffer size of locale name */
68
69#ifdef X_LOCALE
70
71/* alternative setlocale() for when the OS does not provide one */
72
73char *
74_Xsetlocale(
75    int		  category,
76    _Xconst char  *name
77)
78{
79    static char *xsl_name;
80    char *old_name;
81    XrmMethods methods;
82    XPointer state;
83
84    if (category != LC_CTYPE && category != LC_ALL)
85	return NULL;
86    if (!name) {
87	if (xsl_name)
88	    return xsl_name;
89	return "C";
90    }
91    if (!*name)
92	name = getenv("LC_CTYPE");
93    if (!name || !*name)
94	name = getenv("LANG");
95    if (name && strlen(name) >= MAXLOCALE)
96	name = NULL;
97    if (!name || !*name || !_XOpenLC((char *) name))
98	name = "C";
99    old_name = xsl_name;
100    xsl_name = (char *)name;
101    methods = _XrmInitParseInfo(&state);
102    xsl_name = old_name;
103    if (!methods)
104	return NULL;
105    name = (*methods->lcname)(state);
106    xsl_name = strdup(name);
107    if (!xsl_name) {
108	xsl_name = old_name;
109	(*methods->destroy)(state);
110	return NULL;
111    }
112    if (old_name)
113	Xfree(old_name);
114    (*methods->destroy)(state);
115    return xsl_name;
116}
117
118#else /* X_LOCALE */
119
120#if defined(__APPLE__) || defined(__CYGWIN__)
121char *
122_Xsetlocale(
123    int           category,
124    _Xconst char  *name
125)
126{
127    return setlocale(category, name);
128}
129#endif /* __APPLE__ || __CYGWIN__ */
130
131/*
132 * _XlcMapOSLocaleName is an implementation dependent routine that derives
133 * the LC_CTYPE locale name as used in the sample implementation from that
134 * returned by setlocale.
135 *
136 * Should match the code in Xt ExtractLocaleName.
137 *
138 * This function name is a bit of a misnomer. Even the siname parameter
139 * name is a misnomer. On most modern operating systems this function is
140 * a no-op, simply returning the osname; but on older operating systems
141 * like Ultrix, or HPUX 9.x and earlier, when you set LANG=german.88591
142 * then the string returned by setlocale(LC_ALL, "") will look something
143 * like: "german.88591 german.88591 ... german.88591". Then this function
144 * will pick out the LC_CTYPE component and return a pointer to that.
145 */
146
147char *
148_XlcMapOSLocaleName(
149    char *osname,
150    char *siname)
151{
152#if defined(hpux) || defined(CSRG_BASED) || defined(sun) || defined(SVR4) || defined(sgi) || defined(__osf__) || defined(AIXV3) || defined(ultrix) || defined(WIN32) || defined(__UNIXOS2__) || defined(linux)
153# ifdef hpux
154#  ifndef _LastCategory
155   /* HPUX 9 and earlier */
156#   define SKIPCOUNT 2
157#   define STARTCHAR ':'
158#   define ENDCHAR ';'
159#  else
160   /* HPUX 10 */
161#   define ENDCHAR ' '
162#  endif
163# else
164#  ifdef ultrix
165#   define SKIPCOUNT 2
166#   define STARTCHAR '\001'
167#   define ENDCHAR '\001'
168#  else
169#   if defined(WIN32) || defined(__UNIXOS2__)
170#    define SKIPCOUNT 1
171#    define STARTCHAR '='
172#    define ENDCHAR ';'
173#    define WHITEFILL
174#   else
175#    if defined(__osf__) || (defined(AIXV3) && !defined(AIXV4))
176#     define STARTCHAR ' '
177#     define ENDCHAR ' '
178#    else
179#     if defined(linux)
180#      define STARTSTR "LC_CTYPE="
181#      define ENDCHAR ';'
182#     else
183#      if !defined(sun) || defined(SVR4)
184#       define STARTCHAR '/'
185#       define ENDCHAR '/'
186#      endif
187#     endif
188#    endif
189#   endif
190#  endif
191# endif
192
193    char           *start;
194    char           *end;
195    int             len;
196# ifdef SKIPCOUNT
197    int		    n;
198# endif
199
200    start = osname;
201# ifdef SKIPCOUNT
202    for (n = SKIPCOUNT;
203	 --n >= 0 && start && (start = strchr (start, STARTCHAR));
204	 start++)
205	;
206    if (!start)
207	start = osname;
208# endif
209# ifdef STARTCHAR
210    if (start && (start = strchr (start, STARTCHAR)))
211# elif  defined (STARTSTR)
212    if (start && (start = strstr (start,STARTSTR)))
213# endif
214    {
215# ifdef STARTCHAR
216	start++;
217# elif defined (STARTSTR)
218	start += strlen(STARTSTR);
219# endif
220	if ((end = strchr (start, ENDCHAR))) {
221	    len = end - start;
222	    if (len >= MAXLOCALE)
223		len = MAXLOCALE - 1;
224	    strncpy(siname, start, len);
225	    *(siname + len) = '\0';
226# ifdef WHITEFILL
227	    for (start = siname; start = strchr(start, ' '); )
228		*start++ = '-';
229# endif
230	    return siname;
231	} else  /* if no ENDCHAR is found we are at the end of the line */
232	    return start;
233    }
234# ifdef WHITEFILL
235    if (strchr(osname, ' ')) {
236	len = strlen(osname);
237	if (len >= MAXLOCALE - 1)
238	    len = MAXLOCALE - 1;
239	strncpy(siname, osname, len);
240	*(siname + len) = '\0';
241	for (start = siname; start = strchr(start, ' '); )
242	    *start++ = '-';
243	return siname;
244    }
245# endif
246# undef STARTCHAR
247# undef ENDCHAR
248# undef WHITEFILL
249#endif
250    return osname;
251}
252
253#endif  /* X_LOCALE */
254