Keep track of MTU in path

This commit is contained in:
Adrien Gallouët
2016-12-21 16:04:34 +00:00
parent b5a5cb2f1f
commit fe5499d46d

74
mud.c
View File

@@ -85,6 +85,10 @@ struct mud_path {
struct { struct {
uint64_t send_time; uint64_t send_time;
int remote; int remote;
struct {
int remote;
int local;
} mtu;
} conf; } conf;
unsigned char *tc; unsigned char *tc;
uint64_t rdt; uint64_t rdt;
@@ -166,10 +170,7 @@ struct mud {
int use_next; int use_next;
int aes; int aes;
} crypto; } crypto;
struct { int mtu;
int remote;
int local;
} mtu;
unsigned char kiss[MUD_SID_SIZE]; unsigned char kiss[MUD_SID_SIZE];
}; };
@@ -528,19 +529,11 @@ mud_peer(struct mud *mud, const char *name, const char *host, int port,
path->state.active = 1; path->state.active = 1;
path->state.backup = !!backup; path->state.backup = !!backup;
path->conf.mtu.local = mud->mtu; // XXX
return 0; return 0;
} }
static void
mud_update_conf(struct mud *mud)
{
struct mud_path *path;
for (path = mud->path; path; path = path->next)
path->conf.remote = 0;
}
int int
mud_get_key(struct mud *mud, unsigned char *key, size_t *size) mud_get_key(struct mud *mud, unsigned char *key, size_t *size)
{ {
@@ -602,26 +595,45 @@ mud_set_time_tolerance_sec(struct mud *mud, unsigned sec)
int int
mud_get_mtu(struct mud *mud) mud_get_mtu(struct mud *mud)
{ {
if ((!mud->mtu.remote) || int mtu = mud->mtu;
(mud->mtu.local < mud->mtu.remote))
return mud->mtu.local;
return mud->mtu.remote; struct mud_path *path;
for (path = mud->path; path; path = path->next) {
if (path->conf.mtu.local && path->conf.mtu.local < mtu)
mtu = path->conf.mtu.local;
if (path->conf.mtu.remote && path->conf.mtu.remote < mtu)
mtu = path->conf.mtu.remote;
}
return mtu;
} }
int int
mud_set_mtu(struct mud *mud, int mtu) mud_set_mtu(struct mud *mud, int mtu)
{ {
if ((mtu < sizeof(struct mud_packet)) || if (mtu <= 0)
(mtu > MUD_PACKET_MAX_SIZE - 50)) { // XXX mtu = MUD_PACKET_MAX_SIZE;
errno = EINVAL;
return -1; if (mtu < sizeof(struct mud_packet))
mtu = sizeof(struct mud_packet);
if (mtu > MUD_PACKET_MAX_SIZE)
mtu = MUD_PACKET_MAX_SIZE;
mtu -= MUD_PACKET_MIN_SIZE;
struct mud_path *path;
for (path = mud->path; path; path = path->next) {
if (path->conf.mtu.local == mtu)
continue;
path->conf.mtu.local = mtu;
path->conf.remote = 0;
} }
if (mud->mtu.local != mtu) { if (!mud->mtu)
mud->mtu.local = mtu; mud->mtu = mtu;
mud_update_conf(mud);
}
return 0; return 0;
} }
@@ -696,7 +708,6 @@ mud_create(int port, int v4, int v6, int aes, int mtu)
mud->send_timeout = MUD_SEND_TIMEOUT; mud->send_timeout = MUD_SEND_TIMEOUT;
mud->time_tolerance = MUD_TIME_TOLERANCE; mud->time_tolerance = MUD_TIME_TOLERANCE;
mud->mtu.local = mtu;
unsigned char key[MUD_KEY_SIZE]; unsigned char key[MUD_KEY_SIZE];
@@ -708,6 +719,8 @@ mud_create(int port, int v4, int v6, int aes, int mtu)
randombytes_buf(mud->kiss, sizeof(mud->kiss)); randombytes_buf(mud->kiss, sizeof(mud->kiss));
mud_set_mtu(mud, mtu);
return mud; return mud;
} }
@@ -865,7 +878,7 @@ mud_packet_send(struct mud *mud, enum mud_packet_code code,
case mud_conf: case mud_conf:
size = sizeof(packet.data.conf); size = sizeof(packet.data.conf);
memcpy(&packet.data.conf.kiss, &mud->kiss, size); memcpy(&packet.data.conf.kiss, &mud->kiss, size);
mud_write48(packet.data.conf.mtu, mud->mtu.local); mud_write48(packet.data.conf.mtu, path->conf.mtu.local);
packet.data.conf.backup = (unsigned char)path->state.backup; packet.data.conf.backup = (unsigned char)path->state.backup;
break; break;
case mud_stat: case mud_stat:
@@ -976,11 +989,14 @@ mud_packet_check_size(unsigned char *data, size_t size)
return -1; return -1;
// clang-format off // clang-format off
const size_t sizes[] = { const size_t sizes[] = {
[mud_conf] = MUD_PACKET_SIZE(sizeof(packet->data.conf)), [mud_conf] = MUD_PACKET_SIZE(sizeof(packet->data.conf)),
[mud_stat] = MUD_PACKET_SIZE(sizeof(packet->data.stat)), [mud_stat] = MUD_PACKET_SIZE(sizeof(packet->data.stat)),
[mud_keyx] = MUD_PACKET_SIZE(sizeof(packet->data.public)), [mud_keyx] = MUD_PACKET_SIZE(sizeof(packet->data.public)),
}; // clang-format on };
// clang-format on
return (packet->hdr.code >= sizeof(sizes)) || return (packet->hdr.code >= sizeof(sizes)) ||
(sizes[packet->hdr.code] != size); (sizes[packet->hdr.code] != size);
@@ -1013,7 +1029,7 @@ mud_packet_recv(struct mud *mud, struct mud_path *path,
switch (packet->hdr.code) { switch (packet->hdr.code) {
case mud_conf: case mud_conf:
mud->mtu.remote = mud_read48(packet->data.conf.mtu); path->conf.mtu.remote = mud_read48(packet->data.conf.mtu);
path->conf.remote = !memcmp(mud->kiss, packet->data.conf.kiss, path->conf.remote = !memcmp(mud->kiss, packet->data.conf.kiss,
sizeof(mud->kiss)); sizeof(mud->kiss));
if (path->state.active) if (path->state.active)