]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
include/strutils: add strdup_between_structs()
authorKarel Zak <kzak@redhat.com>
Wed, 23 Oct 2019 10:28:09 +0000 (12:28 +0200)
committerKarel Zak <kzak@redhat.com>
Thu, 31 Oct 2019 11:25:08 +0000 (12:25 +0100)
* improve strdup_to_offset() readability

* add strdup_between_offsets() and strdup_between_structs() to have
  better support for use-cases when we copy structs

Signed-off-by: Karel Zak <kzak@redhat.com>
include/strutils.h

index 963e3d6f4c3a1cf6605c0e2fd028b4daab35a4db..fc3bb0c1c79e8cddfc78417dc5bc88a80b44669e 100644 (file)
@@ -124,29 +124,61 @@ nothing:
        return NULL;
 }
 
+/* Copy string @str to struct @stru to member addressed by @offset */
 static inline int strdup_to_offset(void *stru, size_t offset, const char *str)
 {
-       char *n = NULL;
        char **o;
+       char *p = NULL;
 
        if (!stru)
                return -EINVAL;
 
        o = (char **) ((char *) stru + offset);
        if (str) {
-               n = strdup(str);
-               if (!n)
+               p = strdup(str);
+               if (!p)
                        return -ENOMEM;
        }
 
        free(*o);
-       *o = n;
+       *o = p;
        return 0;
 }
 
+/* Copy string __str to struct member _m of the struct _s */
 #define strdup_to_struct_member(_s, _m, _str) \
                strdup_to_offset((void *) _s, offsetof(__typeof__(*(_s)), _m), _str)
 
+/* Copy string addressed by @offset between two structs */
+static inline int strdup_between_offsets(void *stru_dst, void *stru_src, size_t offset)
+{
+       char **src;
+       char **dst;
+       char *p = NULL;
+
+       if (!stru_src || !stru_dst)
+               return -EINVAL;
+
+       src = (char **) ((char *) stru_src + offset);
+       dst = (char **) ((char *) stru_dst + offset);
+
+       if (*src) {
+               p = strdup(*src);
+               if (!p)
+                       return -ENOMEM;
+       }
+
+       free(*dst);
+       *dst = p;
+       return 0;
+}
+
+/* Copy string addressed by struct member between two instances of the same
+ * struct type */
+#define strdup_between_structs(_dst, _src, _m) \
+               strdup_between_offsets((void *)_dst, (void *)_src, offsetof(__typeof__(*(_src)), _m))
+
+
 extern char *xstrmode(mode_t mode, char *str);
 
 /* Options for size_to_human_string() */