]>
Commit | Line | Data |
---|---|---|
49698745 VG |
1 | // SPDX-License-Identifier: GPL-2.0 |
2 | #include <linux/ctype.h> | |
3 | #include <linux/kernel.h> | |
d58106c3 | 4 | #include <linux/errno.h> |
7e0d92f0 | 5 | #undef CONFIG_KASAN |
49698745 VG |
6 | #include "../lib/string.c" |
7 | ||
8 | int strncmp(const char *cs, const char *ct, size_t count) | |
9 | { | |
10 | unsigned char c1, c2; | |
11 | ||
12 | while (count) { | |
13 | c1 = *cs++; | |
14 | c2 = *ct++; | |
15 | if (c1 != c2) | |
16 | return c1 < c2 ? -1 : 1; | |
17 | if (!c1) | |
18 | break; | |
19 | count--; | |
20 | } | |
21 | return 0; | |
22 | } | |
23 | ||
24 | char *skip_spaces(const char *str) | |
25 | { | |
26 | while (isspace(*str)) | |
27 | ++str; | |
28 | return (char *)str; | |
29 | } | |
30 | ||
31 | char *strim(char *s) | |
32 | { | |
33 | size_t size; | |
34 | char *end; | |
35 | ||
36 | size = strlen(s); | |
37 | if (!size) | |
38 | return s; | |
39 | ||
40 | end = s + size - 1; | |
41 | while (end >= s && isspace(*end)) | |
42 | end--; | |
43 | *(end + 1) = '\0'; | |
44 | ||
45 | return skip_spaces(s); | |
46 | } | |
47 | ||
48 | /* Works only for digits and letters, but small and fast */ | |
49 | #define TOLOWER(x) ((x) | 0x20) | |
50 | ||
51 | static unsigned int simple_guess_base(const char *cp) | |
52 | { | |
53 | if (cp[0] == '0') { | |
54 | if (TOLOWER(cp[1]) == 'x' && isxdigit(cp[2])) | |
55 | return 16; | |
56 | else | |
57 | return 8; | |
58 | } else { | |
59 | return 10; | |
60 | } | |
61 | } | |
62 | ||
63 | /** | |
64 | * simple_strtoull - convert a string to an unsigned long long | |
65 | * @cp: The start of the string | |
66 | * @endp: A pointer to the end of the parsed string will be placed here | |
67 | * @base: The number base to use | |
68 | */ | |
69 | ||
70 | unsigned long long simple_strtoull(const char *cp, char **endp, | |
71 | unsigned int base) | |
72 | { | |
73 | unsigned long long result = 0; | |
74 | ||
75 | if (!base) | |
76 | base = simple_guess_base(cp); | |
77 | ||
78 | if (base == 16 && cp[0] == '0' && TOLOWER(cp[1]) == 'x') | |
79 | cp += 2; | |
80 | ||
81 | while (isxdigit(*cp)) { | |
82 | unsigned int value; | |
83 | ||
84 | value = isdigit(*cp) ? *cp - '0' : TOLOWER(*cp) - 'a' + 10; | |
85 | if (value >= base) | |
86 | break; | |
87 | result = result * base + value; | |
88 | cp++; | |
89 | } | |
90 | if (endp) | |
91 | *endp = (char *)cp; | |
92 | ||
93 | return result; | |
94 | } | |
95 | ||
96 | long simple_strtol(const char *cp, char **endp, unsigned int base) | |
97 | { | |
98 | if (*cp == '-') | |
99 | return -simple_strtoull(cp + 1, endp, base); | |
100 | ||
101 | return simple_strtoull(cp, endp, base); | |
102 | } | |
d58106c3 VG |
103 | |
104 | int kstrtobool(const char *s, bool *res) | |
105 | { | |
106 | if (!s) | |
107 | return -EINVAL; | |
108 | ||
109 | switch (s[0]) { | |
110 | case 'y': | |
111 | case 'Y': | |
112 | case '1': | |
113 | *res = true; | |
114 | return 0; | |
115 | case 'n': | |
116 | case 'N': | |
117 | case '0': | |
118 | *res = false; | |
119 | return 0; | |
120 | case 'o': | |
121 | case 'O': | |
122 | switch (s[1]) { | |
123 | case 'n': | |
124 | case 'N': | |
125 | *res = true; | |
126 | return 0; | |
127 | case 'f': | |
128 | case 'F': | |
129 | *res = false; | |
130 | return 0; | |
131 | default: | |
132 | break; | |
133 | } | |
134 | default: | |
135 | break; | |
136 | } | |
137 | ||
138 | return -EINVAL; | |
139 | } |