]> git.ozlabs.org Git - ccan/blobdiff - ccan/bytestring/bytestring.h
coroutine: Remove on-stack buffers from testcases
[ccan] / ccan / bytestring / bytestring.h
index 5a8d3cd896fb003704bada0f535d4e11c5354171..bc99e7951c739e94221148e12491ea994642fbae 100644 (file)
@@ -11,6 +11,7 @@
 
 #include <ccan/array_size/array_size.h>
 #include <ccan/mem/mem.h>
+#include <ccan/compiler/compiler.h>
 
 struct bytestring {
        const char *ptr;
@@ -29,7 +30,8 @@ struct bytestring {
  *     struct bytestring bs = bytestring(x, 5);
  *     assert(bs.len == 5);
  */
-static inline struct bytestring bytestring(const char *p, size_t l)
+static inline CONST_FUNCTION struct bytestring
+bytestring(const char *p, size_t l)
 {
        struct bytestring bs = {
                .ptr = p,
@@ -53,6 +55,18 @@ static inline struct bytestring bytestring(const char *p, size_t l)
  */
 #define BYTESTRING(s) (bytestring((s), ARRAY_SIZE(s) - 1))
 
+/**
+ * BYTESTRING_INIT - bytestring initializer
+ * @s: string literal
+ *
+ * Produces an initializer for a bytestring from a literal string.
+ * The resulting bytestring will not include the terminating \0, but
+ * will include any internal \0s.
+ *
+ * Example:
+ *     static const struct bytestring CONSTANT = BYTESTRING_INIT("CONSTANT");
+ */
+#define BYTESTRING_INIT(s) { .ptr = (s), .len = ARRAY_SIZE(s) - 1}
 
 /**
  * bytestring_from_string - construct a bytestring from a NUL terminated string
@@ -80,8 +94,7 @@ static inline struct bytestring bytestring_from_string(const char *s)
  */
 static inline bool bytestring_eq(struct bytestring a, struct bytestring b)
 {
-       return (a.len == b.len)
-               && (memcmp(a.ptr, b.ptr, a.len) == 0);
+       return memeq(a.ptr, a.len, b.ptr, b.len);
 }
 
 /**
@@ -135,8 +148,7 @@ static inline struct bytestring bytestring_slice(struct bytestring s,
 static inline bool bytestring_starts(struct bytestring s,
                                     struct bytestring prefix)
 {
-       return (s.len >= prefix.len) && (memcmp(s.ptr,
-                                               prefix.ptr, prefix.len) == 0);
+       return memstarts(s.ptr, s.len, prefix.ptr, prefix.len);
 }
 
 /**
@@ -149,8 +161,7 @@ static inline bool bytestring_starts(struct bytestring s,
 static inline bool bytestring_ends(struct bytestring s,
                                   struct bytestring suffix)
 {
-       return (s.len >= suffix.len) && (memcmp(s.ptr + s.len - suffix.len,
-                                               suffix.ptr, suffix.len) == 0);
+       return memends(s.ptr, s.len, suffix.ptr, suffix.len);
 }
 
 /**
@@ -276,4 +287,32 @@ struct bytestring bytestring_splitchrs_next(struct bytestring whole,
             (_s).ptr;                                         \
             (_s) = bytestring_splitchrs_next((_w), (_delim), (_s)))
 
+/**
+ * bytestring_splitstr_first - split a bytestring on a delimiter string
+ * @whole: a bytestring
+ * @delim: delimiter substring
+ *
+ * Returns the first substring of @whole delimited by the substring in
+ * @delim.
+ */
+struct bytestring bytestring_splitstr_first(struct bytestring whole,
+                                            struct bytestring delim);
+
+/**
+ * bytestring_splitstr_next - split a bytestring on a delimiter string
+ * @whole: a bytestring
+ * @delim: delimiter string
+ * @prev: last substring
+ *
+ * Returns the next @delim delimited substring of @whole after @prev.
+ */
+struct bytestring bytestring_splitstr_next(struct bytestring whole,
+                                          struct bytestring delim,
+                                          struct bytestring prev);
+
+#define bytestring_foreach_splitstr(_s, _w, _delim) \
+       for ((_s) = bytestring_splitstr_first((_w), (_delim)); \
+            (_s).ptr;                                         \
+            (_s) = bytestring_splitstr_next((_w), (_delim), (_s)))
+
 #endif /* CCAN_BYTESTRING_H_ */