8be66a
From 50b103a982dfd6f1b2bf98bbc98a8063fa153e89 Mon Sep 17 00:00:00 2001
8be66a
From: Lennart Poettering <lennart@poettering.net>
8be66a
Date: Fri, 23 Nov 2018 16:27:15 +0100
8be66a
Subject: [PATCH] strv: add new macro STARTSWITH_SET()
8be66a
8be66a
This is to startswith() what PATH_STARTSWITH_SET() is to
8be66a
path_startswith().
8be66a
8be66a
Or in other words, checks if the specified string has any of the listed
8be66a
prefixes, and if so, returns the remainder of the string.
8be66a
8be66a
(cherry picked from commit 52f1552073047195d51901f7e5a5a4fa3189034e)
8be66a
8be66a
Related: #1848373
8be66a
---
8be66a
 src/basic/strv.h     | 12 ++++++++++++
8be66a
 src/test/test-strv.c | 15 +++++++++++++++
8be66a
 2 files changed, 27 insertions(+)
8be66a
8be66a
diff --git a/src/basic/strv.h b/src/basic/strv.h
8be66a
index 51d03db940..c1e4c973b6 100644
8be66a
--- a/src/basic/strv.h
8be66a
+++ b/src/basic/strv.h
8be66a
@@ -136,6 +136,18 @@ void strv_print(char **l);
8be66a
                 _x && strv_contains(STRV_MAKE(__VA_ARGS__), _x); \
8be66a
         })
8be66a
 
8be66a
+#define STARTSWITH_SET(p, ...)                                  \
8be66a
+        ({                                                      \
8be66a
+                const char *_p = (p);                           \
8be66a
+                char  *_found = NULL, **_i;                     \
8be66a
+                STRV_FOREACH(_i, STRV_MAKE(__VA_ARGS__)) {      \
8be66a
+                        _found = startswith(_p, *_i);           \
8be66a
+                        if (_found)                             \
8be66a
+                                break;                          \
8be66a
+                }                                               \
8be66a
+                _found;                                         \
8be66a
+        })
8be66a
+
8be66a
 #define FOREACH_STRING(x, ...)                               \
8be66a
         for (char **_l = ({                                  \
8be66a
                 char **_ll = STRV_MAKE(__VA_ARGS__);         \
8be66a
diff --git a/src/test/test-strv.c b/src/test/test-strv.c
8be66a
index 1c192239a2..79d999d3ed 100644
8be66a
--- a/src/test/test-strv.c
8be66a
+++ b/src/test/test-strv.c
8be66a
@@ -56,6 +56,20 @@ static void test_strptr_in_set(void) {
8be66a
         assert_se(!STRPTR_IN_SET(NULL, NULL));
8be66a
 }
8be66a
 
8be66a
+static void test_startswith_set(void) {
8be66a
+        assert_se(!STARTSWITH_SET("foo", "bar", "baz", "waldo"));
8be66a
+        assert_se(!STARTSWITH_SET("foo", "bar"));
8be66a
+
8be66a
+        assert_se(STARTSWITH_SET("abc", "a", "ab", "abc"));
8be66a
+        assert_se(STARTSWITH_SET("abc", "ax", "ab", "abc"));
8be66a
+        assert_se(STARTSWITH_SET("abc", "ax", "abx", "abc"));
8be66a
+        assert_se(!STARTSWITH_SET("abc", "ax", "abx", "abcx"));
8be66a
+
8be66a
+        assert_se(streq_ptr(STARTSWITH_SET("foobar", "hhh", "kkk", "foo", "zzz"), "bar"));
8be66a
+        assert_se(streq_ptr(STARTSWITH_SET("foobar", "hhh", "kkk", "", "zzz"), "foobar"));
8be66a
+        assert_se(streq_ptr(STARTSWITH_SET("", "hhh", "kkk", "zzz", ""), ""));
8be66a
+}
8be66a
+
8be66a
 static const char* const input_table_multiple[] = {
8be66a
         "one",
8be66a
         "two",
8be66a
@@ -700,6 +714,7 @@ int main(int argc, char *argv[]) {
8be66a
         test_specifier_printf();
8be66a
         test_str_in_set();
8be66a
         test_strptr_in_set();
8be66a
+        test_startswith_set();
8be66a
         test_strv_foreach();
8be66a
         test_strv_foreach_backwards();
8be66a
         test_strv_foreach_pair();