#include <errno.h>
#include <linux/ctype.h>
+/* from lib/kstrtox.c */
+static const char *_parse_integer_fixup_radix(const char *s, unsigned int *base)
+{
+ if (*base == 0) {
+ if (s[0] == '0') {
+ if (tolower(s[1]) == 'x' && isxdigit(s[2]))
+ *base = 16;
+ else
+ *base = 8;
+ } else {
+ int i = 0;
+ char var;
+
+ *base = 10;
+
+ do {
+ var = tolower(s[i++]);
+ if (var >= 'a' && var <= 'f') {
+ *base = 16;
+ break;
+ }
+
+ if (!(var >= '0' && var <= '9'))
+ break;
+ } while (var);
+ }
+ }
+
+ if (*base == 16 && s[0] == '0' && tolower(s[1]) == 'x')
+ s += 2;
+ return s;
+}
+
unsigned long simple_strtoul(const char *cp, char **endp,
unsigned int base)
{
unsigned long result = 0;
unsigned long value;
- if (*cp == '0') {
- cp++;
- if ((*cp == 'x') && isxdigit(cp[1])) {
- base = 16;
- cp++;
- }
-
- if (!base)
- base = 8;
- }
-
- if (!base)
- base = 10;
+ cp = _parse_integer_fixup_radix(cp, &base);
while (isxdigit(*cp) && (value = isdigit(*cp) ? *cp-'0' : (islower(*cp)
? toupper(*cp) : *cp)-'A'+10) < base) {
unsigned long ustrtoul(const char *cp, char **endp, unsigned int base)
{
unsigned long result = simple_strtoul(cp, endp, base);
- switch (**endp) {
- case 'G':
+ switch (tolower(**endp)) {
+ case 'g':
result *= 1024;
/* fall through */
- case 'M':
+ case 'm':
result *= 1024;
/* fall through */
- case 'K':
case 'k':
result *= 1024;
- if ((*endp)[1] == 'i') {
- if ((*endp)[2] == 'B')
- (*endp) += 3;
- else
- (*endp) += 2;
- }
+ (*endp)++;
+ if (**endp == 'i')
+ (*endp)++;
+ if (**endp == 'B')
+ (*endp)++;
}
return result;
}
unsigned long long ustrtoull(const char *cp, char **endp, unsigned int base)
{
unsigned long long result = simple_strtoull(cp, endp, base);
- switch (**endp) {
- case 'G':
+ switch (tolower(**endp)) {
+ case 'g':
result *= 1024;
/* fall through */
- case 'M':
+ case 'm':
result *= 1024;
/* fall through */
- case 'K':
case 'k':
result *= 1024;
- if ((*endp)[1] == 'i') {
- if ((*endp)[2] == 'B')
- (*endp) += 3;
- else
- (*endp) += 2;
- }
+ (*endp)++;
+ if (**endp == 'i')
+ (*endp)++;
+ if (**endp == 'B')
+ (*endp)++;
}
return result;
}
{
unsigned long long result = 0, value;
- if (*cp == '0') {
- cp++;
- if ((*cp == 'x') && isxdigit(cp[1])) {
- base = 16;
- cp++;
- }
-
- if (!base)
- base = 8;
- }
-
- if (!base)
- base = 10;
+ cp = _parse_integer_fixup_radix(cp, &base);
while (isxdigit(*cp) && (value = isdigit(*cp) ? *cp - '0'
: (islower(*cp) ? toupper(*cp) : *cp) - 'A' + 10) < base) {
{
return trailing_strtoln(str, NULL);
}
+
+void str_to_upper(const char *in, char *out, size_t len)
+{
+ for (; len > 0 && *in; len--)
+ *out++ = toupper(*in++);
+ if (len)
+ *out = '\0';
+}