]>
Commit | Line | Data |
---|---|---|
1 | /* Checking macros for wchar functions. | |
2 | Copyright (C) 2005-2025 Free Software Foundation, Inc. | |
3 | This file is part of the GNU C Library. | |
4 | ||
5 | The GNU C Library is free software; you can redistribute it and/or | |
6 | modify it under the terms of the GNU Lesser General Public | |
7 | License as published by the Free Software Foundation; either | |
8 | version 2.1 of the License, or (at your option) any later version. | |
9 | ||
10 | The GNU C Library is distributed in the hope that it will be useful, | |
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
13 | Lesser General Public License for more details. | |
14 | ||
15 | You should have received a copy of the GNU Lesser General Public | |
16 | License along with the GNU C Library; if not, see | |
17 | <https://www.gnu.org/licenses/>. */ | |
18 | ||
19 | #ifndef _WCHAR_H | |
20 | # error "Never include <bits/wchar2.h> directly; use <wchar.h> instead." | |
21 | #endif | |
22 | ||
23 | __fortify_function __attribute_overloadable__ wchar_t * | |
24 | __NTH (wmemcpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __s1), | |
25 | const wchar_t *__restrict __s2, size_t __n)) | |
26 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __s1, sizeof (wchar_t), | |
27 | "wmemcpy called with length bigger " | |
28 | "than size of destination buffer") | |
29 | { | |
30 | return __glibc_fortify_n (wmemcpy, __n, sizeof (wchar_t), | |
31 | __glibc_objsize0 (__s1), | |
32 | __s1, __s2, __n); | |
33 | } | |
34 | ||
35 | __fortify_function __attribute_overloadable__ wchar_t * | |
36 | __NTH (wmemmove (__fortify_clang_overload_arg (wchar_t *, ,__s1), | |
37 | const wchar_t *__s2, size_t __n)) | |
38 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __s1, sizeof (wchar_t), | |
39 | "wmemmove called with length bigger " | |
40 | "than size of destination buffer") | |
41 | { | |
42 | return __glibc_fortify_n (wmemmove, __n, sizeof (wchar_t), | |
43 | __glibc_objsize0 (__s1), | |
44 | __s1, __s2, __n); | |
45 | } | |
46 | ||
47 | #ifdef __USE_GNU | |
48 | __fortify_function __attribute_overloadable__ wchar_t * | |
49 | __NTH (wmempcpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __s1), | |
50 | const wchar_t *__restrict __s2, size_t __n)) | |
51 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __s1, sizeof (wchar_t), | |
52 | "wmempcpy called with length bigger " | |
53 | "than size of destination buffer") | |
54 | { | |
55 | return __glibc_fortify_n (wmempcpy, __n, sizeof (wchar_t), | |
56 | __glibc_objsize0 (__s1), | |
57 | __s1, __s2, __n); | |
58 | } | |
59 | #endif | |
60 | ||
61 | __fortify_function __attribute_overloadable__ wchar_t * | |
62 | __NTH (wmemset (__fortify_clang_overload_arg (wchar_t *, ,__s), wchar_t __c, | |
63 | size_t __n)) | |
64 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __s, sizeof (wchar_t), | |
65 | "wmemset called with length bigger " | |
66 | "than size of destination buffer") | |
67 | { | |
68 | return __glibc_fortify_n (wmemset, __n, sizeof (wchar_t), | |
69 | __glibc_objsize0 (__s), | |
70 | __s, __c, __n); | |
71 | } | |
72 | ||
73 | __fortify_function __attribute_overloadable__ wchar_t * | |
74 | __NTH (wcscpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
75 | const wchar_t *__restrict __src)) | |
76 | { | |
77 | size_t __sz = __glibc_objsize (__dest); | |
78 | if (__sz != (size_t) -1) | |
79 | return __wcscpy_chk (__dest, __src, __sz / sizeof (wchar_t)); | |
80 | return __wcscpy_alias (__dest, __src); | |
81 | } | |
82 | ||
83 | __fortify_function __attribute_overloadable__ wchar_t * | |
84 | __NTH (wcpcpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
85 | const wchar_t *__restrict __src)) | |
86 | { | |
87 | size_t __sz = __glibc_objsize (__dest); | |
88 | if (__sz != (size_t) -1) | |
89 | return __wcpcpy_chk (__dest, __src, __sz / sizeof (wchar_t)); | |
90 | return __wcpcpy_alias (__dest, __src); | |
91 | } | |
92 | ||
93 | __fortify_function __attribute_overloadable__ wchar_t * | |
94 | __NTH (wcsncpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
95 | const wchar_t *__restrict __src, size_t __n)) | |
96 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __dest, sizeof (wchar_t), | |
97 | "wcsncpy called with length bigger " | |
98 | "than size of destination buffer") | |
99 | { | |
100 | return __glibc_fortify_n (wcsncpy, __n, sizeof (wchar_t), | |
101 | __glibc_objsize (__dest), | |
102 | __dest, __src, __n); | |
103 | } | |
104 | ||
105 | __fortify_function __attribute_overloadable__ wchar_t * | |
106 | __NTH (wcpncpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
107 | const wchar_t *__restrict __src, size_t __n)) | |
108 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __dest, sizeof (wchar_t), | |
109 | "wcpncpy called with length bigger " | |
110 | "than size of destination buffer") | |
111 | { | |
112 | return __glibc_fortify_n (wcpncpy, __n, sizeof (wchar_t), | |
113 | __glibc_objsize (__dest), | |
114 | __dest, __src, __n); | |
115 | } | |
116 | ||
117 | __fortify_function __attribute_overloadable__ wchar_t * | |
118 | __NTH (wcscat (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
119 | const wchar_t *__restrict __src)) | |
120 | { | |
121 | size_t __sz = __glibc_objsize (__dest); | |
122 | if (__sz != (size_t) -1) | |
123 | return __wcscat_chk (__dest, __src, __sz / sizeof (wchar_t)); | |
124 | return __wcscat_alias (__dest, __src); | |
125 | } | |
126 | ||
127 | __fortify_function __attribute_overloadable__ wchar_t * | |
128 | __NTH (wcsncat (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
129 | const wchar_t *__restrict __src, size_t __n)) | |
130 | { | |
131 | size_t __sz = __glibc_objsize (__dest); | |
132 | if (__sz != (size_t) -1) | |
133 | return __wcsncat_chk (__dest, __src, __n, __sz / sizeof (wchar_t)); | |
134 | return __wcsncat_alias (__dest, __src, __n); | |
135 | } | |
136 | ||
137 | #ifdef __USE_MISC | |
138 | __fortify_function __attribute_overloadable__ size_t | |
139 | __NTH (wcslcpy (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
140 | const wchar_t *__restrict __src, size_t __n)) | |
141 | __fortify_clang_warning_only_if_bos0_lt2 (__n, __dest, sizeof (wchar_t), | |
142 | "wcslcpy called with length bigger " | |
143 | "than size of destination buffer") | |
144 | { | |
145 | if (__glibc_objsize (__dest) != (size_t) -1 | |
146 | && (!__builtin_constant_p (__n | |
147 | > __glibc_objsize (__dest) / sizeof (wchar_t)) | |
148 | || __n > __glibc_objsize (__dest) / sizeof (wchar_t))) | |
149 | return __wcslcpy_chk (__dest, __src, __n, | |
150 | __glibc_objsize (__dest) / sizeof (wchar_t)); | |
151 | return __wcslcpy_alias (__dest, __src, __n); | |
152 | } | |
153 | ||
154 | __fortify_function __attribute_overloadable__ size_t | |
155 | __NTH (wcslcat (__fortify_clang_overload_arg (wchar_t *, __restrict, __dest), | |
156 | const wchar_t *__restrict __src, size_t __n)) | |
157 | { | |
158 | if (__glibc_objsize (__dest) != (size_t) -1 | |
159 | && (!__builtin_constant_p (__n > __glibc_objsize (__dest) | |
160 | / sizeof (wchar_t)) | |
161 | || __n > __glibc_objsize (__dest) / sizeof (wchar_t))) | |
162 | return __wcslcat_chk (__dest, __src, __n, | |
163 | __glibc_objsize (__dest) / sizeof (wchar_t)); | |
164 | return __wcslcat_alias (__dest, __src, __n); | |
165 | } | |
166 | #endif /* __USE_MISC */ | |
167 | ||
168 | #ifdef __va_arg_pack | |
169 | __fortify_function int | |
170 | __NTH (swprintf (wchar_t *__restrict __s, size_t __n, | |
171 | const wchar_t *__restrict __fmt, ...)) | |
172 | { | |
173 | size_t __sz = __glibc_objsize (__s); | |
174 | if (__sz != (size_t) -1 || __USE_FORTIFY_LEVEL > 1) | |
175 | return __swprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1, | |
176 | __sz / sizeof (wchar_t), __fmt, __va_arg_pack ()); | |
177 | return __swprintf_alias (__s, __n, __fmt, __va_arg_pack ()); | |
178 | } | |
179 | #elif __fortify_use_clang | |
180 | __fortify_function_error_function __attribute_overloadable__ int | |
181 | __NTH (swprintf (__fortify_clang_overload_arg (wchar_t *, __restrict, __s), | |
182 | size_t __n, const wchar_t *__restrict __fmt, ...)) | |
183 | { | |
184 | __gnuc_va_list __fortify_ap; | |
185 | __builtin_va_start (__fortify_ap, __fmt); | |
186 | int __r; | |
187 | if (__glibc_objsize (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1) | |
188 | __r = __vswprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1, | |
189 | __glibc_objsize (__s) / sizeof (wchar_t), | |
190 | __fmt, __fortify_ap); | |
191 | else | |
192 | __r = __vswprintf_alias (__s, __n, __fmt, __fortify_ap); | |
193 | __builtin_va_end (__fortify_ap); | |
194 | return __r; | |
195 | } | |
196 | #elif !defined __cplusplus | |
197 | /* XXX We might want to have support in gcc for swprintf. */ | |
198 | # define swprintf(s, n, ...) \ | |
199 | (__glibc_objsize (s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1 \ | |
200 | ? __swprintf_chk (s, n, __USE_FORTIFY_LEVEL - 1, \ | |
201 | __glibc_objsize (s) / sizeof (wchar_t), __VA_ARGS__) \ | |
202 | : swprintf (s, n, __VA_ARGS__)) | |
203 | #endif | |
204 | ||
205 | __fortify_function int | |
206 | __NTH (vswprintf (wchar_t *__restrict __s, size_t __n, | |
207 | const wchar_t *__restrict __fmt, __gnuc_va_list __ap)) | |
208 | { | |
209 | size_t __sz = __glibc_objsize (__s); | |
210 | if (__sz != (size_t) -1 || __USE_FORTIFY_LEVEL > 1) | |
211 | return __vswprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1, | |
212 | __sz / sizeof (wchar_t), __fmt, __ap); | |
213 | return __vswprintf_alias (__s, __n, __fmt, __ap); | |
214 | } | |
215 | ||
216 | ||
217 | #if __USE_FORTIFY_LEVEL > 1 | |
218 | ||
219 | # ifdef __va_arg_pack | |
220 | __fortify_function int | |
221 | wprintf (const wchar_t *__restrict __fmt, ...) | |
222 | { | |
223 | return __wprintf_chk (__USE_FORTIFY_LEVEL - 1, __fmt, __va_arg_pack ()); | |
224 | } | |
225 | ||
226 | __fortify_function int | |
227 | fwprintf (__FILE *__restrict __stream, const wchar_t *__restrict __fmt, ...) | |
228 | { | |
229 | return __fwprintf_chk (__stream, __USE_FORTIFY_LEVEL - 1, __fmt, | |
230 | __va_arg_pack ()); | |
231 | } | |
232 | # elif !defined __cplusplus | |
233 | # define wprintf(...) \ | |
234 | __wprintf_chk (__USE_FORTIFY_LEVEL - 1, __VA_ARGS__) | |
235 | # define fwprintf(stream, ...) \ | |
236 | __fwprintf_chk (stream, __USE_FORTIFY_LEVEL - 1, __VA_ARGS__) | |
237 | # endif | |
238 | ||
239 | __fortify_function int | |
240 | vwprintf (const wchar_t *__restrict __fmt, __gnuc_va_list __ap) | |
241 | { | |
242 | return __vwprintf_chk (__USE_FORTIFY_LEVEL - 1, __fmt, __ap); | |
243 | } | |
244 | ||
245 | __fortify_function int | |
246 | vfwprintf (__FILE *__restrict __stream, | |
247 | const wchar_t *__restrict __fmt, __gnuc_va_list __ap) | |
248 | { | |
249 | return __vfwprintf_chk (__stream, __USE_FORTIFY_LEVEL - 1, __fmt, __ap); | |
250 | } | |
251 | ||
252 | #endif | |
253 | __fortify_function __attribute_overloadable__ __wur wchar_t * | |
254 | fgetws (__fortify_clang_overload_arg (wchar_t *, __restrict, __s), int __n, | |
255 | __FILE *__restrict __stream) | |
256 | __fortify_clang_warning_only_if_bos_lt2 (__n, __s, sizeof (wchar_t), | |
257 | "fgetws called with length bigger " | |
258 | "than size of destination buffer") | |
259 | { | |
260 | size_t __sz = __glibc_objsize (__s); | |
261 | if (__glibc_safe_or_unknown_len (__n, sizeof (wchar_t), __sz)) | |
262 | return __fgetws_alias (__s, __n, __stream); | |
263 | #if !__fortify_use_clang | |
264 | if (__glibc_unsafe_len (__n, sizeof (wchar_t), __sz)) | |
265 | return __fgetws_chk_warn (__s, __sz / sizeof (wchar_t), __n, __stream); | |
266 | #endif | |
267 | return __fgetws_chk (__s, __sz / sizeof (wchar_t), __n, __stream); | |
268 | } | |
269 | ||
270 | #ifdef __USE_GNU | |
271 | __fortify_function __attribute_overloadable__ __wur wchar_t * | |
272 | fgetws_unlocked (__fortify_clang_overload_arg (wchar_t *, __restrict, __s), | |
273 | int __n, __FILE *__restrict __stream) | |
274 | __fortify_clang_warning_only_if_bos_lt2 (__n, __s, sizeof (wchar_t), | |
275 | "fgetws_unlocked called with length bigger " | |
276 | "than size of destination buffer") | |
277 | { | |
278 | size_t __sz = __glibc_objsize (__s); | |
279 | if (__glibc_safe_or_unknown_len (__n, sizeof (wchar_t), __sz)) | |
280 | return __fgetws_unlocked_alias (__s, __n, __stream); | |
281 | # if !__fortify_use_clang | |
282 | if (__glibc_unsafe_len (__n, sizeof (wchar_t), __sz)) | |
283 | return __fgetws_unlocked_chk_warn (__s, __sz / sizeof (wchar_t), __n, | |
284 | __stream); | |
285 | # endif | |
286 | return __fgetws_unlocked_chk (__s, __sz / sizeof (wchar_t), __n, __stream); | |
287 | } | |
288 | #endif | |
289 | ||
290 | __fortify_function __attribute_overloadable__ __wur size_t | |
291 | __NTH (wcrtomb (__fortify_clang_overload_arg (char *, __restrict, __s), | |
292 | wchar_t __wchar, mbstate_t *__restrict __ps)) | |
293 | { | |
294 | /* We would have to include <limits.h> to get a definition of MB_LEN_MAX. | |
295 | But this would only disturb the namespace. So we define our own | |
296 | version here. */ | |
297 | #define __WCHAR_MB_LEN_MAX 16 | |
298 | #if defined MB_LEN_MAX && MB_LEN_MAX != __WCHAR_MB_LEN_MAX | |
299 | # error "Assumed value of MB_LEN_MAX wrong" | |
300 | #endif | |
301 | if (__glibc_objsize (__s) != (size_t) -1 | |
302 | && __WCHAR_MB_LEN_MAX > __glibc_objsize (__s)) | |
303 | return __wcrtomb_chk (__s, __wchar, __ps, __glibc_objsize (__s)); | |
304 | return __wcrtomb_alias (__s, __wchar, __ps); | |
305 | } | |
306 | ||
307 | __fortify_function __attribute_overloadable__ size_t | |
308 | __NTH (mbsrtowcs (__fortify_clang_overload_arg (wchar_t *, __restrict, __dst), | |
309 | const char **__restrict __src, | |
310 | size_t __len, mbstate_t *__restrict __ps)) | |
311 | __fortify_clang_warning_only_if_bos_lt2 (__len, __dst, sizeof (wchar_t), | |
312 | "mbsrtowcs called with dst buffer " | |
313 | "smaller than len * sizeof (wchar_t)") | |
314 | { | |
315 | return __glibc_fortify_n (mbsrtowcs, __len, sizeof (wchar_t), | |
316 | __glibc_objsize (__dst), | |
317 | __dst, __src, __len, __ps); | |
318 | } | |
319 | ||
320 | __fortify_function __attribute_overloadable__ size_t | |
321 | __NTH (wcsrtombs (__fortify_clang_overload_arg (char *, __restrict, __dst), | |
322 | const wchar_t **__restrict __src, | |
323 | size_t __len, mbstate_t *__restrict __ps)) | |
324 | __fortify_clang_warning_only_if_bos_lt (__len, __dst, | |
325 | "wcsrtombs called with dst buffer " | |
326 | "smaller than len") | |
327 | { | |
328 | return __glibc_fortify (wcsrtombs, __len, sizeof (char), | |
329 | __glibc_objsize (__dst), | |
330 | __dst, __src, __len, __ps); | |
331 | } | |
332 | ||
333 | ||
334 | #ifdef __USE_XOPEN2K8 | |
335 | __fortify_function __attribute_overloadable__ size_t | |
336 | __NTH (mbsnrtowcs (__fortify_clang_overload_arg (wchar_t *, __restrict, __dst), | |
337 | const char **__restrict __src, size_t __nmc, size_t __len, | |
338 | mbstate_t *__restrict __ps)) | |
339 | __fortify_clang_warning_only_if_bos_lt (sizeof (wchar_t) * __len, __dst, | |
340 | "mbsnrtowcs called with dst buffer " | |
341 | "smaller than len * sizeof (wchar_t)") | |
342 | { | |
343 | return __glibc_fortify_n (mbsnrtowcs, __len, sizeof (wchar_t), | |
344 | __glibc_objsize (__dst), | |
345 | __dst, __src, __nmc, __len, __ps); | |
346 | } | |
347 | ||
348 | __fortify_function __attribute_overloadable__ size_t | |
349 | __NTH (wcsnrtombs (__fortify_clang_overload_arg (char *, __restrict, __dst), | |
350 | const wchar_t **__restrict __src, size_t __nwc, | |
351 | size_t __len, mbstate_t *__restrict __ps)) | |
352 | __fortify_clang_warning_only_if_bos_lt (__len, __dst, | |
353 | "wcsnrtombs called with dst buffer " | |
354 | "smaller than len") | |
355 | { | |
356 | return __glibc_fortify (wcsnrtombs, __len, sizeof (char), | |
357 | __glibc_objsize (__dst), | |
358 | __dst, __src, __nwc, __len, __ps); | |
359 | } | |
360 | #endif |