]> git.ipfire.org Git - thirdparty/gcc.git/blob - libcilkrts/runtime/sslib/strcpy_s.c
[Patch AArch64] Fixup floating point division with -march=armv8-a+nosimd
[thirdparty/gcc.git] / libcilkrts / runtime / sslib / strcpy_s.c
1 /*------------------------------------------------------------------
2 * strcpy_s.c
3 *
4 * October 2008, Bo Berry
5 *
6 * Copyright (c) 2008-2011 by Cisco Systems, Inc
7 * All rights reserved.
8 *
9 * Permission is hereby granted, free of charge, to any person
10 * obtaining a copy of this software and associated documentation
11 * files (the "Software"), to deal in the Software without
12 * restriction, including without limitation the rights to use,
13 * copy, modify, merge, publish, distribute, sublicense, and/or
14 * sell copies of the Software, and to permit persons to whom the
15 * Software is furnished to do so, subject to the following
16 * conditions:
17 *
18 * The above copyright notice and this permission notice shall be
19 * included in all copies or substantial portions of the Software.
20 *
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
23 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
24 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
25 * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
26 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
27 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
28 * OTHER DEALINGS IN THE SOFTWARE.
29 *------------------------------------------------------------------
30 */
31
32 #include "safeclib_private.h"
33 #include "safe_str_constraint.h"
34 #include "safe_str_lib.h"
35
36
37 /**
38 * NAME
39 * strcpy_s
40 *
41 * SYNOPSIS
42 * #include "safe_str_lib.h"
43 * errno_t
44 * strcpy_s(char *dest, rsize_t dmax, const char *src)
45 *
46 * DESCRIPTION
47 * The strcpy_s function copies the string pointed to by src
48 * (including the terminating null character) into the array
49 * pointed to by dest. All elements following the terminating
50 * null character (if any) written by strcpy_s in the array
51 * of dmax characters pointed to by dest are nulled when
52 * strcpy_s returns.
53 *
54 * SPECIFIED IN
55 * ISO/IEC TR 24731, Programming languages, environments
56 * and system software interfaces, Extensions to the C Library,
57 * Part I: Bounds-checking interfaces
58 *
59 * INPUT PARAMETERS
60 * dest pointer to string that will be replaced by src.
61 *
62 * dmax restricted maximum length of dest
63 *
64 * src pointer to the string that will be copied
65 * to dest
66 *
67 * OUTPUT PARAMETERS
68 * dest updated
69 *
70 * RUNTIME CONSTRAINTS
71 * Neither dest nor src shall be a null pointer.
72 * dmax shall not be greater than RSIZE_MAX_STR.
73 * dmax shall not equal zero.
74 * dmax shall be greater than strnlen_s(src, dmax).
75 * Copying shall not take place between objects that overlap.
76 * If there is a runtime-constraint violation, then if dest
77 * is not a null pointer and destmax is greater than zero and
78 * not greater than RSIZE_MAX_STR, then strcpy_s nulls dest.
79 *
80 * RETURN VALUE
81 * EOK successful operation, the characters in src were
82 * copied into dest and the result is null terminated.
83 * ESNULLP NULL pointer
84 * ESZEROL zero length
85 * ESLEMAX length exceeds max limit
86 * ESOVRLP strings overlap
87 * ESNOSPC not enough space to copy src
88 *
89 * ALSO SEE
90 * strcat_s(), strncat_s(), strncpy_s()
91 *
92 */
93 errno_t
94 strcpy_s (char *dest, rsize_t dmax, const char *src)
95 {
96 rsize_t orig_dmax;
97 char *orig_dest;
98 const char *overlap_bumper;
99
100 if (dest == NULL) {
101 invoke_safe_str_constraint_handler("strcpy_s: dest is null",
102 NULL, ESNULLP);
103 return RCNEGATE(ESNULLP);
104 }
105
106 if (dmax == 0) {
107 invoke_safe_str_constraint_handler("strcpy_s: dmax is 0",
108 NULL, ESZEROL);
109 return RCNEGATE(ESZEROL);
110 }
111
112 if (dmax > RSIZE_MAX_STR) {
113 invoke_safe_str_constraint_handler("strcpy_s: dmax exceeds max",
114 NULL, ESLEMAX);
115 return RCNEGATE(ESLEMAX);
116 }
117
118 if (src == NULL) {
119 #ifdef SAFECLIB_STR_NULL_SLACK
120 /* null string to clear data */
121 while (dmax) { *dest = '\0'; dmax--; dest++; }
122 #else
123 *dest = '\0';
124 #endif
125 invoke_safe_str_constraint_handler("strcpy_s: src is null",
126 NULL, ESNULLP);
127 return RCNEGATE(ESNULLP);
128 }
129
130 if (dest == src) {
131 return RCNEGATE(EOK);
132 }
133
134 /* hold base of dest in case src was not copied */
135 orig_dmax = dmax;
136 orig_dest = dest;
137
138 if (dest < src) {
139 overlap_bumper = src;
140
141 while (dmax > 0) {
142 if (dest == overlap_bumper) {
143 handle_error(orig_dest, orig_dmax, "strcpy_s: "
144 "overlapping objects",
145 ESOVRLP);
146 return RCNEGATE(ESOVRLP);
147 }
148
149 *dest = *src;
150 if (*dest == '\0') {
151 #ifdef SAFECLIB_STR_NULL_SLACK
152 /* null slack to clear any data */
153 while (dmax) { *dest = '\0'; dmax--; dest++; }
154 #endif
155 return RCNEGATE(EOK);
156 }
157
158 dmax--;
159 dest++;
160 src++;
161 }
162
163 } else {
164 overlap_bumper = dest;
165
166 while (dmax > 0) {
167 if (src == overlap_bumper) {
168 handle_error(orig_dest, orig_dmax, "strcpy_s: "
169 "overlapping objects",
170 ESOVRLP);
171 return RCNEGATE(ESOVRLP);
172 }
173
174 *dest = *src;
175 if (*dest == '\0') {
176 #ifdef SAFECLIB_STR_NULL_SLACK
177 /* null slack to clear any data */
178 while (dmax) { *dest = '\0'; dmax--; dest++; }
179 #endif
180 return RCNEGATE(EOK);
181 }
182
183 dmax--;
184 dest++;
185 src++;
186 }
187 }
188
189 /*
190 * the entire src must have been copied, if not reset dest
191 * to null the string.
192 */
193 handle_error(orig_dest, orig_dmax, "strcpy_s: not "
194 "enough space for src",
195 ESNOSPC);
196 return RCNEGATE(ESNOSPC);
197 }
198 EXPORT_SYMBOL(strcpy_s);