• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) Huawei Technologies Co., Ltd. 2014-2021. All rights reserved.
3  * Licensed under Mulan PSL v2.
4  * You can use this software according to the terms and conditions of the Mulan PSL v2.
5  * You may obtain a copy of Mulan PSL v2 at:
6  *          http://license.coscl.org.cn/MulanPSL2
7  * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
8  * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
9  * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
10  * See the Mulan PSL v2 for more details.
11  * Description: Define internal used macro and data type. The marco of SECUREC_ON_64BITS
12  *              will be determined in this header file, which is a switch for part
13  *              of code. Some macro are used to suppress warning by MS compiler.
14  * Create: 2014-02-25
15  * Notes: User can change the value of SECUREC_STRING_MAX_LEN and SECUREC_MEM_MAX_LEN
16  *        macro to meet their special need, but The maximum value should not exceed 2G.
17  */
18 /*
19  * [Standardize-exceptions]: Performance-sensitive
20  * [reason]: Strict parameter verification has been done before use
21  */
22 
23 #ifndef SECURECTYPE_H_A7BBB686_AADA_451B_B9F9_44DACDAE18A7
24 #define SECURECTYPE_H_A7BBB686_AADA_451B_B9F9_44DACDAE18A7
25 
26 #ifndef SECUREC_USING_STD_SECURE_LIB
27 #if defined(_MSC_VER) && _MSC_VER >= 1400
28 #if defined(__STDC_WANT_SECURE_LIB__) && (!__STDC_WANT_SECURE_LIB__)
29 /* Security functions have been provided since vs2005, default use of system library functions */
30 #define SECUREC_USING_STD_SECURE_LIB    0
31 #else
32 #define SECUREC_USING_STD_SECURE_LIB    1
33 #endif
34 #else
35 #define SECUREC_USING_STD_SECURE_LIB    0
36 #endif
37 #endif
38 
39 /* Compatibility with older Secure C versions, shielding VC symbol redefinition warning */
40 #if defined(_MSC_VER) && (_MSC_VER >= 1400) && (!SECUREC_USING_STD_SECURE_LIB)
41 #ifndef SECUREC_DISABLE_CRT_FUNC
42 #define SECUREC_DISABLE_CRT_FUNC        1
43 #endif
44 #ifndef SECUREC_DISABLE_CRT_IMP
45 #define SECUREC_DISABLE_CRT_IMP         1
46 #endif
47 #else /*  MSC VER */
48 #ifndef SECUREC_DISABLE_CRT_FUNC
49 #define SECUREC_DISABLE_CRT_FUNC        0
50 #endif
51 #ifndef SECUREC_DISABLE_CRT_IMP
52 #define SECUREC_DISABLE_CRT_IMP         0
53 #endif
54 #endif
55 
56 #if SECUREC_DISABLE_CRT_FUNC
57 #ifdef __STDC_WANT_SECURE_LIB__
58 #undef __STDC_WANT_SECURE_LIB__
59 #endif
60 #define __STDC_WANT_SECURE_LIB__        0
61 #endif
62 
63 #if SECUREC_DISABLE_CRT_IMP
64 #ifdef _CRTIMP_ALTERNATIVE
65 #undef _CRTIMP_ALTERNATIVE
66 #endif
67 #define _CRTIMP_ALTERNATIVE     /* Comment Microsoft *_s function */
68 #endif
69 
70 /* Compile in kernel under macro control */
71 #ifndef SECUREC_IN_KERNEL
72 #ifdef __KERNEL__
73 #define SECUREC_IN_KERNEL               1
74 #else
75 #define SECUREC_IN_KERNEL               0
76 #endif
77 #endif
78 
79 /* make kernel symbols of functions available to loadable modules */
80 #ifndef SECUREC_EXPORT_KERNEL_SYMBOL
81 #if SECUREC_IN_KERNEL
82 #define SECUREC_EXPORT_KERNEL_SYMBOL    1
83 #else
84 #define SECUREC_EXPORT_KERNEL_SYMBOL    0
85 #endif
86 #endif
87 
88 #if SECUREC_IN_KERNEL
89 #ifndef SECUREC_ENABLE_SCANF_FILE
90 #define SECUREC_ENABLE_SCANF_FILE       0
91 #endif
92 #ifndef SECUREC_ENABLE_WCHAR_FUNC
93 #define SECUREC_ENABLE_WCHAR_FUNC       0
94 #endif
95 #else /* SECUREC_IN_KERNEL */
96 #ifndef SECUREC_ENABLE_SCANF_FILE
97 #define SECUREC_ENABLE_SCANF_FILE       1
98 #endif
99 #ifndef SECUREC_ENABLE_WCHAR_FUNC
100 #define SECUREC_ENABLE_WCHAR_FUNC       1
101 #endif
102 #endif
103 
104 /* Default secure function declaration, default declarations for non-standard functions */
105 #ifndef SECUREC_SNPRINTF_TRUNCATED
106 #define SECUREC_SNPRINTF_TRUNCATED      1
107 #endif
108 
109 #if SECUREC_USING_STD_SECURE_LIB
110 #if defined(_MSC_VER) && _MSC_VER >= 1400
111 /* Declare secure functions that are not available in the VS compiler */
112 #ifndef SECUREC_ENABLE_MEMSET
113 #define SECUREC_ENABLE_MEMSET           1
114 #endif
115 /* VS 2005 have vsnprintf_s function */
116 #ifndef SECUREC_ENABLE_VSNPRINTF
117 #define SECUREC_ENABLE_VSNPRINTF        0
118 #endif
119 #ifndef SECUREC_ENABLE_SNPRINTF
120 /* VS 2005 have vsnprintf_s function Adapt the snprintf_s of the security function */
121 #define snprintf_s _snprintf_s
122 #define SECUREC_ENABLE_SNPRINTF         0
123 #endif
124 /* Before VS 2010 do not have v functions */
125 #if _MSC_VER <= 1600 || defined(SECUREC_FOR_V_SCANFS)
126 #ifndef SECUREC_ENABLE_VFSCANF
127 #define SECUREC_ENABLE_VFSCANF          1
128 #endif
129 #ifndef SECUREC_ENABLE_VSCANF
130 #define SECUREC_ENABLE_VSCANF           1
131 #endif
132 #ifndef SECUREC_ENABLE_VSSCANF
133 #define SECUREC_ENABLE_VSSCANF          1
134 #endif
135 #endif
136 
137 #else /* MSC VER */
138 #ifndef SECUREC_ENABLE_MEMSET
139 #define SECUREC_ENABLE_MEMSET           0
140 #endif
141 #ifndef SECUREC_ENABLE_SNPRINTF
142 #define SECUREC_ENABLE_SNPRINTF         0
143 #endif
144 #ifndef SECUREC_ENABLE_VSNPRINTF
145 #define SECUREC_ENABLE_VSNPRINTF        0
146 #endif
147 #endif
148 
149 #ifndef SECUREC_ENABLE_MEMMOVE
150 #define SECUREC_ENABLE_MEMMOVE          0
151 #endif
152 #ifndef SECUREC_ENABLE_MEMCPY
153 #define SECUREC_ENABLE_MEMCPY           0
154 #endif
155 #ifndef SECUREC_ENABLE_STRCPY
156 #define SECUREC_ENABLE_STRCPY           0
157 #endif
158 #ifndef SECUREC_ENABLE_STRNCPY
159 #define SECUREC_ENABLE_STRNCPY          0
160 #endif
161 #ifndef SECUREC_ENABLE_STRCAT
162 #define SECUREC_ENABLE_STRCAT           0
163 #endif
164 #ifndef SECUREC_ENABLE_STRNCAT
165 #define SECUREC_ENABLE_STRNCAT          0
166 #endif
167 #ifndef SECUREC_ENABLE_SPRINTF
168 #define SECUREC_ENABLE_SPRINTF          0
169 #endif
170 #ifndef SECUREC_ENABLE_VSPRINTF
171 #define SECUREC_ENABLE_VSPRINTF          0
172 #endif
173 #ifndef SECUREC_ENABLE_SSCANF
174 #define SECUREC_ENABLE_SSCANF           0
175 #endif
176 #ifndef SECUREC_ENABLE_VSSCANF
177 #define SECUREC_ENABLE_VSSCANF          0
178 #endif
179 #ifndef SECUREC_ENABLE_SCANF
180 #define SECUREC_ENABLE_SCANF            0
181 #endif
182 #ifndef SECUREC_ENABLE_VSCANF
183 #define SECUREC_ENABLE_VSCANF           0
184 #endif
185 
186 #ifndef SECUREC_ENABLE_FSCANF
187 #define SECUREC_ENABLE_FSCANF           0
188 #endif
189 #ifndef SECUREC_ENABLE_VFSCANF
190 #define SECUREC_ENABLE_VFSCANF          0
191 #endif
192 #ifndef SECUREC_ENABLE_STRTOK
193 #define SECUREC_ENABLE_STRTOK           0
194 #endif
195 #ifndef SECUREC_ENABLE_GETS
196 #define SECUREC_ENABLE_GETS             0
197 #endif
198 
199 #else /* SECUREC USE STD SECURE LIB */
200 
201 #ifndef SECUREC_ENABLE_MEMSET
202 #define SECUREC_ENABLE_MEMSET           1
203 #endif
204 #ifndef SECUREC_ENABLE_MEMMOVE
205 #define SECUREC_ENABLE_MEMMOVE          1
206 #endif
207 #ifndef SECUREC_ENABLE_MEMCPY
208 #define SECUREC_ENABLE_MEMCPY           1
209 #endif
210 #ifndef SECUREC_ENABLE_STRCPY
211 #define SECUREC_ENABLE_STRCPY           1
212 #endif
213 #ifndef SECUREC_ENABLE_STRNCPY
214 #define SECUREC_ENABLE_STRNCPY          1
215 #endif
216 #ifndef SECUREC_ENABLE_STRCAT
217 #define SECUREC_ENABLE_STRCAT           1
218 #endif
219 #ifndef SECUREC_ENABLE_STRNCAT
220 #define SECUREC_ENABLE_STRNCAT          1
221 #endif
222 #ifndef SECUREC_ENABLE_SPRINTF
223 #define SECUREC_ENABLE_SPRINTF          1
224 #endif
225 #ifndef SECUREC_ENABLE_VSPRINTF
226 #define SECUREC_ENABLE_VSPRINTF          1
227 #endif
228 #ifndef SECUREC_ENABLE_SNPRINTF
229 #define SECUREC_ENABLE_SNPRINTF         1
230 #endif
231 #ifndef SECUREC_ENABLE_VSNPRINTF
232 #define SECUREC_ENABLE_VSNPRINTF        1
233 #endif
234 #ifndef SECUREC_ENABLE_SSCANF
235 #define SECUREC_ENABLE_SSCANF           1
236 #endif
237 #ifndef SECUREC_ENABLE_VSSCANF
238 #define SECUREC_ENABLE_VSSCANF          1
239 #endif
240 #ifndef SECUREC_ENABLE_SCANF
241 #if SECUREC_ENABLE_SCANF_FILE
242 #define SECUREC_ENABLE_SCANF            1
243 #else
244 #define SECUREC_ENABLE_SCANF            0
245 #endif
246 #endif
247 #ifndef SECUREC_ENABLE_VSCANF
248 #if SECUREC_ENABLE_SCANF_FILE
249 #define SECUREC_ENABLE_VSCANF           1
250 #else
251 #define SECUREC_ENABLE_VSCANF           0
252 #endif
253 #endif
254 
255 #ifndef SECUREC_ENABLE_FSCANF
256 #if SECUREC_ENABLE_SCANF_FILE
257 #define SECUREC_ENABLE_FSCANF           1
258 #else
259 #define SECUREC_ENABLE_FSCANF           0
260 #endif
261 #endif
262 #ifndef SECUREC_ENABLE_VFSCANF
263 #if SECUREC_ENABLE_SCANF_FILE
264 #define SECUREC_ENABLE_VFSCANF          1
265 #else
266 #define SECUREC_ENABLE_VFSCANF          0
267 #endif
268 #endif
269 
270 #ifndef SECUREC_ENABLE_STRTOK
271 #define SECUREC_ENABLE_STRTOK           1
272 #endif
273 #ifndef SECUREC_ENABLE_GETS
274 #define SECUREC_ENABLE_GETS             1
275 #endif
276 #endif /* SECUREC_USE_STD_SECURE_LIB */
277 
278 #if !SECUREC_ENABLE_SCANF_FILE
279 #if SECUREC_ENABLE_FSCANF
280 #undef SECUREC_ENABLE_FSCANF
281 #define SECUREC_ENABLE_FSCANF           0
282 #endif
283 #if SECUREC_ENABLE_VFSCANF
284 #undef SECUREC_ENABLE_VFSCANF
285 #define SECUREC_ENABLE_VFSCANF          0
286 #endif
287 #if SECUREC_ENABLE_SCANF
288 #undef SECUREC_ENABLE_SCANF
289 #define SECUREC_ENABLE_SCANF            0
290 #endif
291 #if SECUREC_ENABLE_FSCANF
292 #undef SECUREC_ENABLE_FSCANF
293 #define SECUREC_ENABLE_FSCANF           0
294 #endif
295 
296 #endif
297 
298 #if SECUREC_IN_KERNEL
299 #include <linux/kernel.h>
300 #include <linux/module.h>
301 #else
302 #ifndef SECUREC_HAVE_STDIO_H
303 #define SECUREC_HAVE_STDIO_H 1
304 #endif
305 #ifndef SECUREC_HAVE_STRING_H
306 #define SECUREC_HAVE_STRING_H 1
307 #endif
308 #ifndef SECUREC_HAVE_STDLIB_H
309 #define SECUREC_HAVE_STDLIB_H 1
310 #endif
311 #if SECUREC_HAVE_STDIO_H
312 #include <stdio.h>
313 #endif
314 #if SECUREC_HAVE_STRING_H
315 #include <string.h>
316 #endif
317 #if SECUREC_HAVE_STDLIB_H
318 #include <stdlib.h>
319 #endif
320 #endif
321 
322 /*
323  * If you need high performance, enable the SECUREC_WITH_PERFORMANCE_ADDONS macro, default is enable.
324  * The macro is automatically closed on the windows platform and linux kernel
325  */
326 #ifndef SECUREC_WITH_PERFORMANCE_ADDONS
327 #if SECUREC_IN_KERNEL
328 #define SECUREC_WITH_PERFORMANCE_ADDONS 0
329 #else
330 #define SECUREC_WITH_PERFORMANCE_ADDONS 1
331 #endif
332 #endif
333 
334 /* If enable SECUREC_COMPATIBLE_WIN_FORMAT, the output format will be compatible to Windows. */
335 #if (defined(_WIN32) || defined(_WIN64) || defined(_MSC_VER)) && !defined(SECUREC_COMPATIBLE_LINUX_FORMAT)
336 #ifndef SECUREC_COMPATIBLE_WIN_FORMAT
337 #define SECUREC_COMPATIBLE_WIN_FORMAT
338 #endif
339 #endif
340 
341 #if defined(SECUREC_COMPATIBLE_WIN_FORMAT)
342 /* On windows platform, can't use optimized function for there is no __builtin_constant_p like function */
343 /* If need optimized macro, can define this: define __builtin_constant_p(x) 0 */
344 #ifdef SECUREC_WITH_PERFORMANCE_ADDONS
345 #undef SECUREC_WITH_PERFORMANCE_ADDONS
346 #define SECUREC_WITH_PERFORMANCE_ADDONS 0
347 #endif
348 #endif
349 
350 #if defined(__VXWORKS__) || defined(__vxworks) || defined(__VXWORKS) || defined(_VXWORKS_PLATFORM_)  || \
351     defined(SECUREC_VXWORKS_VERSION_5_4)
352 #ifndef SECUREC_VXWORKS_PLATFORM
353 #define SECUREC_VXWORKS_PLATFORM
354 #endif
355 #endif
356 
357 /* If enable SECUREC_COMPATIBLE_LINUX_FORMAT, the output format will be compatible to Linux. */
358 #if !defined(SECUREC_COMPATIBLE_WIN_FORMAT) && !defined(SECUREC_VXWORKS_PLATFORM)
359 #ifndef SECUREC_COMPATIBLE_LINUX_FORMAT
360 #define SECUREC_COMPATIBLE_LINUX_FORMAT
361 #endif
362 #endif
363 
364 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
365 #ifndef SECUREC_HAVE_STDDEF_H
366 #define SECUREC_HAVE_STDDEF_H 1
367 #endif
368 /* Some system may no stddef.h */
369 #if SECUREC_HAVE_STDDEF_H
370 #if !SECUREC_IN_KERNEL
371 #include <stddef.h>
372 #endif
373 #endif
374 #endif
375 
376 /*
377  * Add  the -DSECUREC_SUPPORT_FORMAT_WARNING=1  compiler option to supoort  -Wformat=2.
378  * Default does not check the format is that the same data type in the actual code.
379  * In the product is different in the original data type definition of VxWorks and Linux.
380  */
381 #ifndef SECUREC_SUPPORT_FORMAT_WARNING
382 #define SECUREC_SUPPORT_FORMAT_WARNING 0
383 #endif
384 
385 #if SECUREC_SUPPORT_FORMAT_WARNING
386 #define SECUREC_ATTRIBUTE(x, y)  __attribute__((format(printf, (x), (y))))
387 #else
388 #define SECUREC_ATTRIBUTE(x, y)
389 #endif
390 
391 /*
392  * Add the -DSECUREC_SUPPORT_BUILTIN_EXPECT=0 compiler option, if compiler can not support __builtin_expect.
393  */
394 #ifndef SECUREC_SUPPORT_BUILTIN_EXPECT
395 #define SECUREC_SUPPORT_BUILTIN_EXPECT 1
396 #endif
397 
398 #if SECUREC_SUPPORT_BUILTIN_EXPECT && defined(__GNUC__) && ((__GNUC__ > 3) || \
399     (defined(__GNUC_MINOR__) && (__GNUC__ == 3 && __GNUC_MINOR__ > 3)))
400 /*
401  * This is a built-in function that can be used without a declaration, if warning for declaration not found occurred,
402  * you can add -DSECUREC_NEED_BUILTIN_EXPECT_DECLARE to compiler options
403  */
404 #ifdef SECUREC_NEED_BUILTIN_EXPECT_DECLARE
405 long __builtin_expect(long exp, long c);
406 #endif
407 
408 #define SECUREC_LIKELY(x) __builtin_expect(!!(x), 1)
409 #define SECUREC_UNLIKELY(x) __builtin_expect(!!(x), 0)
410 #else
411 #define SECUREC_LIKELY(x) (x)
412 #define SECUREC_UNLIKELY(x) (x)
413 #endif
414 
415 /* Define the max length of the string */
416 #ifndef SECUREC_STRING_MAX_LEN
417 #define SECUREC_STRING_MAX_LEN 0x7fffffffUL
418 #endif
419 #define SECUREC_WCHAR_STRING_MAX_LEN (SECUREC_STRING_MAX_LEN / sizeof(wchar_t))
420 
421 /* Add SECUREC_MEM_MAX_LEN for memcpy and memmove */
422 #ifndef SECUREC_MEM_MAX_LEN
423 #define SECUREC_MEM_MAX_LEN 0x7fffffffUL
424 #endif
425 #define SECUREC_WCHAR_MEM_MAX_LEN (SECUREC_MEM_MAX_LEN / sizeof(wchar_t))
426 
427 #if SECUREC_STRING_MAX_LEN > 0x7fffffffUL
428 #error "max string is 2G"
429 #endif
430 
431 #if (defined(__GNUC__) && defined(__SIZEOF_POINTER__))
432 #if (__SIZEOF_POINTER__ != 4) && (__SIZEOF_POINTER__ != 8)
433 #error "unsupported system"
434 #endif
435 #endif
436 
437 #if defined(_WIN64) || defined(WIN64) || defined(__LP64__) || defined(_LP64)
438 #define SECUREC_ON_64BITS
439 #endif
440 
441 #if (!defined(SECUREC_ON_64BITS) && defined(__GNUC__) && defined(__SIZEOF_POINTER__))
442 #if __SIZEOF_POINTER__ == 8
443 #define SECUREC_ON_64BITS
444 #endif
445 #endif
446 
447 #if defined(__SVR4) || defined(__svr4__)
448 #define SECUREC_ON_SOLARIS
449 #endif
450 
451 #if (defined(__hpux) || defined(_AIX) || defined(SECUREC_ON_SOLARIS))
452 #define SECUREC_ON_UNIX
453 #endif
454 
455 /*
456  * Codes should run under the macro SECUREC_COMPATIBLE_LINUX_FORMAT in unknown system on default,
457  * and strtold.
458  * The function strtold is referenced first at ISO9899:1999(C99), and some old compilers can
459  * not support these functions. Here provides a macro to open these functions:
460  * SECUREC_SUPPORT_STRTOLD  -- If defined, strtold will be used
461  */
462 #ifndef SECUREC_SUPPORT_STRTOLD
463 #define SECUREC_SUPPORT_STRTOLD 0
464 #if (defined(SECUREC_COMPATIBLE_LINUX_FORMAT))
465 #if defined(__USE_ISOC99)  || \
466     (defined(_AIX) && defined(_ISOC99_SOURCE)) || \
467     (defined(__hpux) && defined(__ia64)) || \
468     (defined(SECUREC_ON_SOLARIS) && (!defined(_STRICT_STDC) && !defined(__XOPEN_OR_POSIX)) || \
469     defined(_STDC_C99) || defined(__EXTENSIONS__))
470 #undef  SECUREC_SUPPORT_STRTOLD
471 #define SECUREC_SUPPORT_STRTOLD 1
472 #endif
473 #endif
474 #if ((defined(SECUREC_WRLINUX_BELOW4) || defined(_WRLINUX_BELOW4_)))
475 #undef  SECUREC_SUPPORT_STRTOLD
476 #define SECUREC_SUPPORT_STRTOLD 0
477 #endif
478 #endif
479 
480 #if SECUREC_WITH_PERFORMANCE_ADDONS
481 
482 #ifndef SECUREC_TWO_MIN
483 #define SECUREC_TWO_MIN(a, b) ((a) < (b) ? (a) : (b))
484 #endif
485 
486 /* For strncpy_s performance optimization */
487 #define SECUREC_STRNCPY_SM(dest, destMax, src, count) \
488     (((void *)(dest) != NULL && (const void *)(src) != NULL && (size_t)(destMax) > 0 && \
489     (((unsigned long long)(destMax) & (unsigned long long)(-2)) < SECUREC_STRING_MAX_LEN) && \
490     (SECUREC_TWO_MIN((size_t)(count), strlen(src)) + 1) <= (size_t)(destMax)) ? \
491     (((size_t)(count) < strlen(src)) ? (memcpy((dest), (src), (count)), *((char *)(dest) + (count)) = '\0', EOK) : \
492     (memcpy((dest), (src), strlen(src) + 1), EOK)) : (strncpy_error((dest), (destMax), (src), (count))))
493 
494 #define SECUREC_STRCPY_SM(dest, destMax, src) \
495     (((void *)(dest) != NULL && (const void *)(src) != NULL && (size_t)(destMax) > 0 && \
496     (((unsigned long long)(destMax) & (unsigned long long)(-2)) < SECUREC_STRING_MAX_LEN) && \
497     (strlen(src) + 1) <= (size_t)(destMax)) ? (memcpy((dest), (src), strlen(src) + 1), EOK) : \
498     (strcpy_error((dest), (destMax), (src))))
499 
500 /* For strcat_s performance optimization */
501 #if defined(__GNUC__)
502 #define SECUREC_STRCAT_SM(dest, destMax, src) ({ \
503     int catRet_ = EOK; \
504     if ((void *)(dest) != NULL && (const void *)(src) != NULL && (size_t)(destMax) > 0 && \
505         (((unsigned long long)(destMax) & (unsigned long long)(-2)) < SECUREC_STRING_MAX_LEN)) { \
506         char *catTmpDst_ = (char *)(dest); \
507         size_t catRestSize_ = (destMax); \
508         while (catRestSize_ > 0 && *catTmpDst_ != '\0') { \
509             ++catTmpDst_; \
510             --catRestSize_; \
511         } \
512         if (catRestSize_ == 0) { \
513             catRet_ = EINVAL; \
514         } else if ((strlen(src) + 1) <= catRestSize_) { \
515             memcpy(catTmpDst_, (src), strlen(src) + 1); \
516             catRet_ = EOK; \
517         } else { \
518             catRet_ = ERANGE; \
519         } \
520         if (catRet_ != EOK) { \
521             catRet_ = strcat_s((dest), (destMax), (src)); \
522         } \
523     } else { \
524         catRet_ = strcat_s((dest), (destMax), (src)); \
525     } \
526     catRet_; \
527 })
528 #else
529 #define SECUREC_STRCAT_SM(dest, destMax, src) strcat_s((dest), (destMax), (src))
530 #endif
531 
532 /* For strncat_s performance optimization */
533 #if defined(__GNUC__)
534 #define SECUREC_STRNCAT_SM(dest, destMax, src, count) ({ \
535     int ncatRet_ = EOK; \
536     if ((void *)(dest) != NULL && (const void *)(src) != NULL && (size_t)(destMax) > 0 && \
537         (((unsigned long long)(destMax) & (unsigned long long)(-2)) < SECUREC_STRING_MAX_LEN)  && \
538         (((unsigned long long)(count) & (unsigned long long)(-2)) < SECUREC_STRING_MAX_LEN)) { \
539         char *ncatTmpDest_ = (char *)(dest); \
540         size_t ncatRestSize_ = (size_t)(destMax); \
541         while (ncatRestSize_ > 0 && *ncatTmpDest_ != '\0') { \
542             ++ncatTmpDest_; \
543             --ncatRestSize_; \
544         } \
545         if (ncatRestSize_ == 0) { \
546             ncatRet_ = EINVAL; \
547         } else if ((SECUREC_TWO_MIN((count), strlen(src)) + 1) <= ncatRestSize_) { \
548             if ((size_t)(count) < strlen(src)) { \
549                 memcpy(ncatTmpDest_, (src), (count)); \
550                 *(ncatTmpDest_ + (count)) = '\0'; \
551             } else { \
552                 memcpy(ncatTmpDest_, (src), strlen(src) + 1); \
553             } \
554         } else { \
555             ncatRet_ = ERANGE; \
556         } \
557         if (ncatRet_ != EOK) { \
558             ncatRet_ = strncat_s((dest), (destMax), (src), (count)); \
559         } \
560     } else { \
561         ncatRet_ = strncat_s((dest), (destMax), (src), (count)); \
562     } \
563     ncatRet_; \
564 })
565 #else
566 #define SECUREC_STRNCAT_SM(dest, destMax, src, count) strncat_s((dest), (destMax), (src), (count))
567 #endif
568 
569 /* This macro do not check buffer overlap by default */
570 #define  SECUREC_MEMCPY_SM(dest, destMax, src, count) \
571     (!(((size_t)(destMax) == 0) || \
572         (((unsigned long long)(destMax) & (unsigned long long)(-2)) > SECUREC_MEM_MAX_LEN) || \
573         ((size_t)(count) > (size_t)(destMax)) || ((void *)(dest)) == NULL || ((const void *)(src) == NULL)) ? \
574         (memcpy((dest), (src), (count)), EOK) : \
575         (memcpy_s((dest), (destMax), (src), (count))))
576 
577 #define  SECUREC_MEMSET_SM(dest, destMax, c, count) \
578     (!((((unsigned long long)(destMax) & (unsigned long long)(-2)) > SECUREC_MEM_MAX_LEN) || \
579         ((void *)(dest) == NULL) || ((size_t)(count) > (size_t)(destMax))) ? \
580         (memset((dest), (c), (count)), EOK) : \
581         (memset_s((dest), (destMax), (c), (count))))
582 
583 #endif
584 #endif
585 
586