Adds function strim_dupe which trims leading & trailing whitespace and duplicate adjacent. Initial use case is to shorten T10 storage IDs. Signed-off-by: Tony Asleson <tasleson@xxxxxxxxxx> --- include/linux/string.h | 2 ++ lib/string.c | 35 +++++++++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+) diff --git a/include/linux/string.h b/include/linux/string.h index b6ccdc2c7f02..bcca6bfab6ab 100644 --- a/include/linux/string.h +++ b/include/linux/string.h @@ -72,6 +72,8 @@ extern char * __must_check skip_spaces(const char *); extern char *strim(char *); +extern size_t strim_dupe(char *s); + static inline __must_check char *strstrip(char *str) { return strim(str); diff --git a/lib/string.c b/lib/string.c index 08ec58cc673b..1186cce1f66b 100644 --- a/lib/string.c +++ b/lib/string.c @@ -515,6 +515,41 @@ char *strim(char *s) } EXPORT_SYMBOL(strim); +/** + * Removes leading and trailing whitespace and removes duplicate + * adjacent whitespace in a string, modifies string in place. + * @s The %NUL-terminated string to have spaces removed + * Returns the new length + */ +size_t strim_dupe(char *s) +{ + size_t ret = 0; + char *w = s; + char *p; + + /* + * This will remove all leading and duplicate adjacent, but leave + * 1 space at the end if one or more are present. + */ + for (p = s; *p != '\0'; ++p) { + if (!isspace(*p) || (p != s && !isspace(*(p - 1)))) { + *w = *p; + ++w; + ret += 1; + } + } + + *w = '\0'; + + /* Take off the last character if it's a space too */ + if (ret && isspace(*(w - 1))) { + ret--; + *(w - 1) = '\0'; + } + return ret; +} +EXPORT_SYMBOL(strim_dupe); + #ifndef __HAVE_ARCH_STRLEN /** * strlen - Find the length of a string -- 2.21.0