Line | Count | Source |
1 | | /* A more useful interface to strtol. |
2 | | |
3 | | Copyright (C) 1995-1996, 1998-2001, 2003-2007, 2009-2026 Free Software |
4 | | Foundation, Inc. |
5 | | |
6 | | This program is free software: you can redistribute it and/or modify |
7 | | it under the terms of the GNU General Public License as published by |
8 | | the Free Software Foundation, either version 3 of the License, or |
9 | | (at your option) any later version. |
10 | | |
11 | | This program is distributed in the hope that it will be useful, |
12 | | but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 | | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 | | GNU General Public License for more details. |
15 | | |
16 | | You should have received a copy of the GNU General Public License |
17 | | along with this program. If not, see <https://www.gnu.org/licenses/>. */ |
18 | | |
19 | | /* Written by Jim Meyering. */ |
20 | | |
21 | | #ifndef __strtol |
22 | 4.89k | # define __strtol strtol |
23 | 4.89k | # define __strtol_t long int |
24 | | # define __xstrtol xstrtol |
25 | | # define STRTOL_T_MINIMUM LONG_MIN |
26 | | # define STRTOL_T_MAXIMUM LONG_MAX |
27 | | #endif |
28 | | |
29 | | #include <config.h> |
30 | | |
31 | | #include "xstrtol.h" |
32 | | |
33 | | #include <ctype.h> |
34 | | #include <errno.h> |
35 | | #include <limits.h> |
36 | | #include <stdckdint.h> |
37 | | #include <stdlib.h> |
38 | | #include <string.h> |
39 | | |
40 | | #if XSTRTOL_INCLUDE_INTTYPES_H |
41 | | # include <inttypes.h> |
42 | | #endif |
43 | | |
44 | | #include "intprops.h" |
45 | | |
46 | | static strtol_error |
47 | | bkm_scale (__strtol_t *x, int scale_factor) |
48 | 0 | { |
49 | 0 | __strtol_t scaled; |
50 | 0 | if (ckd_mul (&scaled, *x, scale_factor)) |
51 | 0 | { |
52 | 0 | *x = *x < 0 ? TYPE_MINIMUM (__strtol_t) : TYPE_MAXIMUM (__strtol_t); |
53 | 0 | return LONGINT_OVERFLOW; |
54 | 0 | } |
55 | | |
56 | 0 | *x = scaled; |
57 | |
|
58 | 0 | return LONGINT_OK; |
59 | 0 | } Unexecuted instantiation: xstrtoul.c:bkm_scale Unexecuted instantiation: xstrtol.c:bkm_scale Unexecuted instantiation: xstrtoll.c:bkm_scale Unexecuted instantiation: xstrtoull.c:bkm_scale |
60 | | |
61 | | static strtol_error |
62 | | bkm_scale_by_power (__strtol_t *x, int base, int power) |
63 | 0 | { |
64 | 0 | strtol_error err = LONGINT_OK; |
65 | 0 | while (power--) |
66 | 0 | err |= bkm_scale (x, base); |
67 | 0 | return err; |
68 | 0 | } Unexecuted instantiation: xstrtoul.c:bkm_scale_by_power Unexecuted instantiation: xstrtol.c:bkm_scale_by_power Unexecuted instantiation: xstrtoll.c:bkm_scale_by_power Unexecuted instantiation: xstrtoull.c:bkm_scale_by_power |
69 | | |
70 | | strtol_error |
71 | | __xstrtol (char const *nptr, char **endptr, int base, |
72 | | __strtol_t *val, char const *valid_suffixes) |
73 | 31.0k | { |
74 | 31.0k | char *t_ptr; |
75 | 31.0k | char **p = endptr ? endptr : &t_ptr; |
76 | | |
77 | 31.0k | if (! TYPE_SIGNED (__strtol_t)) |
78 | 9.45k | { |
79 | 9.45k | char const *q = nptr; |
80 | 9.45k | unsigned char ch = *q; |
81 | 9.45k | while (isspace (ch)) |
82 | 9.01k | ch = *++q; |
83 | 9.45k | if (ch == '-') |
84 | 487 | { |
85 | 487 | *p = (char *) nptr; |
86 | 487 | return LONGINT_INVALID; |
87 | 487 | } |
88 | 9.45k | } |
89 | | |
90 | 31.0k | errno = 0; |
91 | 30.5k | __strtol_t tmp = __strtol (nptr, p, base); |
92 | 30.5k | strtol_error err = LONGINT_OK; |
93 | | |
94 | 30.5k | if (*p == nptr) |
95 | 5.27k | { |
96 | | /* If there is no number but there is a valid suffix, assume the |
97 | | number is 1. The string is invalid otherwise. */ |
98 | 5.27k | if (! (valid_suffixes && *nptr && strchr (valid_suffixes, *nptr))) |
99 | 5.27k | return LONGINT_INVALID; |
100 | 0 | tmp = 1; |
101 | 0 | } |
102 | 25.2k | else if (errno != 0) |
103 | 1.73k | { |
104 | 1.73k | if (errno != ERANGE) |
105 | 0 | return LONGINT_INVALID; |
106 | 1.73k | err = LONGINT_OVERFLOW; |
107 | 1.73k | } |
108 | | |
109 | | /* Let valid_suffixes == NULL mean "allow any suffix". */ |
110 | | /* FIXME: update all callers except the ones that allow suffixes |
111 | | after the number, changing last parameter NULL to "". */ |
112 | 25.2k | if (!valid_suffixes) |
113 | 25.2k | { |
114 | 25.2k | *val = tmp; |
115 | 25.2k | return err; |
116 | 25.2k | } |
117 | | |
118 | 0 | if (**p != '\0') |
119 | 0 | { |
120 | 0 | if (!strchr (valid_suffixes, **p)) |
121 | 0 | { |
122 | 0 | *val = tmp; |
123 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; |
124 | 0 | } |
125 | | |
126 | 0 | int xbase = 1024; |
127 | 0 | int suffixes = 1; |
128 | 0 | switch (**p) |
129 | 0 | { |
130 | 0 | case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm': |
131 | 0 | case 'P': case 'Q': case 'R': case 'T': case 't': case 'Y': case 'Z': |
132 | | |
133 | | /* The "valid suffix" '0' is a special flag meaning that |
134 | | an optional second suffix is allowed, which can change |
135 | | the base. A suffix "B" (e.g. "100MB") stands for a power |
136 | | of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for |
137 | | a power of 1024. If no suffix (e.g. "100M"), assume |
138 | | power-of-1024. */ |
139 | |
|
140 | 0 | if (strchr (valid_suffixes, '0')) |
141 | 0 | switch (p[0][1]) |
142 | 0 | { |
143 | 0 | case 'i': |
144 | 0 | if (p[0][2] == 'B') |
145 | 0 | suffixes += 2; |
146 | 0 | break; |
147 | | |
148 | 0 | case 'B': |
149 | 0 | case 'D': /* 'D' is obsolescent */ |
150 | 0 | xbase = 1000; |
151 | 0 | suffixes++; |
152 | 0 | break; |
153 | 0 | } |
154 | 0 | } |
155 | | |
156 | 0 | strtol_error overflow; |
157 | 0 | switch (**p) |
158 | 0 | { |
159 | 0 | case 'b': |
160 | 0 | overflow = bkm_scale (&tmp, 512); |
161 | 0 | break; |
162 | | |
163 | 0 | case 'B': |
164 | | /* This obsolescent first suffix is distinct from the 'B' |
165 | | second suffix above. E.g., 'tar -L 1000B' means change |
166 | | the tape after writing 1000 KiB of data. */ |
167 | 0 | overflow = bkm_scale (&tmp, 1024); |
168 | 0 | break; |
169 | | |
170 | 0 | case 'c': |
171 | 0 | overflow = LONGINT_OK; |
172 | 0 | break; |
173 | | |
174 | 0 | case 'E': /* exa or exbi */ |
175 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 6); |
176 | 0 | break; |
177 | | |
178 | 0 | case 'G': /* giga or gibi */ |
179 | 0 | case 'g': /* 'g' is undocumented; for compatibility only */ |
180 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 3); |
181 | 0 | break; |
182 | | |
183 | 0 | case 'k': /* kilo */ |
184 | 0 | case 'K': /* kibi */ |
185 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 1); |
186 | 0 | break; |
187 | | |
188 | 0 | case 'M': /* mega or mebi */ |
189 | 0 | case 'm': /* 'm' is undocumented; for compatibility only */ |
190 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 2); |
191 | 0 | break; |
192 | | |
193 | 0 | case 'P': /* peta or pebi */ |
194 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 5); |
195 | 0 | break; |
196 | | |
197 | 0 | case 'Q': /* quetta or 2**100 */ |
198 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 10); |
199 | 0 | break; |
200 | | |
201 | 0 | case 'R': /* ronna or 2**90 */ |
202 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 9); |
203 | 0 | break; |
204 | | |
205 | 0 | case 'T': /* tera or tebi */ |
206 | 0 | case 't': /* 't' is undocumented; for compatibility only */ |
207 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 4); |
208 | 0 | break; |
209 | | |
210 | 0 | case 'w': |
211 | 0 | overflow = bkm_scale (&tmp, 2); |
212 | 0 | break; |
213 | | |
214 | 0 | case 'Y': /* yotta or 2**80 */ |
215 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 8); |
216 | 0 | break; |
217 | | |
218 | 0 | case 'Z': /* zetta or 2**70 */ |
219 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 7); |
220 | 0 | break; |
221 | | |
222 | 0 | default: |
223 | 0 | *val = tmp; |
224 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; |
225 | 0 | } |
226 | | |
227 | 0 | err |= overflow; |
228 | 0 | *p += suffixes; |
229 | 0 | if (**p) |
230 | 0 | err |= LONGINT_INVALID_SUFFIX_CHAR; |
231 | 0 | } |
232 | | |
233 | 0 | *val = tmp; |
234 | 0 | return err; |
235 | 0 | } Line | Count | Source | 73 | 4.30k | { | 74 | 4.30k | char *t_ptr; | 75 | 4.30k | char **p = endptr ? endptr : &t_ptr; | 76 | | | 77 | 4.30k | if (! TYPE_SIGNED (__strtol_t)) | 78 | 4.30k | { | 79 | 4.30k | char const *q = nptr; | 80 | 4.30k | unsigned char ch = *q; | 81 | 4.30k | while (isspace (ch)) | 82 | 3.52k | ch = *++q; | 83 | 4.30k | if (ch == '-') | 84 | 282 | { | 85 | 282 | *p = (char *) nptr; | 86 | 282 | return LONGINT_INVALID; | 87 | 282 | } | 88 | 4.30k | } | 89 | | | 90 | 4.30k | errno = 0; | 91 | 4.02k | __strtol_t tmp = __strtol (nptr, p, base); | 92 | 4.02k | strtol_error err = LONGINT_OK; | 93 | | | 94 | 4.02k | if (*p == nptr) | 95 | 344 | { | 96 | | /* If there is no number but there is a valid suffix, assume the | 97 | | number is 1. The string is invalid otherwise. */ | 98 | 344 | if (! (valid_suffixes && *nptr && strchr (valid_suffixes, *nptr))) | 99 | 344 | return LONGINT_INVALID; | 100 | 0 | tmp = 1; | 101 | 0 | } | 102 | 3.68k | else if (errno != 0) | 103 | 213 | { | 104 | 213 | if (errno != ERANGE) | 105 | 0 | return LONGINT_INVALID; | 106 | 213 | err = LONGINT_OVERFLOW; | 107 | 213 | } | 108 | | | 109 | | /* Let valid_suffixes == NULL mean "allow any suffix". */ | 110 | | /* FIXME: update all callers except the ones that allow suffixes | 111 | | after the number, changing last parameter NULL to "". */ | 112 | 3.68k | if (!valid_suffixes) | 113 | 3.68k | { | 114 | 3.68k | *val = tmp; | 115 | 3.68k | return err; | 116 | 3.68k | } | 117 | | | 118 | 0 | if (**p != '\0') | 119 | 0 | { | 120 | 0 | if (!strchr (valid_suffixes, **p)) | 121 | 0 | { | 122 | 0 | *val = tmp; | 123 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 124 | 0 | } | 125 | | | 126 | 0 | int xbase = 1024; | 127 | 0 | int suffixes = 1; | 128 | 0 | switch (**p) | 129 | 0 | { | 130 | 0 | case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm': | 131 | 0 | case 'P': case 'Q': case 'R': case 'T': case 't': case 'Y': case 'Z': | 132 | | | 133 | | /* The "valid suffix" '0' is a special flag meaning that | 134 | | an optional second suffix is allowed, which can change | 135 | | the base. A suffix "B" (e.g. "100MB") stands for a power | 136 | | of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for | 137 | | a power of 1024. If no suffix (e.g. "100M"), assume | 138 | | power-of-1024. */ | 139 | |
| 140 | 0 | if (strchr (valid_suffixes, '0')) | 141 | 0 | switch (p[0][1]) | 142 | 0 | { | 143 | 0 | case 'i': | 144 | 0 | if (p[0][2] == 'B') | 145 | 0 | suffixes += 2; | 146 | 0 | break; | 147 | | | 148 | 0 | case 'B': | 149 | 0 | case 'D': /* 'D' is obsolescent */ | 150 | 0 | xbase = 1000; | 151 | 0 | suffixes++; | 152 | 0 | break; | 153 | 0 | } | 154 | 0 | } | 155 | | | 156 | 0 | strtol_error overflow; | 157 | 0 | switch (**p) | 158 | 0 | { | 159 | 0 | case 'b': | 160 | 0 | overflow = bkm_scale (&tmp, 512); | 161 | 0 | break; | 162 | | | 163 | 0 | case 'B': | 164 | | /* This obsolescent first suffix is distinct from the 'B' | 165 | | second suffix above. E.g., 'tar -L 1000B' means change | 166 | | the tape after writing 1000 KiB of data. */ | 167 | 0 | overflow = bkm_scale (&tmp, 1024); | 168 | 0 | break; | 169 | | | 170 | 0 | case 'c': | 171 | 0 | overflow = LONGINT_OK; | 172 | 0 | break; | 173 | | | 174 | 0 | case 'E': /* exa or exbi */ | 175 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 6); | 176 | 0 | break; | 177 | | | 178 | 0 | case 'G': /* giga or gibi */ | 179 | 0 | case 'g': /* 'g' is undocumented; for compatibility only */ | 180 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 3); | 181 | 0 | break; | 182 | | | 183 | 0 | case 'k': /* kilo */ | 184 | 0 | case 'K': /* kibi */ | 185 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 1); | 186 | 0 | break; | 187 | | | 188 | 0 | case 'M': /* mega or mebi */ | 189 | 0 | case 'm': /* 'm' is undocumented; for compatibility only */ | 190 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 2); | 191 | 0 | break; | 192 | | | 193 | 0 | case 'P': /* peta or pebi */ | 194 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 5); | 195 | 0 | break; | 196 | | | 197 | 0 | case 'Q': /* quetta or 2**100 */ | 198 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 10); | 199 | 0 | break; | 200 | | | 201 | 0 | case 'R': /* ronna or 2**90 */ | 202 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 9); | 203 | 0 | break; | 204 | | | 205 | 0 | case 'T': /* tera or tebi */ | 206 | 0 | case 't': /* 't' is undocumented; for compatibility only */ | 207 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 4); | 208 | 0 | break; | 209 | | | 210 | 0 | case 'w': | 211 | 0 | overflow = bkm_scale (&tmp, 2); | 212 | 0 | break; | 213 | | | 214 | 0 | case 'Y': /* yotta or 2**80 */ | 215 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 8); | 216 | 0 | break; | 217 | | | 218 | 0 | case 'Z': /* zetta or 2**70 */ | 219 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 7); | 220 | 0 | break; | 221 | | | 222 | 0 | default: | 223 | 0 | *val = tmp; | 224 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 225 | 0 | } | 226 | | | 227 | 0 | err |= overflow; | 228 | 0 | *p += suffixes; | 229 | 0 | if (**p) | 230 | 0 | err |= LONGINT_INVALID_SUFFIX_CHAR; | 231 | 0 | } | 232 | | | 233 | 0 | *val = tmp; | 234 | 0 | return err; | 235 | 0 | } |
Line | Count | Source | 73 | 4.89k | { | 74 | 4.89k | char *t_ptr; | 75 | 4.89k | char **p = endptr ? endptr : &t_ptr; | 76 | | | 77 | 4.89k | if (! TYPE_SIGNED (__strtol_t)) | 78 | 0 | { | 79 | 0 | char const *q = nptr; | 80 | 0 | unsigned char ch = *q; | 81 | 0 | while (isspace (ch)) | 82 | 0 | ch = *++q; | 83 | 0 | if (ch == '-') | 84 | 0 | { | 85 | 0 | *p = (char *) nptr; | 86 | 0 | return LONGINT_INVALID; | 87 | 0 | } | 88 | 0 | } | 89 | | | 90 | 4.89k | errno = 0; | 91 | 4.89k | __strtol_t tmp = __strtol (nptr, p, base); | 92 | 4.89k | strtol_error err = LONGINT_OK; | 93 | | | 94 | 4.89k | if (*p == nptr) | 95 | 652 | { | 96 | | /* If there is no number but there is a valid suffix, assume the | 97 | | number is 1. The string is invalid otherwise. */ | 98 | 652 | if (! (valid_suffixes && *nptr && strchr (valid_suffixes, *nptr))) | 99 | 652 | return LONGINT_INVALID; | 100 | 0 | tmp = 1; | 101 | 0 | } | 102 | 4.24k | else if (errno != 0) | 103 | 245 | { | 104 | 245 | if (errno != ERANGE) | 105 | 0 | return LONGINT_INVALID; | 106 | 245 | err = LONGINT_OVERFLOW; | 107 | 245 | } | 108 | | | 109 | | /* Let valid_suffixes == NULL mean "allow any suffix". */ | 110 | | /* FIXME: update all callers except the ones that allow suffixes | 111 | | after the number, changing last parameter NULL to "". */ | 112 | 4.24k | if (!valid_suffixes) | 113 | 4.24k | { | 114 | 4.24k | *val = tmp; | 115 | 4.24k | return err; | 116 | 4.24k | } | 117 | | | 118 | 0 | if (**p != '\0') | 119 | 0 | { | 120 | 0 | if (!strchr (valid_suffixes, **p)) | 121 | 0 | { | 122 | 0 | *val = tmp; | 123 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 124 | 0 | } | 125 | | | 126 | 0 | int xbase = 1024; | 127 | 0 | int suffixes = 1; | 128 | 0 | switch (**p) | 129 | 0 | { | 130 | 0 | case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm': | 131 | 0 | case 'P': case 'Q': case 'R': case 'T': case 't': case 'Y': case 'Z': | 132 | | | 133 | | /* The "valid suffix" '0' is a special flag meaning that | 134 | | an optional second suffix is allowed, which can change | 135 | | the base. A suffix "B" (e.g. "100MB") stands for a power | 136 | | of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for | 137 | | a power of 1024. If no suffix (e.g. "100M"), assume | 138 | | power-of-1024. */ | 139 | |
| 140 | 0 | if (strchr (valid_suffixes, '0')) | 141 | 0 | switch (p[0][1]) | 142 | 0 | { | 143 | 0 | case 'i': | 144 | 0 | if (p[0][2] == 'B') | 145 | 0 | suffixes += 2; | 146 | 0 | break; | 147 | | | 148 | 0 | case 'B': | 149 | 0 | case 'D': /* 'D' is obsolescent */ | 150 | 0 | xbase = 1000; | 151 | 0 | suffixes++; | 152 | 0 | break; | 153 | 0 | } | 154 | 0 | } | 155 | | | 156 | 0 | strtol_error overflow; | 157 | 0 | switch (**p) | 158 | 0 | { | 159 | 0 | case 'b': | 160 | 0 | overflow = bkm_scale (&tmp, 512); | 161 | 0 | break; | 162 | | | 163 | 0 | case 'B': | 164 | | /* This obsolescent first suffix is distinct from the 'B' | 165 | | second suffix above. E.g., 'tar -L 1000B' means change | 166 | | the tape after writing 1000 KiB of data. */ | 167 | 0 | overflow = bkm_scale (&tmp, 1024); | 168 | 0 | break; | 169 | | | 170 | 0 | case 'c': | 171 | 0 | overflow = LONGINT_OK; | 172 | 0 | break; | 173 | | | 174 | 0 | case 'E': /* exa or exbi */ | 175 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 6); | 176 | 0 | break; | 177 | | | 178 | 0 | case 'G': /* giga or gibi */ | 179 | 0 | case 'g': /* 'g' is undocumented; for compatibility only */ | 180 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 3); | 181 | 0 | break; | 182 | | | 183 | 0 | case 'k': /* kilo */ | 184 | 0 | case 'K': /* kibi */ | 185 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 1); | 186 | 0 | break; | 187 | | | 188 | 0 | case 'M': /* mega or mebi */ | 189 | 0 | case 'm': /* 'm' is undocumented; for compatibility only */ | 190 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 2); | 191 | 0 | break; | 192 | | | 193 | 0 | case 'P': /* peta or pebi */ | 194 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 5); | 195 | 0 | break; | 196 | | | 197 | 0 | case 'Q': /* quetta or 2**100 */ | 198 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 10); | 199 | 0 | break; | 200 | | | 201 | 0 | case 'R': /* ronna or 2**90 */ | 202 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 9); | 203 | 0 | break; | 204 | | | 205 | 0 | case 'T': /* tera or tebi */ | 206 | 0 | case 't': /* 't' is undocumented; for compatibility only */ | 207 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 4); | 208 | 0 | break; | 209 | | | 210 | 0 | case 'w': | 211 | 0 | overflow = bkm_scale (&tmp, 2); | 212 | 0 | break; | 213 | | | 214 | 0 | case 'Y': /* yotta or 2**80 */ | 215 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 8); | 216 | 0 | break; | 217 | | | 218 | 0 | case 'Z': /* zetta or 2**70 */ | 219 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 7); | 220 | 0 | break; | 221 | | | 222 | 0 | default: | 223 | 0 | *val = tmp; | 224 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 225 | 0 | } | 226 | | | 227 | 0 | err |= overflow; | 228 | 0 | *p += suffixes; | 229 | 0 | if (**p) | 230 | 0 | err |= LONGINT_INVALID_SUFFIX_CHAR; | 231 | 0 | } | 232 | | | 233 | 0 | *val = tmp; | 234 | 0 | return err; | 235 | 0 | } |
Line | Count | Source | 73 | 16.6k | { | 74 | 16.6k | char *t_ptr; | 75 | 16.6k | char **p = endptr ? endptr : &t_ptr; | 76 | | | 77 | 16.6k | if (! TYPE_SIGNED (__strtol_t)) | 78 | 0 | { | 79 | 0 | char const *q = nptr; | 80 | 0 | unsigned char ch = *q; | 81 | 0 | while (isspace (ch)) | 82 | 0 | ch = *++q; | 83 | 0 | if (ch == '-') | 84 | 0 | { | 85 | 0 | *p = (char *) nptr; | 86 | 0 | return LONGINT_INVALID; | 87 | 0 | } | 88 | 0 | } | 89 | | | 90 | 16.6k | errno = 0; | 91 | 16.6k | __strtol_t tmp = __strtol (nptr, p, base); | 92 | 16.6k | strtol_error err = LONGINT_OK; | 93 | | | 94 | 16.6k | if (*p == nptr) | 95 | 2.18k | { | 96 | | /* If there is no number but there is a valid suffix, assume the | 97 | | number is 1. The string is invalid otherwise. */ | 98 | 2.18k | if (! (valid_suffixes && *nptr && strchr (valid_suffixes, *nptr))) | 99 | 2.18k | return LONGINT_INVALID; | 100 | 0 | tmp = 1; | 101 | 0 | } | 102 | 14.4k | else if (errno != 0) | 103 | 843 | { | 104 | 843 | if (errno != ERANGE) | 105 | 0 | return LONGINT_INVALID; | 106 | 843 | err = LONGINT_OVERFLOW; | 107 | 843 | } | 108 | | | 109 | | /* Let valid_suffixes == NULL mean "allow any suffix". */ | 110 | | /* FIXME: update all callers except the ones that allow suffixes | 111 | | after the number, changing last parameter NULL to "". */ | 112 | 14.4k | if (!valid_suffixes) | 113 | 14.4k | { | 114 | 14.4k | *val = tmp; | 115 | 14.4k | return err; | 116 | 14.4k | } | 117 | | | 118 | 0 | if (**p != '\0') | 119 | 0 | { | 120 | 0 | if (!strchr (valid_suffixes, **p)) | 121 | 0 | { | 122 | 0 | *val = tmp; | 123 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 124 | 0 | } | 125 | | | 126 | 0 | int xbase = 1024; | 127 | 0 | int suffixes = 1; | 128 | 0 | switch (**p) | 129 | 0 | { | 130 | 0 | case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm': | 131 | 0 | case 'P': case 'Q': case 'R': case 'T': case 't': case 'Y': case 'Z': | 132 | | | 133 | | /* The "valid suffix" '0' is a special flag meaning that | 134 | | an optional second suffix is allowed, which can change | 135 | | the base. A suffix "B" (e.g. "100MB") stands for a power | 136 | | of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for | 137 | | a power of 1024. If no suffix (e.g. "100M"), assume | 138 | | power-of-1024. */ | 139 | |
| 140 | 0 | if (strchr (valid_suffixes, '0')) | 141 | 0 | switch (p[0][1]) | 142 | 0 | { | 143 | 0 | case 'i': | 144 | 0 | if (p[0][2] == 'B') | 145 | 0 | suffixes += 2; | 146 | 0 | break; | 147 | | | 148 | 0 | case 'B': | 149 | 0 | case 'D': /* 'D' is obsolescent */ | 150 | 0 | xbase = 1000; | 151 | 0 | suffixes++; | 152 | 0 | break; | 153 | 0 | } | 154 | 0 | } | 155 | | | 156 | 0 | strtol_error overflow; | 157 | 0 | switch (**p) | 158 | 0 | { | 159 | 0 | case 'b': | 160 | 0 | overflow = bkm_scale (&tmp, 512); | 161 | 0 | break; | 162 | | | 163 | 0 | case 'B': | 164 | | /* This obsolescent first suffix is distinct from the 'B' | 165 | | second suffix above. E.g., 'tar -L 1000B' means change | 166 | | the tape after writing 1000 KiB of data. */ | 167 | 0 | overflow = bkm_scale (&tmp, 1024); | 168 | 0 | break; | 169 | | | 170 | 0 | case 'c': | 171 | 0 | overflow = LONGINT_OK; | 172 | 0 | break; | 173 | | | 174 | 0 | case 'E': /* exa or exbi */ | 175 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 6); | 176 | 0 | break; | 177 | | | 178 | 0 | case 'G': /* giga or gibi */ | 179 | 0 | case 'g': /* 'g' is undocumented; for compatibility only */ | 180 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 3); | 181 | 0 | break; | 182 | | | 183 | 0 | case 'k': /* kilo */ | 184 | 0 | case 'K': /* kibi */ | 185 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 1); | 186 | 0 | break; | 187 | | | 188 | 0 | case 'M': /* mega or mebi */ | 189 | 0 | case 'm': /* 'm' is undocumented; for compatibility only */ | 190 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 2); | 191 | 0 | break; | 192 | | | 193 | 0 | case 'P': /* peta or pebi */ | 194 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 5); | 195 | 0 | break; | 196 | | | 197 | 0 | case 'Q': /* quetta or 2**100 */ | 198 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 10); | 199 | 0 | break; | 200 | | | 201 | 0 | case 'R': /* ronna or 2**90 */ | 202 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 9); | 203 | 0 | break; | 204 | | | 205 | 0 | case 'T': /* tera or tebi */ | 206 | 0 | case 't': /* 't' is undocumented; for compatibility only */ | 207 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 4); | 208 | 0 | break; | 209 | | | 210 | 0 | case 'w': | 211 | 0 | overflow = bkm_scale (&tmp, 2); | 212 | 0 | break; | 213 | | | 214 | 0 | case 'Y': /* yotta or 2**80 */ | 215 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 8); | 216 | 0 | break; | 217 | | | 218 | 0 | case 'Z': /* zetta or 2**70 */ | 219 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 7); | 220 | 0 | break; | 221 | | | 222 | 0 | default: | 223 | 0 | *val = tmp; | 224 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 225 | 0 | } | 226 | | | 227 | 0 | err |= overflow; | 228 | 0 | *p += suffixes; | 229 | 0 | if (**p) | 230 | 0 | err |= LONGINT_INVALID_SUFFIX_CHAR; | 231 | 0 | } | 232 | | | 233 | 0 | *val = tmp; | 234 | 0 | return err; | 235 | 0 | } |
Line | Count | Source | 73 | 5.14k | { | 74 | 5.14k | char *t_ptr; | 75 | 5.14k | char **p = endptr ? endptr : &t_ptr; | 76 | | | 77 | 5.14k | if (! TYPE_SIGNED (__strtol_t)) | 78 | 5.14k | { | 79 | 5.14k | char const *q = nptr; | 80 | 5.14k | unsigned char ch = *q; | 81 | 5.14k | while (isspace (ch)) | 82 | 5.49k | ch = *++q; | 83 | 5.14k | if (ch == '-') | 84 | 205 | { | 85 | 205 | *p = (char *) nptr; | 86 | 205 | return LONGINT_INVALID; | 87 | 205 | } | 88 | 5.14k | } | 89 | | | 90 | 5.14k | errno = 0; | 91 | 4.94k | __strtol_t tmp = __strtol (nptr, p, base); | 92 | 4.94k | strtol_error err = LONGINT_OK; | 93 | | | 94 | 4.94k | if (*p == nptr) | 95 | 2.09k | { | 96 | | /* If there is no number but there is a valid suffix, assume the | 97 | | number is 1. The string is invalid otherwise. */ | 98 | 2.09k | if (! (valid_suffixes && *nptr && strchr (valid_suffixes, *nptr))) | 99 | 2.09k | return LONGINT_INVALID; | 100 | 0 | tmp = 1; | 101 | 0 | } | 102 | 2.85k | else if (errno != 0) | 103 | 431 | { | 104 | 431 | if (errno != ERANGE) | 105 | 0 | return LONGINT_INVALID; | 106 | 431 | err = LONGINT_OVERFLOW; | 107 | 431 | } | 108 | | | 109 | | /* Let valid_suffixes == NULL mean "allow any suffix". */ | 110 | | /* FIXME: update all callers except the ones that allow suffixes | 111 | | after the number, changing last parameter NULL to "". */ | 112 | 2.85k | if (!valid_suffixes) | 113 | 2.85k | { | 114 | 2.85k | *val = tmp; | 115 | 2.85k | return err; | 116 | 2.85k | } | 117 | | | 118 | 0 | if (**p != '\0') | 119 | 0 | { | 120 | 0 | if (!strchr (valid_suffixes, **p)) | 121 | 0 | { | 122 | 0 | *val = tmp; | 123 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 124 | 0 | } | 125 | | | 126 | 0 | int xbase = 1024; | 127 | 0 | int suffixes = 1; | 128 | 0 | switch (**p) | 129 | 0 | { | 130 | 0 | case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm': | 131 | 0 | case 'P': case 'Q': case 'R': case 'T': case 't': case 'Y': case 'Z': | 132 | | | 133 | | /* The "valid suffix" '0' is a special flag meaning that | 134 | | an optional second suffix is allowed, which can change | 135 | | the base. A suffix "B" (e.g. "100MB") stands for a power | 136 | | of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for | 137 | | a power of 1024. If no suffix (e.g. "100M"), assume | 138 | | power-of-1024. */ | 139 | |
| 140 | 0 | if (strchr (valid_suffixes, '0')) | 141 | 0 | switch (p[0][1]) | 142 | 0 | { | 143 | 0 | case 'i': | 144 | 0 | if (p[0][2] == 'B') | 145 | 0 | suffixes += 2; | 146 | 0 | break; | 147 | | | 148 | 0 | case 'B': | 149 | 0 | case 'D': /* 'D' is obsolescent */ | 150 | 0 | xbase = 1000; | 151 | 0 | suffixes++; | 152 | 0 | break; | 153 | 0 | } | 154 | 0 | } | 155 | | | 156 | 0 | strtol_error overflow; | 157 | 0 | switch (**p) | 158 | 0 | { | 159 | 0 | case 'b': | 160 | 0 | overflow = bkm_scale (&tmp, 512); | 161 | 0 | break; | 162 | | | 163 | 0 | case 'B': | 164 | | /* This obsolescent first suffix is distinct from the 'B' | 165 | | second suffix above. E.g., 'tar -L 1000B' means change | 166 | | the tape after writing 1000 KiB of data. */ | 167 | 0 | overflow = bkm_scale (&tmp, 1024); | 168 | 0 | break; | 169 | | | 170 | 0 | case 'c': | 171 | 0 | overflow = LONGINT_OK; | 172 | 0 | break; | 173 | | | 174 | 0 | case 'E': /* exa or exbi */ | 175 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 6); | 176 | 0 | break; | 177 | | | 178 | 0 | case 'G': /* giga or gibi */ | 179 | 0 | case 'g': /* 'g' is undocumented; for compatibility only */ | 180 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 3); | 181 | 0 | break; | 182 | | | 183 | 0 | case 'k': /* kilo */ | 184 | 0 | case 'K': /* kibi */ | 185 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 1); | 186 | 0 | break; | 187 | | | 188 | 0 | case 'M': /* mega or mebi */ | 189 | 0 | case 'm': /* 'm' is undocumented; for compatibility only */ | 190 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 2); | 191 | 0 | break; | 192 | | | 193 | 0 | case 'P': /* peta or pebi */ | 194 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 5); | 195 | 0 | break; | 196 | | | 197 | 0 | case 'Q': /* quetta or 2**100 */ | 198 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 10); | 199 | 0 | break; | 200 | | | 201 | 0 | case 'R': /* ronna or 2**90 */ | 202 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 9); | 203 | 0 | break; | 204 | | | 205 | 0 | case 'T': /* tera or tebi */ | 206 | 0 | case 't': /* 't' is undocumented; for compatibility only */ | 207 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 4); | 208 | 0 | break; | 209 | | | 210 | 0 | case 'w': | 211 | 0 | overflow = bkm_scale (&tmp, 2); | 212 | 0 | break; | 213 | | | 214 | 0 | case 'Y': /* yotta or 2**80 */ | 215 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 8); | 216 | 0 | break; | 217 | | | 218 | 0 | case 'Z': /* zetta or 2**70 */ | 219 | 0 | overflow = bkm_scale_by_power (&tmp, xbase, 7); | 220 | 0 | break; | 221 | | | 222 | 0 | default: | 223 | 0 | *val = tmp; | 224 | 0 | return err | LONGINT_INVALID_SUFFIX_CHAR; | 225 | 0 | } | 226 | | | 227 | 0 | err |= overflow; | 228 | 0 | *p += suffixes; | 229 | 0 | if (**p) | 230 | 0 | err |= LONGINT_INVALID_SUFFIX_CHAR; | 231 | 0 | } | 232 | | | 233 | 0 | *val = tmp; | 234 | 0 | return err; | 235 | 0 | } |
|