Branch data Line data Source code
1 : : /*
2 : : * Convert integer string representation to an integer.
3 : : * If an integer doesn't fit into specified type, -E is returned.
4 : : *
5 : : * Integer starts with optional sign.
6 : : * kstrtou*() functions do not accept sign "-".
7 : : *
8 : : * Radix 0 means autodetection: leading "0x" implies radix 16,
9 : : * leading "0" implies radix 8, otherwise radix is 10.
10 : : * Autodetection hints work after optional sign, but not before.
11 : : *
12 : : * If -E is returned, result is not touched.
13 : : */
14 : : #include <linux/ctype.h>
15 : : #include <linux/errno.h>
16 : : #include <linux/kernel.h>
17 : : #include <linux/math64.h>
18 : : #include <linux/export.h>
19 : : #include <linux/types.h>
20 : : #include <asm/uaccess.h>
21 : : #include "kstrtox.h"
22 : :
23 : 0 : const char *_parse_integer_fixup_radix(const char *s, unsigned int *base)
24 : : {
25 [ + ]: 211 : if (*base == 0) {
26 [ + + ]: 294 : if (s[0] == '0') {
27 [ - + ][ # # ]: 4 : if (_tolower(s[1]) == 'x' && isxdigit(s[2]))
28 : 0 : *base = 16;
29 : : else
30 : 4 : *base = 8;
31 : : } else
32 : 79 : *base = 10;
33 : : }
34 [ # # ][ # # ]: 0 : if (*base == 16 && s[0] == '0' && _tolower(s[1]) == 'x')
[ # # ]
35 : 0 : s += 2;
36 : 0 : return s;
37 : : }
38 : :
39 : : /*
40 : : * Convert non-negative integer string representation in explicitly given radix
41 : : * to an integer.
42 : : * Return number of characters consumed maybe or-ed with overflow bit.
43 : : * If overflow occurs, result integer (incorrect) is still returned.
44 : : *
45 : : * Don't you dare use this function.
46 : : */
47 : 0 : unsigned int _parse_integer(const char *s, unsigned int base, unsigned long long *p)
48 : : {
49 : : unsigned long long res;
50 : : unsigned int rv;
51 : : int overflow;
52 : :
53 : : res = 0;
54 : : rv = 0;
55 : : overflow = 0;
56 [ + + ]: 788 : while (*s) {
57 : : unsigned int val;
58 : :
59 [ + + ]: 707 : if ('0' <= *s && *s <= '9')
60 : 577 : val = *s - '0';
61 : : else if ('a' <= _tolower(*s) && _tolower(*s) <= 'f')
62 : 0 : val = _tolower(*s) - 'a' + 10;
63 : : else
64 : : break;
65 : :
66 [ + ]: 577 : if (val >= base)
67 : : break;
68 : : /*
69 : : * Check for overflow only if we are within range of
70 : : * it in the max base we support (16)
71 : : */
72 [ + + ]: 788 : if (unlikely(res & (~0ull << 60))) {
73 [ # # ]: 0 : if (res > div_u64(ULLONG_MAX - val, base))
74 : : overflow = 1;
75 : : }
76 : 577 : res = res * base + val;
77 : 577 : rv++;
78 : 577 : s++;
79 : : }
80 : 0 : *p = res;
81 [ # # ]: 0 : if (overflow)
82 : 0 : rv |= KSTRTOX_OVERFLOW;
83 : 0 : return rv;
84 : : }
85 : :
86 : 0 : static int _kstrtoull(const char *s, unsigned int base, unsigned long long *res)
87 : : {
88 : : unsigned long long _res;
89 : : unsigned int rv;
90 : :
91 : 2 : s = _parse_integer_fixup_radix(s, &base);
92 : 2 : rv = _parse_integer(s, base, &_res);
93 [ + - ]: 2 : if (rv & KSTRTOX_OVERFLOW)
94 : : return -ERANGE;
95 [ + - ]: 2 : if (rv == 0)
96 : : return -EINVAL;
97 : 2 : s += rv;
98 [ + - ]: 2 : if (*s == '\n')
99 : 2 : s++;
100 [ + ]: 2 : if (*s)
101 : : return -EINVAL;
102 : 2 : *res = _res;
103 : 2 : return 0;
104 : : }
105 : :
106 : : /**
107 : : * kstrtoull - convert a string to an unsigned long long
108 : : * @s: The start of the string. The string must be null-terminated, and may also
109 : : * include a single newline before its terminating null. The first character
110 : : * may also be a plus sign, but not a minus sign.
111 : : * @base: The number base to use. The maximum supported base is 16. If base is
112 : : * given as 0, then the base of the string is automatically detected with the
113 : : * conventional semantics - If it begins with 0x the number will be parsed as a
114 : : * hexadecimal (case insensitive), if it otherwise begins with 0, it will be
115 : : * parsed as an octal number. Otherwise it will be parsed as a decimal.
116 : : * @res: Where to write the result of the conversion on success.
117 : : *
118 : : * Returns 0 on success, -ERANGE on overflow and -EINVAL on parsing error.
119 : : * Used as a replacement for the obsolete simple_strtoull. Return code must
120 : : * be checked.
121 : : */
122 : 0 : int kstrtoull(const char *s, unsigned int base, unsigned long long *res)
123 : : {
124 [ # # ][ # # ]: 2 : if (s[0] == '+')
[ # # ][ # # ]
[ # # ][ # # ]
[ - + ]
125 : 0 : s++;
126 : 2 : return _kstrtoull(s, base, res);
127 : : }
128 : : EXPORT_SYMBOL(kstrtoull);
129 : :
130 : : /**
131 : : * kstrtoll - convert a string to a long long
132 : : * @s: The start of the string. The string must be null-terminated, and may also
133 : : * include a single newline before its terminating null. The first character
134 : : * may also be a plus sign or a minus sign.
135 : : * @base: The number base to use. The maximum supported base is 16. If base is
136 : : * given as 0, then the base of the string is automatically detected with the
137 : : * conventional semantics - If it begins with 0x the number will be parsed as a
138 : : * hexadecimal (case insensitive), if it otherwise begins with 0, it will be
139 : : * parsed as an octal number. Otherwise it will be parsed as a decimal.
140 : : * @res: Where to write the result of the conversion on success.
141 : : *
142 : : * Returns 0 on success, -ERANGE on overflow and -EINVAL on parsing error.
143 : : * Used as a replacement for the obsolete simple_strtoull. Return code must
144 : : * be checked.
145 : : */
146 : 0 : int kstrtoll(const char *s, unsigned int base, long long *res)
147 : : {
148 : : unsigned long long tmp;
149 : : int rv;
150 : :
151 [ # # ]: 0 : if (s[0] == '-') {
152 : 0 : rv = _kstrtoull(s + 1, base, &tmp);
153 [ # # ]: 0 : if (rv < 0)
154 : : return rv;
155 [ # # ]: 0 : if ((long long)(-tmp) >= 0)
156 : : return -ERANGE;
157 : 0 : *res = -tmp;
158 : : } else {
159 : : rv = kstrtoull(s, base, &tmp);
160 [ # # ]: 0 : if (rv < 0)
161 : : return rv;
162 [ # # ]: 0 : if ((long long)tmp < 0)
163 : : return -ERANGE;
164 : 0 : *res = tmp;
165 : : }
166 : : return 0;
167 : : }
168 : : EXPORT_SYMBOL(kstrtoll);
169 : :
170 : : /* Internal, do not use. */
171 : 0 : int _kstrtoul(const char *s, unsigned int base, unsigned long *res)
172 : : {
173 : : unsigned long long tmp;
174 : : int rv;
175 : :
176 : : rv = kstrtoull(s, base, &tmp);
177 [ # # ]: 0 : if (rv < 0)
178 : : return rv;
179 [ # # ]: 0 : if (tmp != (unsigned long long)(unsigned long)tmp)
180 : : return -ERANGE;
181 : 0 : *res = tmp;
182 : 0 : return 0;
183 : : }
184 : : EXPORT_SYMBOL(_kstrtoul);
185 : :
186 : : /* Internal, do not use. */
187 : 0 : int _kstrtol(const char *s, unsigned int base, long *res)
188 : : {
189 : : long long tmp;
190 : : int rv;
191 : :
192 : 0 : rv = kstrtoll(s, base, &tmp);
193 [ # # ]: 0 : if (rv < 0)
194 : : return rv;
195 [ # # ]: 0 : if (tmp != (long long)(long)tmp)
196 : : return -ERANGE;
197 : 0 : *res = tmp;
198 : 0 : return 0;
199 : : }
200 : : EXPORT_SYMBOL(_kstrtol);
201 : :
202 : : /**
203 : : * kstrtouint - convert a string to an unsigned int
204 : : * @s: The start of the string. The string must be null-terminated, and may also
205 : : * include a single newline before its terminating null. The first character
206 : : * may also be a plus sign, but not a minus sign.
207 : : * @base: The number base to use. The maximum supported base is 16. If base is
208 : : * given as 0, then the base of the string is automatically detected with the
209 : : * conventional semantics - If it begins with 0x the number will be parsed as a
210 : : * hexadecimal (case insensitive), if it otherwise begins with 0, it will be
211 : : * parsed as an octal number. Otherwise it will be parsed as a decimal.
212 : : * @res: Where to write the result of the conversion on success.
213 : : *
214 : : * Returns 0 on success, -ERANGE on overflow and -EINVAL on parsing error.
215 : : * Used as a replacement for the obsolete simple_strtoull. Return code must
216 : : * be checked.
217 : : */
218 : 0 : int kstrtouint(const char *s, unsigned int base, unsigned int *res)
219 : : {
220 : : unsigned long long tmp;
221 : : int rv;
222 : :
223 : : rv = kstrtoull(s, base, &tmp);
224 [ # # ]: 0 : if (rv < 0)
225 : : return rv;
226 [ # # ]: 0 : if (tmp != (unsigned long long)(unsigned int)tmp)
227 : : return -ERANGE;
228 : 0 : *res = tmp;
229 : 0 : return 0;
230 : : }
231 : : EXPORT_SYMBOL(kstrtouint);
232 : :
233 : : /**
234 : : * kstrtoint - convert a string to an int
235 : : * @s: The start of the string. The string must be null-terminated, and may also
236 : : * include a single newline before its terminating null. The first character
237 : : * may also be a plus sign or a minus sign.
238 : : * @base: The number base to use. The maximum supported base is 16. If base is
239 : : * given as 0, then the base of the string is automatically detected with the
240 : : * conventional semantics - If it begins with 0x the number will be parsed as a
241 : : * hexadecimal (case insensitive), if it otherwise begins with 0, it will be
242 : : * parsed as an octal number. Otherwise it will be parsed as a decimal.
243 : : * @res: Where to write the result of the conversion on success.
244 : : *
245 : : * Returns 0 on success, -ERANGE on overflow and -EINVAL on parsing error.
246 : : * Used as a replacement for the obsolete simple_strtoull. Return code must
247 : : * be checked.
248 : : */
249 : 0 : int kstrtoint(const char *s, unsigned int base, int *res)
250 : : {
251 : : long long tmp;
252 : : int rv;
253 : :
254 : 0 : rv = kstrtoll(s, base, &tmp);
255 [ # # ]: 0 : if (rv < 0)
256 : : return rv;
257 [ # # ]: 0 : if (tmp != (long long)(int)tmp)
258 : : return -ERANGE;
259 : 0 : *res = tmp;
260 : 0 : return 0;
261 : : }
262 : : EXPORT_SYMBOL(kstrtoint);
263 : :
264 : 0 : int kstrtou16(const char *s, unsigned int base, u16 *res)
265 : : {
266 : : unsigned long long tmp;
267 : : int rv;
268 : :
269 : : rv = kstrtoull(s, base, &tmp);
270 [ # # ]: 0 : if (rv < 0)
271 : : return rv;
272 [ # # ]: 0 : if (tmp != (unsigned long long)(u16)tmp)
273 : : return -ERANGE;
274 : 0 : *res = tmp;
275 : 0 : return 0;
276 : : }
277 : : EXPORT_SYMBOL(kstrtou16);
278 : :
279 : 0 : int kstrtos16(const char *s, unsigned int base, s16 *res)
280 : : {
281 : : long long tmp;
282 : : int rv;
283 : :
284 : 0 : rv = kstrtoll(s, base, &tmp);
285 [ # # ]: 0 : if (rv < 0)
286 : : return rv;
287 [ # # ]: 0 : if (tmp != (long long)(s16)tmp)
288 : : return -ERANGE;
289 : 0 : *res = tmp;
290 : 0 : return 0;
291 : : }
292 : : EXPORT_SYMBOL(kstrtos16);
293 : :
294 : 0 : int kstrtou8(const char *s, unsigned int base, u8 *res)
295 : : {
296 : : unsigned long long tmp;
297 : : int rv;
298 : :
299 : : rv = kstrtoull(s, base, &tmp);
300 [ # # ]: 0 : if (rv < 0)
301 : : return rv;
302 [ # # ]: 0 : if (tmp != (unsigned long long)(u8)tmp)
303 : : return -ERANGE;
304 : 0 : *res = tmp;
305 : 0 : return 0;
306 : : }
307 : : EXPORT_SYMBOL(kstrtou8);
308 : :
309 : 0 : int kstrtos8(const char *s, unsigned int base, s8 *res)
310 : : {
311 : : long long tmp;
312 : : int rv;
313 : :
314 : 0 : rv = kstrtoll(s, base, &tmp);
315 [ # # ]: 0 : if (rv < 0)
316 : : return rv;
317 [ # # ]: 0 : if (tmp != (long long)(s8)tmp)
318 : : return -ERANGE;
319 : 0 : *res = tmp;
320 : 0 : return 0;
321 : : }
322 : : EXPORT_SYMBOL(kstrtos8);
323 : :
324 : : #define kstrto_from_user(f, g, type) \
325 : : int f(const char __user *s, size_t count, unsigned int base, type *res) \
326 : : { \
327 : : /* sign, base 2 representation, newline, terminator */ \
328 : : char buf[1 + sizeof(type) * 8 + 1 + 1]; \
329 : : \
330 : : count = min(count, sizeof(buf) - 1); \
331 : : if (copy_from_user(buf, s, count)) \
332 : : return -EFAULT; \
333 : : buf[count] = '\0'; \
334 : : return g(buf, base, res); \
335 : : } \
336 : : EXPORT_SYMBOL(f)
337 : :
338 [ # # ]: 0 : kstrto_from_user(kstrtoull_from_user, kstrtoull, unsigned long long);
339 [ # # ]: 0 : kstrto_from_user(kstrtoll_from_user, kstrtoll, long long);
340 [ # # ]: 0 : kstrto_from_user(kstrtoul_from_user, kstrtoul, unsigned long);
341 [ # # ]: 0 : kstrto_from_user(kstrtol_from_user, kstrtol, long);
342 [ # # ]: 0 : kstrto_from_user(kstrtouint_from_user, kstrtouint, unsigned int);
343 [ # # ]: 0 : kstrto_from_user(kstrtoint_from_user, kstrtoint, int);
344 [ # # ]: 0 : kstrto_from_user(kstrtou16_from_user, kstrtou16, u16);
345 [ # # ]: 0 : kstrto_from_user(kstrtos16_from_user, kstrtos16, s16);
346 [ # # ]: 0 : kstrto_from_user(kstrtou8_from_user, kstrtou8, u8);
347 [ # # ]: 0 : kstrto_from_user(kstrtos8_from_user, kstrtos8, s8);
|