io-util: split out "struct iovec" related calls into their own .c/.h files
This is preparation for #28891, which adds a bunch more helpers around "struct iovec", at which point this really deserves its own .c/.h file. The idea is that we sooner or later can consider "struct iovec" as an entirely generic mechanism to reference some binary blob, and is the go-to type for this purpose whenever we need one.
This commit is contained in:
@@ -10,7 +10,7 @@
|
||||
#include "audit-util.h"
|
||||
#include "fd-util.h"
|
||||
#include "fileio.h"
|
||||
#include "io-util.h"
|
||||
#include "iovec-util.h"
|
||||
#include "macro.h"
|
||||
#include "parse-util.h"
|
||||
#include "process-util.h"
|
||||
|
||||
+1
-27
@@ -7,6 +7,7 @@
|
||||
|
||||
#include "errno-util.h"
|
||||
#include "io-util.h"
|
||||
#include "iovec-util.h"
|
||||
#include "string-util.h"
|
||||
#include "time-util.h"
|
||||
|
||||
@@ -305,23 +306,6 @@ ssize_t sparse_write(int fd, const void *p, size_t sz, size_t run_length) {
|
||||
return q - (const uint8_t*) p;
|
||||
}
|
||||
|
||||
char* set_iovec_string_field(struct iovec *iovec, size_t *n_iovec, const char *field, const char *value) {
|
||||
char *x;
|
||||
|
||||
x = strjoin(field, value);
|
||||
if (x)
|
||||
iovec[(*n_iovec)++] = IOVEC_MAKE_STRING(x);
|
||||
return x;
|
||||
}
|
||||
|
||||
char* set_iovec_string_field_free(struct iovec *iovec, size_t *n_iovec, const char *field, char *value) {
|
||||
char *x;
|
||||
|
||||
x = set_iovec_string_field(iovec, n_iovec, field, value);
|
||||
free(value);
|
||||
return x;
|
||||
}
|
||||
|
||||
struct iovec_wrapper *iovw_new(void) {
|
||||
return malloc0(sizeof(struct iovec_wrapper));
|
||||
}
|
||||
@@ -429,13 +413,3 @@ rollback:
|
||||
target->count = original_count;
|
||||
return r;
|
||||
}
|
||||
|
||||
void iovec_array_free(struct iovec *iov, size_t n) {
|
||||
if (!iov)
|
||||
return;
|
||||
|
||||
for (size_t i = 0; i < n; i++)
|
||||
free(iov[i].iov_base);
|
||||
|
||||
free(iov);
|
||||
}
|
||||
|
||||
@@ -28,38 +28,6 @@ int fd_wait_for_event(int fd, int event, usec_t timeout);
|
||||
|
||||
ssize_t sparse_write(int fd, const void *p, size_t sz, size_t run_length);
|
||||
|
||||
static inline size_t IOVEC_TOTAL_SIZE(const struct iovec *i, size_t n) {
|
||||
size_t r = 0;
|
||||
|
||||
for (size_t j = 0; j < n; j++)
|
||||
r += i[j].iov_len;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static inline bool IOVEC_INCREMENT(struct iovec *i, size_t n, size_t k) {
|
||||
/* Returns true if there is nothing else to send (bytes written cover all of the iovec),
|
||||
* false if there's still work to do. */
|
||||
|
||||
for (size_t j = 0; j < n; j++) {
|
||||
size_t sub;
|
||||
|
||||
if (i[j].iov_len == 0)
|
||||
continue;
|
||||
if (k == 0)
|
||||
return false;
|
||||
|
||||
sub = MIN(i[j].iov_len, k);
|
||||
i[j].iov_len -= sub;
|
||||
i[j].iov_base = (uint8_t*) i[j].iov_base + sub;
|
||||
k -= sub;
|
||||
}
|
||||
|
||||
assert(k == 0); /* Anything else would mean that we wrote more bytes than available,
|
||||
* or the kernel reported writing more bytes than sent. */
|
||||
return true;
|
||||
}
|
||||
|
||||
static inline bool FILE_SIZE_VALID(uint64_t l) {
|
||||
/* ftruncate() and friends take an unsigned file size, but actually cannot deal with file sizes larger than
|
||||
* 2^63 since the kernel internally handles it as signed value. This call allows checking for this early. */
|
||||
@@ -78,17 +46,6 @@ static inline bool FILE_SIZE_VALID_OR_INFINITY(uint64_t l) {
|
||||
|
||||
}
|
||||
|
||||
#define IOVEC_NULL (struct iovec) {}
|
||||
#define IOVEC_MAKE(base, len) (struct iovec) { .iov_base = (base), .iov_len = (len) }
|
||||
#define IOVEC_MAKE_STRING(string) \
|
||||
({ \
|
||||
char *_s = (char*) (string); \
|
||||
IOVEC_MAKE(_s, strlen(_s)); \
|
||||
})
|
||||
|
||||
char* set_iovec_string_field(struct iovec *iovec, size_t *n_iovec, const char *field, const char *value);
|
||||
char* set_iovec_string_field_free(struct iovec *iovec, size_t *n_iovec, const char *field, char *value);
|
||||
|
||||
struct iovec_wrapper {
|
||||
struct iovec *iovec;
|
||||
size_t count;
|
||||
@@ -123,5 +80,3 @@ int iovw_put_string_field_free(struct iovec_wrapper *iovw, const char *field, ch
|
||||
void iovw_rebase(struct iovec_wrapper *iovw, char *old, char *new);
|
||||
size_t iovw_size(struct iovec_wrapper *iovw);
|
||||
int iovw_append(struct iovec_wrapper *target, const struct iovec_wrapper *source);
|
||||
|
||||
void iovec_array_free(struct iovec *iov, size_t n);
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
||||
|
||||
#include "iovec-util.h"
|
||||
#include "string-util.h"
|
||||
|
||||
|
||||
char* set_iovec_string_field(struct iovec *iovec, size_t *n_iovec, const char *field, const char *value) {
|
||||
char *x;
|
||||
|
||||
assert(iovec);
|
||||
assert(n_iovec);
|
||||
|
||||
x = strjoin(field, value);
|
||||
if (x)
|
||||
iovec[(*n_iovec)++] = IOVEC_MAKE_STRING(x);
|
||||
return x;
|
||||
}
|
||||
|
||||
char* set_iovec_string_field_free(struct iovec *iovec, size_t *n_iovec, const char *field, char *value) {
|
||||
char *x;
|
||||
|
||||
assert(iovec);
|
||||
assert(n_iovec);
|
||||
|
||||
x = set_iovec_string_field(iovec, n_iovec, field, value);
|
||||
free(value);
|
||||
return x;
|
||||
}
|
||||
|
||||
void iovec_array_free(struct iovec *iov, size_t n) {
|
||||
if (!iov)
|
||||
return;
|
||||
|
||||
for (size_t i = 0; i < n; i++)
|
||||
free(iov[i].iov_base);
|
||||
|
||||
free(iov);
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
||||
#pragma once
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/uio.h>
|
||||
|
||||
#include "macro.h"
|
||||
|
||||
static inline size_t IOVEC_TOTAL_SIZE(const struct iovec *i, size_t n) {
|
||||
size_t r = 0;
|
||||
|
||||
for (size_t j = 0; j < n; j++)
|
||||
r += i[j].iov_len;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static inline bool IOVEC_INCREMENT(struct iovec *i, size_t n, size_t k) {
|
||||
/* Returns true if there is nothing else to send (bytes written cover all of the iovec),
|
||||
* false if there's still work to do. */
|
||||
|
||||
for (size_t j = 0; j < n; j++) {
|
||||
size_t sub;
|
||||
|
||||
if (i[j].iov_len == 0)
|
||||
continue;
|
||||
if (k == 0)
|
||||
return false;
|
||||
|
||||
sub = MIN(i[j].iov_len, k);
|
||||
i[j].iov_len -= sub;
|
||||
i[j].iov_base = (uint8_t*) i[j].iov_base + sub;
|
||||
k -= sub;
|
||||
}
|
||||
|
||||
assert(k == 0); /* Anything else would mean that we wrote more bytes than available,
|
||||
* or the kernel reported writing more bytes than sent. */
|
||||
return true;
|
||||
}
|
||||
|
||||
#define IOVEC_NULL (struct iovec) {}
|
||||
#define IOVEC_MAKE(base, len) (struct iovec) { .iov_base = (base), .iov_len = (len) }
|
||||
#define IOVEC_MAKE_STRING(string) \
|
||||
({ \
|
||||
char *_s = (char*) (string); \
|
||||
IOVEC_MAKE(_s, strlen(_s)); \
|
||||
})
|
||||
|
||||
char* set_iovec_string_field(struct iovec *iovec, size_t *n_iovec, const char *field, const char *value);
|
||||
char* set_iovec_string_field_free(struct iovec *iovec, size_t *n_iovec, const char *field, char *value);
|
||||
|
||||
void iovec_array_free(struct iovec *iov, size_t n);
|
||||
+1
-1
@@ -21,7 +21,7 @@
|
||||
#include "errno-util.h"
|
||||
#include "fd-util.h"
|
||||
#include "format-util.h"
|
||||
#include "io-util.h"
|
||||
#include "iovec-util.h"
|
||||
#include "log.h"
|
||||
#include "macro.h"
|
||||
#include "missing_syscall.h"
|
||||
|
||||
@@ -44,6 +44,7 @@ basic_sources = files(
|
||||
'initrd-util.c',
|
||||
'inotify-util.c',
|
||||
'io-util.c',
|
||||
'iovec-util.c',
|
||||
'ioprio-util.c',
|
||||
'label.c',
|
||||
'limits-util.c',
|
||||
|
||||
Reference in New Issue
Block a user