1/* $NetBSD: string.h,v 1.14 2020/09/05 13:37:59 mrg Exp $ */
2
3/*-
4 *
5 * SPDX-License-Identifier: BSD-2-Clause
6 *
7 * Copyright (c) 2006 The NetBSD Foundation, Inc.
8 * All rights reserved.
9 *
10 * This code is derived from software contributed to The NetBSD Foundation
11 * by Christos Zoulas.
12 *
13 * Redistribution and use in source and binary forms, with or without
14 * modification, are permitted provided that the following conditions
15 * are met:
16 * 1. Redistributions of source code must retain the above copyright
17 * notice, this list of conditions and the following disclaimer.
18 * 2. Redistributions in binary form must reproduce the above copyright
19 * notice, this list of conditions and the following disclaimer in the
20 * documentation and/or other materials provided with the distribution.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
23 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
24 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
25 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
26 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
27 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
28 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
29 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
30 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
31 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32 * POSSIBILITY OF SUCH DAMAGE.
33 */
34
35// zig patch: ssp/string.h header was added in FreeBSD 15
36#if __FreeBSD_version < 1500500
37 #error "ssp/string.h did not exist before FreeBSD 15"
38#endif /* error for FreeBSD before 15 */
39
40#ifndef _SSP_STRING_H_
41#define _SSP_STRING_H_
42
43#include <ssp/ssp.h>
44
45__BEGIN_DECLS
46void *__memcpy_chk(void *, const void *, size_t, size_t);
47void *__memmove_chk(void *, const void *, size_t, size_t);
48void *__memset_chk(void *, int, size_t, size_t);
49char *__stpcpy_chk(char *, const char *, size_t);
50char *__stpncpy_chk(char *, const char *, size_t, size_t);
51char *__strcat_chk(char *, const char *, size_t);
52char *__strcpy_chk(char *, const char *, size_t);
53char *__strncat_chk(char *, const char *, size_t, size_t);
54size_t __strlcat_chk(char *, const char *, size_t, size_t);
55char *__strncpy_chk(char *, const char *, size_t, size_t);
56size_t __strlcpy_chk(char *, const char *, size_t, size_t);
57__END_DECLS
58
59#if __SSP_FORTIFY_LEVEL > 0
60
61#define __ssp_bos_check3_typed_var(fun, dsttype, dsrvar, dst, srctype, srcvar, \
62 src, lenvar, len) __extension__ ({ \
63 srctype srcvar = (src); \
64 dsttype dstvar = (dst); \
65 size_t lenvar = (len); \
66 ((__ssp_bos0(dstvar) != (size_t)-1) ? \
67 __builtin___ ## fun ## _chk(dstvar, srcvar, lenvar, \
68 __ssp_bos0(dstvar)) : \
69 __ ## fun ## _ichk(dstvar, srcvar, lenvar)); \
70})
71
72#define __ssp_bos_check3_typed(fun, dsttype, dst, srctype, src, len) \
73 __ssp_bos_check3_typed_var(fun, dsttype, __ssp_var(dstv), dst, \
74 srctype, __ssp_var(srcv), src, __ssp_var(lenv), len)
75
76#define __ssp_bos_check3(fun, dst, src, len) \
77 __ssp_bos_check3_typed_var(fun, void *, __ssp_var(dstv), dst, \
78 const void *, __ssp_var(srcv), src, __ssp_var(lenv), len)
79
80#define __ssp_bos_check2_var(fun, dstvar, dst, srcvar, src) __extension__ ({ \
81 const void *srcvar = (src); \
82 void *dstvar = (dst); \
83 ((__ssp_bos0(dstvar) != (size_t)-1) ? \
84 __builtin___ ## fun ## _chk(dstvar, srcvar, \
85 __ssp_bos0(dstvar)) : \
86 __ ## fun ## _ichk(dstvar, srcvar)); \
87})
88
89#define __ssp_bos_check2(fun, dst, src) \
90 __ssp_bos_check2_var(fun, __ssp_var(dstv), dst, __ssp_var(srcv), src)
91
92#define __ssp_bos_icheck3_restrict(fun, type1, type2) \
93static __inline type1 __ ## fun ## _ichk(type1 __restrict, type2 __restrict, size_t); \
94static __inline __attribute__((__always_inline__)) type1 \
95__ ## fun ## _ichk(type1 __restrict dst, type2 __restrict src, size_t len) { \
96 return __builtin___ ## fun ## _chk(dst, src, len, __ssp_bos0(dst)); \
97}
98
99#define __ssp_bos_icheck3(fun, type1, type2) \
100static __inline type1 __ ## fun ## _ichk(type1, type2, size_t); \
101static __inline __attribute__((__always_inline__)) type1 \
102__ ## fun ## _ichk(type1 dst, type2 src, size_t len) { \
103 return __builtin___ ## fun ## _chk(dst, src, len, __ssp_bos0(dst)); \
104}
105
106#define __ssp_bos_icheck2_restrict(fun, type1, type2) \
107static __inline type1 __ ## fun ## _ichk(type1, type2); \
108static __inline __attribute__((__always_inline__)) type1 \
109__ ## fun ## _ichk(type1 __restrict dst, type2 __restrict src) { \
110 return __builtin___ ## fun ## _chk(dst, src, __ssp_bos0(dst)); \
111}
112
113__BEGIN_DECLS
114__ssp_bos_icheck3_restrict(memcpy, void *, const void *)
115__ssp_bos_icheck3_restrict(mempcpy, void *, const void *)
116__ssp_bos_icheck3(memmove, void *, const void *)
117__ssp_bos_icheck3(memset, void *, int)
118__ssp_redirect(void *, memset_explicit, (void *__buf, int __ch, size_t __len),
119 (__buf, __ch, __len));
120__ssp_bos_icheck2_restrict(stpcpy, char *, const char *)
121__ssp_bos_icheck3_restrict(stpncpy, char *, const char *)
122__ssp_bos_icheck2_restrict(strcpy, char *, const char *)
123__ssp_bos_icheck2_restrict(strcat, char *, const char *)
124__ssp_redirect0(int, strerror_r, (int __errnum, char *__buf, size_t __len),
125 (__errnum, __buf, __len));
126__ssp_bos_icheck3_restrict(strncpy, char *, const char *)
127__ssp_bos_icheck3_restrict(strncat, char *, const char *)
128__END_DECLS
129
130#define memcpy(dst, src, len) __ssp_bos_check3(memcpy, dst, src, len)
131#define mempcpy(dst, src, len) __ssp_bos_check3(mempcpy, dst, src, len)
132#define memmove(dst, src, len) __ssp_bos_check3(memmove, dst, src, len)
133#define memset(dst, val, len) \
134 __ssp_bos_check3_typed(memset, void *, dst, int, val, len)
135#define stpcpy(dst, src) __ssp_bos_check2(stpcpy, dst, src)
136#define stpncpy(dst, src, len) __ssp_bos_check3(stpncpy, dst, src, len)
137#define strcpy(dst, src) __ssp_bos_check2(strcpy, dst, src)
138#define strcat(dst, src) __ssp_bos_check2(strcat, dst, src)
139#define strlcpy(dst, src, dstlen) \
140 __strlcpy_chk(dst, src, dstlen, __ssp_bos(dst))
141#define strncpy(dst, src, len) __ssp_bos_check3(strncpy, dst, src, len)
142#define strlcat(dst, src, dstlen) \
143 __strlcat_chk(dst, src, dstlen, __ssp_bos(dst))
144#define strncat(dst, src, len) __ssp_bos_check3(strncat, dst, src, len)
145
146#endif /* __SSP_FORTIFY_LEVEL > 0 */
147#endif /* _SSP_STRING_H_ */