uapi: add version magic
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
This commit is contained in:
parent
a8803c17a7
commit
6d20c647d0
|
@ -465,7 +465,7 @@ bool config_read_cmd(struct wgdevice **device, char *argv[], int argc)
|
||||||
{
|
{
|
||||||
struct inflatable_device buf = { 0 };
|
struct inflatable_device buf = { 0 };
|
||||||
size_t peer_offset = 0;
|
size_t peer_offset = 0;
|
||||||
buf.dev = calloc(sizeof(struct wgdevice), 1);
|
buf.dev = calloc(1, sizeof(struct wgdevice));
|
||||||
if (!buf.dev) {
|
if (!buf.dev) {
|
||||||
perror("calloc");
|
perror("calloc");
|
||||||
return false;
|
return false;
|
||||||
|
|
33
src/ipc.c
33
src/ipc.c
|
@ -42,6 +42,15 @@ struct inflatable_buffer {
|
||||||
|
|
||||||
#define max(a, b) ((a) > (b) ? (a) : (b))
|
#define max(a, b) ((a) > (b) ? (a) : (b))
|
||||||
|
|
||||||
|
static int check_version_magic(struct wgdevice *device, int ret)
|
||||||
|
{
|
||||||
|
if (ret == -EPROTO || (!ret && device->version_magic != WG_API_VERSION_MAGIC)) {
|
||||||
|
fprintf(stderr, "This program was built for a different version of WireGuard than\nwhat is currently running. Either this version of wg(8) is out\nof date, or the currently loaded WireGuard module is out of date.\nIf you have just updated your WireGuard installation, you may have\nforgotten to unload the previous running WireGuard module. Try\nrunning `rmmod wireguard` as root, and then try re-adding the device\nand trying again.\n\n");
|
||||||
|
return -EPROTO;
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
static int add_next_to_inflatable_buffer(struct inflatable_buffer *buffer)
|
static int add_next_to_inflatable_buffer(struct inflatable_buffer *buffer)
|
||||||
{
|
{
|
||||||
size_t len, expand_to;
|
size_t len, expand_to;
|
||||||
|
@ -172,6 +181,7 @@ static int userspace_set_device(struct wgdevice *dev)
|
||||||
ret = -EBADMSG;
|
ret = -EBADMSG;
|
||||||
if (!len)
|
if (!len)
|
||||||
goto out;
|
goto out;
|
||||||
|
dev->version_magic = WG_API_VERSION_MAGIC;
|
||||||
ret = write(fd, dev, len);
|
ret = write(fd, dev, len);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -243,6 +253,9 @@ static int userspace_get_device(struct wgdevice **dev, const char *interface)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
len = ((struct wgdevice *)READ_BYTES(sizeof(struct wgdevice)))->num_peers;
|
len = ((struct wgdevice *)READ_BYTES(sizeof(struct wgdevice)))->num_peers;
|
||||||
|
ret = check_version_magic((struct wgdevice *)buffer, ret);
|
||||||
|
if (ret)
|
||||||
|
goto out;
|
||||||
for (i = 0; i < len; ++i)
|
for (i = 0; i < len; ++i)
|
||||||
READ_BYTES(sizeof(struct wgipmask) * ((struct wgpeer *)READ_BYTES(sizeof(struct wgpeer)))->num_ipmasks);
|
READ_BYTES(sizeof(struct wgipmask) * ((struct wgpeer *)READ_BYTES(sizeof(struct wgpeer)))->num_ipmasks);
|
||||||
ret = 0;
|
ret = 0;
|
||||||
|
@ -361,7 +374,7 @@ static bool kernel_has_wireguard_interface(const char *interface)
|
||||||
char *this_interface;
|
char *this_interface;
|
||||||
struct inflatable_buffer buffer = { .len = 4096 };
|
struct inflatable_buffer buffer = { .len = 4096 };
|
||||||
|
|
||||||
buffer.buffer = calloc(buffer.len, 1);
|
buffer.buffer = calloc(1, buffer.len);
|
||||||
if (!buffer.buffer)
|
if (!buffer.buffer)
|
||||||
return false;
|
return false;
|
||||||
if (kernel_get_wireguard_interfaces(&buffer) < 0) {
|
if (kernel_get_wireguard_interfaces(&buffer) < 0) {
|
||||||
|
@ -382,12 +395,16 @@ static bool kernel_has_wireguard_interface(const char *interface)
|
||||||
static int do_ioctl(int req, struct ifreq *ifreq)
|
static int do_ioctl(int req, struct ifreq *ifreq)
|
||||||
{
|
{
|
||||||
static int fd = -1;
|
static int fd = -1;
|
||||||
|
int ret;
|
||||||
if (fd < 0) {
|
if (fd < 0) {
|
||||||
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
||||||
if (fd < 0)
|
if (fd < 0)
|
||||||
return fd;
|
return fd;
|
||||||
}
|
}
|
||||||
return ioctl(fd, req, ifreq);
|
ret = ioctl(fd, req, ifreq);
|
||||||
|
if (ret == -1)
|
||||||
|
ret = -errno;
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int kernel_set_device(struct wgdevice *dev)
|
static int kernel_set_device(struct wgdevice *dev)
|
||||||
|
@ -395,6 +412,7 @@ static int kernel_set_device(struct wgdevice *dev)
|
||||||
struct ifreq ifreq = { .ifr_data = (char *)dev };
|
struct ifreq ifreq = { .ifr_data = (char *)dev };
|
||||||
memcpy(&ifreq.ifr_name, dev->interface, IFNAMSIZ);
|
memcpy(&ifreq.ifr_name, dev->interface, IFNAMSIZ);
|
||||||
ifreq.ifr_name[IFNAMSIZ - 1] = 0;
|
ifreq.ifr_name[IFNAMSIZ - 1] = 0;
|
||||||
|
dev->version_magic = WG_API_VERSION_MAGIC;
|
||||||
return do_ioctl(WG_SET_DEVICE, &ifreq);
|
return do_ioctl(WG_SET_DEVICE, &ifreq);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -410,17 +428,18 @@ static int kernel_get_device(struct wgdevice **dev, const char *interface)
|
||||||
ret = do_ioctl(WG_GET_DEVICE, &ifreq);
|
ret = do_ioctl(WG_GET_DEVICE, &ifreq);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto out;
|
goto out;
|
||||||
*dev = calloc(ret + sizeof(struct wgdevice), 1);
|
*dev = calloc(1, ret + sizeof(struct wgdevice));
|
||||||
if (!*dev) {
|
ret = -ENOMEM;
|
||||||
ret = -ENOMEM;
|
if (!*dev)
|
||||||
goto out;
|
goto out;
|
||||||
}
|
|
||||||
(*dev)->peers_size = ret;
|
(*dev)->peers_size = ret;
|
||||||
|
(*dev)->version_magic = WG_API_VERSION_MAGIC;
|
||||||
ifreq.ifr_data = (char *)*dev;
|
ifreq.ifr_data = (char *)*dev;
|
||||||
memcpy(&ifreq.ifr_name, interface, IFNAMSIZ);
|
memcpy(&ifreq.ifr_name, interface, IFNAMSIZ);
|
||||||
ifreq.ifr_name[IFNAMSIZ - 1] = 0;
|
ifreq.ifr_name[IFNAMSIZ - 1] = 0;
|
||||||
ret = do_ioctl(WG_GET_DEVICE, &ifreq);
|
ret = do_ioctl(WG_GET_DEVICE, &ifreq);
|
||||||
} while (ret == -EMSGSIZE);
|
} while (ret == -EMSGSIZE);
|
||||||
|
ret = check_version_magic(*dev, ret);
|
||||||
if (ret < 0) {
|
if (ret < 0) {
|
||||||
free(*dev);
|
free(*dev);
|
||||||
*dev = NULL;
|
*dev = NULL;
|
||||||
|
@ -438,7 +457,7 @@ char *ipc_list_devices(void)
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
ret = -ENOMEM;
|
ret = -ENOMEM;
|
||||||
buffer.buffer = calloc(buffer.len, 1);
|
buffer.buffer = calloc(1, buffer.len);
|
||||||
if (!buffer.buffer)
|
if (!buffer.buffer)
|
||||||
goto cleanup;
|
goto cleanup;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue