1 /**
2  * @file ctype.h
3  * Copyright 2012, 2013 MinGW.org project
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a
6  * copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation
8  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9  * and/or sell copies of the Software, and to permit persons to whom the
10  * Software is furnished to do so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice (including the next
13  * paragraph) shall be included in all copies or substantial portions of the
14  * Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  * DEALINGS IN THE SOFTWARE.
23  */
24 #ifndef _CTYPE_H_
25 #define _CTYPE_H_
26 #pragma GCC system_header
27 #include <_mingw.h>
28 
29 /*
30  * Functions for testing character types and converting characters.
31  */
32 
33 #define	__need_wchar_t
34 #define	__need_wint_t
35 #ifndef RC_INVOKED
36 #include <stddef.h>
37 #endif	/* Not RC_INVOKED */
38 
39 
40 /*
41  * The following flags are used to tell iswctype and _isctype what character
42  * types you are looking for.
43  */
44 #define	_UPPER		0x0001
45 #define	_LOWER		0x0002
46 #define	_DIGIT		0x0004
47 #define	_SPACE		0x0008 /* HT  LF  VT  FF  CR  SP */
48 #define	_PUNCT		0x0010
49 #define	_CONTROL	0x0020
50 /* _BLANK is set for SP and non-ASCII horizontal space chars (eg,
51    "no-break space", 0xA0, in CP1250) but not for HT.  */
52 #define	_BLANK		0x0040
53 #define	_HEX		0x0080
54 #define	_LEADBYTE	0x8000
55 
56 #define	_ALPHA		0x0103
57 
58 #ifndef RC_INVOKED
59 
60 #ifdef __cplusplus
61 extern "C" {
62 #endif
63 
64 _CRTIMP int __cdecl __MINGW_NOTHROW isalnum(int);
65 _CRTIMP int __cdecl __MINGW_NOTHROW isalpha(int);
66 _CRTIMP int __cdecl __MINGW_NOTHROW iscntrl(int);
67 _CRTIMP int __cdecl __MINGW_NOTHROW isdigit(int);
68 _CRTIMP int __cdecl __MINGW_NOTHROW isgraph(int);
69 _CRTIMP int __cdecl __MINGW_NOTHROW islower(int);
70 _CRTIMP int __cdecl __MINGW_NOTHROW isprint(int);
71 _CRTIMP int __cdecl __MINGW_NOTHROW ispunct(int);
72 _CRTIMP int __cdecl __MINGW_NOTHROW isspace(int);
73 _CRTIMP int __cdecl __MINGW_NOTHROW isupper(int);
74 _CRTIMP int __cdecl __MINGW_NOTHROW isxdigit(int);
75 
76 #if (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) \
77      || !defined __STRICT_ANSI__
78 int __cdecl __MINGW_NOTHROW isblank (int);
79 #endif
80 
81 #ifndef __STRICT_ANSI__
82 _CRTIMP int __cdecl __MINGW_NOTHROW _isctype (int, int);
83 #endif
84 
85 /* These are the ANSI versions, with correct checking of argument */
86 _CRTIMP int __cdecl __MINGW_NOTHROW tolower(int);
87 _CRTIMP int __cdecl __MINGW_NOTHROW toupper(int);
88 
89 /*
90  * NOTE: The above are not old name type wrappers, but functions exported
91  * explicitly by MSVCRT.DLL. However, underscored versions are also
92  * exported.
93  */
94 #ifndef	__STRICT_ANSI__
95 /*
96  *  These are the cheap non-std versions: The return values are undefined
97  *  if the argument is not ASCII char or is not of appropriate case
98  */
99 _CRTIMP int __cdecl __MINGW_NOTHROW _tolower(int);
100 _CRTIMP int __cdecl __MINGW_NOTHROW _toupper(int);
101 #endif
102 
103 /* Also defined in stdlib.h */
104 #ifndef MB_CUR_MAX
105    __MINGW_IMPORT int __mb_cur_max;
106 #  define MB_CUR_MAX __mb_cur_max
107 #endif  /* MB_CUR_MAX */
108 
109 
110 # if __MSVCRT_VERSION__ <= 0x0700
111   /* FIXME: What is _ctype[]? */
112   __MINGW_IMPORT unsigned short _ctype[];
113 # endif
114   __MINGW_IMPORT unsigned short* _pctype;
115 
116 /*
117  * Use inlines here rather than macros, because macros will upset
118  * C++ usage (eg, ::isalnum), and so usually get undefined
119  *
120  * According to standard for SB chars, these function are defined only
121  * for input values representable by unsigned char or EOF.
122  * Thus, there is no range test.
123  * This reproduces behaviour of MSVCRT.dll lib implemention for SB chars.
124  *
125  * If no MB char support is needed, these can be simplified even
126  * more by command line define -DMB_CUR_MAX=1.  The compiler will then
127  * optimise away the constant condition.
128  */
129 
130 #if !(defined (__NO_INLINE__)  || defined (__NO_CTYPE_INLINES) \
131 	|| defined (__STRICT_ANSI__))
132 
133 /* use  simple lookup if SB locale, else  _isctype()  */
134 #define __ISCTYPE(c, mask)  (MB_CUR_MAX == 1 ? (_pctype[c] & mask) : _isctype(c, mask))
isalnum(int c)135 __CRT_INLINE int __cdecl __MINGW_NOTHROW isalnum(int c) {return __ISCTYPE(c, (_ALPHA|_DIGIT));}
isalpha(int c)136 __CRT_INLINE int __cdecl __MINGW_NOTHROW isalpha(int c) {return __ISCTYPE(c, _ALPHA);}
iscntrl(int c)137 __CRT_INLINE int __cdecl __MINGW_NOTHROW iscntrl(int c) {return __ISCTYPE(c, _CONTROL);}
isdigit(int c)138 __CRT_INLINE int __cdecl __MINGW_NOTHROW isdigit(int c) {return __ISCTYPE(c, _DIGIT);}
isgraph(int c)139 __CRT_INLINE int __cdecl __MINGW_NOTHROW isgraph(int c) {return __ISCTYPE(c, (_PUNCT|_ALPHA|_DIGIT));}
islower(int c)140 __CRT_INLINE int __cdecl __MINGW_NOTHROW islower(int c) {return __ISCTYPE(c, _LOWER);}
isprint(int c)141 __CRT_INLINE int __cdecl __MINGW_NOTHROW isprint(int c) {return __ISCTYPE(c, (_BLANK|_PUNCT|_ALPHA|_DIGIT));}
ispunct(int c)142 __CRT_INLINE int __cdecl __MINGW_NOTHROW ispunct(int c) {return __ISCTYPE(c, _PUNCT);}
isspace(int c)143 __CRT_INLINE int __cdecl __MINGW_NOTHROW isspace(int c) {return __ISCTYPE(c, _SPACE);}
isupper(int c)144 __CRT_INLINE int __cdecl __MINGW_NOTHROW isupper(int c) {return __ISCTYPE(c, _UPPER);}
isxdigit(int c)145 __CRT_INLINE int __cdecl __MINGW_NOTHROW isxdigit(int c) {return __ISCTYPE(c, _HEX);}
146 
147 #if (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) \
148      || !defined __STRICT_ANSI__
isblank(int c)149 __CRT_INLINE int __cdecl __MINGW_NOTHROW isblank (int c)
150   {return (__ISCTYPE(c, _BLANK) || c == '\t');}
151 #endif
152 
153 /* these reproduce behaviour of lib underscored versions  */
_tolower(int c)154 __CRT_INLINE int __cdecl __MINGW_NOTHROW _tolower(int c) {return ( c -'A'+'a');}
_toupper(int c)155 __CRT_INLINE int __cdecl __MINGW_NOTHROW _toupper(int c) {return ( c -'a'+'A');}
156 
157 /* TODO? Is it worth inlining ANSI tolower, toupper? Probably only
158    if we only want C-locale. */
159 
160 #endif /* _NO_CTYPE_INLINES */
161 
162 /* Wide character equivalents */
163 
164 #ifndef WEOF
165 #define	WEOF	(wchar_t)(0xFFFF)
166 #endif
167 
168 #ifndef _WCTYPE_T_DEFINED
169 typedef wchar_t wctype_t;
170 #define _WCTYPE_T_DEFINED
171 #endif
172 
173 _CRTIMP int __cdecl __MINGW_NOTHROW iswalnum(wint_t);
174 _CRTIMP int __cdecl __MINGW_NOTHROW iswalpha(wint_t);
175 _CRTIMP int __cdecl __MINGW_NOTHROW iswascii(wint_t);
176 _CRTIMP int __cdecl __MINGW_NOTHROW iswcntrl(wint_t);
177 _CRTIMP int __cdecl __MINGW_NOTHROW iswctype(wint_t, wctype_t);
178 _CRTIMP int __cdecl __MINGW_NOTHROW is_wctype(wint_t, wctype_t);	/* Obsolete! */
179 _CRTIMP int __cdecl __MINGW_NOTHROW iswdigit(wint_t);
180 _CRTIMP int __cdecl __MINGW_NOTHROW iswgraph(wint_t);
181 _CRTIMP int __cdecl __MINGW_NOTHROW iswlower(wint_t);
182 _CRTIMP int __cdecl __MINGW_NOTHROW iswprint(wint_t);
183 _CRTIMP int __cdecl __MINGW_NOTHROW iswpunct(wint_t);
184 _CRTIMP int __cdecl __MINGW_NOTHROW iswspace(wint_t);
185 _CRTIMP int __cdecl __MINGW_NOTHROW iswupper(wint_t);
186 _CRTIMP int __cdecl __MINGW_NOTHROW iswxdigit(wint_t);
187 
188 #if (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) \
189      || !defined __STRICT_ANSI__ || defined __cplusplus
190 int __cdecl __MINGW_NOTHROW iswblank (wint_t);
191 #endif
192 
193 /* Older MS docs uses wchar_t for arg and return type, while newer
194    online MS docs say arg is wint_t and return is int.
195    ISO C uses wint_t for both.  */
196 _CRTIMP wint_t __cdecl __MINGW_NOTHROW towlower (wint_t);
197 _CRTIMP wint_t __cdecl __MINGW_NOTHROW towupper (wint_t);
198 
199 _CRTIMP int __cdecl __MINGW_NOTHROW isleadbyte (int);
200 
201 /* Also in wctype.h */
202 #if ! (defined (__NO_INLINE__) || defined(__NO_CTYPE_INLINES) \
203        || defined(__WCTYPE_INLINES_DEFINED))
204 #define __WCTYPE_INLINES_DEFINED
iswalnum(wint_t wc)205 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswalnum(wint_t wc) {return (iswctype(wc,_ALPHA|_DIGIT));}
iswalpha(wint_t wc)206 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswalpha(wint_t wc) {return (iswctype(wc,_ALPHA));}
iswascii(wint_t wc)207 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswascii(wint_t wc) {return ((wc & ~0x7F) ==0);}
iswcntrl(wint_t wc)208 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswcntrl(wint_t wc) {return (iswctype(wc,_CONTROL));}
iswdigit(wint_t wc)209 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswdigit(wint_t wc) {return (iswctype(wc,_DIGIT));}
iswgraph(wint_t wc)210 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswgraph(wint_t wc) {return (iswctype(wc,_PUNCT|_ALPHA|_DIGIT));}
iswlower(wint_t wc)211 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswlower(wint_t wc) {return (iswctype(wc,_LOWER));}
iswprint(wint_t wc)212 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswprint(wint_t wc) {return (iswctype(wc,_BLANK|_PUNCT|_ALPHA|_DIGIT));}
iswpunct(wint_t wc)213 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswpunct(wint_t wc) {return (iswctype(wc,_PUNCT));}
iswspace(wint_t wc)214 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswspace(wint_t wc) {return (iswctype(wc,_SPACE));}
iswupper(wint_t wc)215 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswupper(wint_t wc) {return (iswctype(wc,_UPPER));}
iswxdigit(wint_t wc)216 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswxdigit(wint_t wc) {return (iswctype(wc,_HEX));}
isleadbyte(int c)217 __CRT_INLINE int __cdecl __MINGW_NOTHROW isleadbyte(int c) {return (_pctype[(unsigned char)(c)] & _LEADBYTE);}
218 #if (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) \
219      || !defined __STRICT_ANSI__ || defined __cplusplus
iswblank(wint_t wc)220 __CRT_INLINE int __cdecl __MINGW_NOTHROW iswblank (wint_t wc)
221   {return (iswctype(wc,_BLANK) || wc == L'\t');}
222 #endif
223 
224 #endif /* !(defined(__NO_CTYPE_INLINES) || defined(__WCTYPE_INLINES_DEFINED)) */
225 
226 #ifndef	__STRICT_ANSI__
227 int __cdecl __MINGW_NOTHROW __isascii (int);
228 int __cdecl __MINGW_NOTHROW __toascii (int);
229 int __cdecl __MINGW_NOTHROW __iscsymf (int);		/* Valid first character in C symbol */
230 int __cdecl __MINGW_NOTHROW __iscsym (int);		/* Valid character in C symbol (after first) */
231 
232 #if !(defined (__NO_INLINE__) || defined (__NO_CTYPE_INLINES))
__isascii(int c)233 __CRT_INLINE int __cdecl __MINGW_NOTHROW __isascii(int c) {return ((c & ~0x7F) == 0);}
__toascii(int c)234 __CRT_INLINE int __cdecl __MINGW_NOTHROW __toascii(int c) {return (c & 0x7F);}
__iscsymf(int c)235 __CRT_INLINE int __cdecl __MINGW_NOTHROW __iscsymf(int c) {return (isalpha(c) || (c == '_'));}
__iscsym(int c)236 __CRT_INLINE int __cdecl __MINGW_NOTHROW __iscsym(int c)  {return  (isalnum(c) || (c == '_'));}
237 #endif /* __NO_CTYPE_INLINES */
238 
239 #ifndef	_NO_OLDNAMES
240 /* Not _CRTIMP */
241 int __cdecl __MINGW_NOTHROW isascii (int);
242 int __cdecl __MINGW_NOTHROW toascii (int);
243 int __cdecl __MINGW_NOTHROW iscsymf (int);
244 int __cdecl __MINGW_NOTHROW iscsym (int);
245 #endif	/* Not _NO_OLDNAMES */
246 
247 #endif	/* Not __STRICT_ANSI__ */
248 
249 #ifdef __cplusplus
250 }
251 #endif
252 
253 #endif	/* Not RC_INVOKED */
254 
255 #endif	/* Not _CTYPE_H_ */
256 
257