basic/iovec-wrapper: add iovw_append and iovw_to_cstring
Existing iovw_append is renamed to iovw_append_iovw. iovw_consume is made noninline.
This commit is contained in:
@@ -41,6 +41,28 @@ int iovw_put(struct iovec_wrapper *iovw, void *data, size_t len) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int iovw_append(struct iovec_wrapper *iovw, const void *data, size_t len) {
|
||||
if (len == 0)
|
||||
return 0;
|
||||
|
||||
void *c = memdup(data, len);
|
||||
if (!c)
|
||||
return -ENOMEM;
|
||||
|
||||
return iovw_put(iovw, c, len);
|
||||
}
|
||||
|
||||
int iovw_consume(struct iovec_wrapper *iovw, void *data, size_t len) {
|
||||
/* Move data into iovw or free on error */
|
||||
int r;
|
||||
|
||||
r = iovw_put(iovw, data, len);
|
||||
if (r < 0)
|
||||
free(data);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
int iovw_put_string_field_full(struct iovec_wrapper *iovw, bool replace, const char *field, const char *value) {
|
||||
_cleanup_free_ char *x = NULL;
|
||||
int r;
|
||||
@@ -103,7 +125,7 @@ size_t iovw_size(const struct iovec_wrapper *iovw) {
|
||||
return iovec_total_size(iovw->iovec, iovw->count);
|
||||
}
|
||||
|
||||
int iovw_append(struct iovec_wrapper *target, const struct iovec_wrapper *source) {
|
||||
int iovw_append_iovw(struct iovec_wrapper *target, const struct iovec_wrapper *source) {
|
||||
size_t original_count;
|
||||
int r;
|
||||
|
||||
@@ -139,3 +161,32 @@ rollback:
|
||||
target->count = original_count;
|
||||
return r;
|
||||
}
|
||||
|
||||
char* iovw_to_cstring(const struct iovec_wrapper *iovw) {
|
||||
size_t size;
|
||||
char *p, *ans;
|
||||
|
||||
assert(iovw);
|
||||
|
||||
/* Squish a series of iovecs into a C string. Embedded NULs are not allowed.
|
||||
* The caller is expected to filter them out when populating the data. */
|
||||
|
||||
size = iovw_size(iovw);
|
||||
if (size == SIZE_MAX)
|
||||
return NULL; /* Prevent theoretical overflow */
|
||||
size ++;
|
||||
|
||||
p = ans = new(char, size);
|
||||
if (!ans)
|
||||
return NULL;
|
||||
|
||||
FOREACH_ARRAY(iovec, iovw->iovec, iovw->count) {
|
||||
assert(!memchr(iovec->iov_base, 0, iovec->iov_len));
|
||||
|
||||
p = mempcpy(p, iovec->iov_base, iovec->iov_len);
|
||||
}
|
||||
|
||||
*p = '\0';
|
||||
|
||||
return ans;
|
||||
}
|
||||
|
||||
@@ -12,16 +12,8 @@ void iovw_done_free(struct iovec_wrapper *iovw);
|
||||
void iovw_done(struct iovec_wrapper *iovw);
|
||||
|
||||
int iovw_put(struct iovec_wrapper *iovw, void *data, size_t len);
|
||||
static inline int iovw_consume(struct iovec_wrapper *iovw, void *data, size_t len) {
|
||||
/* Move data into iovw or free on error */
|
||||
int r;
|
||||
|
||||
r = iovw_put(iovw, data, len);
|
||||
if (r < 0)
|
||||
free(data);
|
||||
|
||||
return r;
|
||||
}
|
||||
int iovw_append(struct iovec_wrapper *iovw, const void *data, size_t len);
|
||||
int iovw_consume(struct iovec_wrapper *iovw, void *data, size_t len);
|
||||
|
||||
static inline bool iovw_isempty(const struct iovec_wrapper *iovw) {
|
||||
return !iovw || iovw->count == 0;
|
||||
@@ -40,4 +32,5 @@ int iovw_put_string_fieldf_full(struct iovec_wrapper *iovw, bool replace, const
|
||||
int iovw_put_string_field_free(struct iovec_wrapper *iovw, const char *field, char *value);
|
||||
void iovw_rebase(struct iovec_wrapper *iovw, void *old, void *new);
|
||||
size_t iovw_size(const struct iovec_wrapper *iovw);
|
||||
int iovw_append(struct iovec_wrapper *target, const struct iovec_wrapper *source);
|
||||
int iovw_append_iovw(struct iovec_wrapper *target, const struct iovec_wrapper *source);
|
||||
char* iovw_to_cstring(const struct iovec_wrapper *iovw);
|
||||
|
||||
Reference in New Issue
Block a user