On Tue, Mar 22, 2022 at 8:27 PM Miklos Szeredi <mszeredi@xxxxxxxxxx> wrote: > > Add a new userspace API that allows getting multiple short values in a > single syscall. Attaching a test program that allows arbitrary queries. Thanks, Miklos
#include <unistd.h> #include <string.h> #include <stdio.h> #include <fcntl.h> #include <err.h> #include <stdint.h> #include <sys/uio.h> struct name_val { const char *name; /* in */ struct iovec value_in; /* in */ struct iovec value_out; /* out */ uint32_t error; /* out */ uint32_t reserved; }; int getvalues(int dfd, const char *path, struct name_val *vec, size_t num, unsigned int flags) { return syscall(451, dfd, path, vec, num, flags); } int main(int argc, char *argv[]) { char *s, buf[4096]; int res, i, o, num = argc - 2; struct name_val nvs[256] = {}; if (argc < 3) errx(1, "usage: %s path name [...]", argv[0]); if (num > 256) errx(1, "too many arguments"); for (i = 0; i < num; i++) nvs[i].name = argv[i + 2]; nvs[0].value_in.iov_base = buf; nvs[0].value_in.iov_len = sizeof(buf); res = getvalues(AT_FDCWD, argv[1], nvs, num, 0); if (res == -1) err(1, NULL); num = res; for (i = 0; i < num; i++) { printf("[%s] = ", nvs[i].name); res = nvs[i].error; if (res) { printf(" ERROR: %s (%i)\n", strerror(res), res); } else { res = nvs[i].value_out.iov_len; s = nvs[i].value_out.iov_base; for (o = 0; o < res; o += strlen(s + o) + 1) printf("\"%.*s\" ", res - o, s + o); printf("(len=%i)\n", res); } } return 0; }