X-Git-Url: https://git.distorted.org.uk/~mdw/tripe/blobdiff_plain/24898e7eadbac98ac25abbecdb813ceacabefa76..18969e42a11e11ef8a3ea81eaf0038e8e74e004d:/server/peer.c diff --git a/server/peer.c b/server/peer.c index 278a6b2a..0b5a6c22 100644 --- a/server/peer.c +++ b/server/peer.c @@ -430,7 +430,7 @@ static void p_read(int fd, unsigned mode, void *v) if (!p) goto unexp; p_rxupdstats(p, n); buf_put(p_txstart(p, MSG_MISC | MISC_PONG), BCUR(&b), BLEFT(&b)); - p_txend(p); + p_txend(p, 0); break; case MISC_PONG: if (!p) goto unexp; @@ -445,7 +445,7 @@ static void p_read(int fd, unsigned mode, void *v) buf_flip(&bb); p_encrypt(p, MSG_MISC | MISC_EPONG, &bb, p_txstart(p, MSG_MISC | MISC_EPONG)); - p_txend(p); + p_txend(p, 0); } break; case MISC_EPONG: @@ -533,6 +533,7 @@ int p_txaddr(const addr *a, const void *p, size_t sz) /* --- @p_txend@ --- * * * Arguments: @peer *p@ = pointer to peer block + * @unsigned f@ = flags * * Returns: --- * @@ -562,11 +563,13 @@ static int p_dotxend(peer *p) } } -void p_txend(peer *p) +void p_txend(peer *p, unsigned f) { - if (p_dotxend(p) && p->spec.t_ka) { - sel_rmtimer(&p->tka); - p_setkatimer(p); + if (p_dotxend(p)) { + if (p->spec.t_ka) { + sel_rmtimer(&p->tka); + p_setkatimer(p); + } } } @@ -656,7 +659,7 @@ int p_pingsend(peer *p, ping *pg, unsigned type, pg->msg = MISC_PONG; b = p_txstart(p, MSG_MISC | MISC_PING); p_pingwrite(pg, b); - p_txend(p); + p_txend(p, 0); break; case MISC_EPING: pg->msg = MISC_EPONG; @@ -667,7 +670,7 @@ int p_pingsend(peer *p, ping *pg, unsigned type, p_encrypt(p, MSG_MISC | MISC_EPING, &bb, b); if (!BOK(b)) return (-1); - p_txend(p); + p_txend(p, 0); break; default: abort(); @@ -704,7 +707,7 @@ void p_greet(peer *p, const void *c, size_t sz) { buf *b = p_txstart(p, MSG_MISC | MISC_GREET); buf_put(b, c, sz); - p_txend(p); + p_txend(p, 0); } /* --- @p_tun@ --- * @@ -726,7 +729,7 @@ void p_tun(peer *p, buf *b) if (BOK(bb) && BLEN(bb)) { p->st.n_ipout++; p->st.sz_ipout += BLEN(bb); - p_txend(p); + p_txend(p, 0); } } @@ -809,14 +812,14 @@ const addr *p_addr(peer *p) { return (&p->spec.sa); } * * Arguments: @struct addrinfo *ailist@ = addresses to bind to * - * Returns: --- + * Returns: Zero on success, @-1@ on failure. * - * Use: Initializes the peer system; creates the socket. + * Use: Binds to the main UDP sockets. */ -void p_bind(struct addrinfo *ailist) +int p_bind(struct addrinfo *ailist) { - int fd; + int fd = -1; int len = PKBUFSZ; int yes = 1; int i; @@ -842,13 +845,13 @@ void p_bind(struct addrinfo *ailist) if ((fd = socket(ai->ai_family, SOCK_DGRAM, 0)) < 0) { a_warn("PEER", "-", "udp-socket", "%s", aftab[i].name, "create-failed", "?ERRNO", A_END); - exit(EXIT_FAILURE); + goto fail; } if (i == AFIX_INET6 && setsockopt(fd, IPPROTO_IPV6, IPV6_V6ONLY, &yes, sizeof(yes))) { a_warn("PEER", "-", "udp-socket", "%s", aftab[i].name, "set-v6only-failed", "?ERRNO", A_END); - exit(EXIT_FAILURE); + goto fail; } assert(ai->ai_addrlen <= sizeof(a)); memcpy(&a, ai->ai_addr, ai->ai_addrlen); @@ -856,13 +859,13 @@ void p_bind(struct addrinfo *ailist) if (bind(fd, &a.sa, addrsz(&a))) { a_warn("PEER", "-", "udp-socket", "%s", aftab[i].name, "bind-failed", "?ERRNO", A_END); - exit(EXIT_FAILURE); + goto fail; } if (setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &len, sizeof(len)) || setsockopt(fd, SOL_SOCKET, SO_SNDBUF, &len, sizeof(len))) { a_warn("PEER", "-", "udp-socket", "%s", aftab[i].name, "set-buffers-failed", "?ERRNO", A_END); - exit(EXIT_FAILURE); + goto fail; } fdflags(fd, O_NONBLOCK, O_NONBLOCK, FD_CLOEXEC, FD_CLOEXEC); if (port) @@ -872,15 +875,22 @@ void p_bind(struct addrinfo *ailist) if (getsockname(fd, &a.sa, &sz)) { a_warn("PEER", "-", "udp-socket", "%s", aftab[i].name, "read-local-address-failed", "?ERRNO", A_END); - exit(EXIT_FAILURE); + goto fail; } udpsock[i].port = lastport = getport(&a); } T( trace(T_PEER, "peer: created %s socket", aftab[i].name); ) sel_initfile(&sel, &udpsock[i].sf, fd, SEL_READ, p_read, 0); sel_addfile(&udpsock[i].sf); + fd = -1; } + return (0); + +fail: + if (fd != -1) close(fd); + p_unbind(); + return (-1); } /* --- @p_unbind@ --- * @@ -928,28 +938,29 @@ void p_init(void) * * Arguments: @const tunnel_ops *tops@ = tunnel ops to add * - * Returns: --- + * Returns: Zero on success, @-1@ on failure. * - * Use: Adds a tunnel class to the list of known classes. If there - * is no current default tunnel, then this one is made the - * default. + * Use: Adds a tunnel class to the list of known classes, if it + * initializes properly. If there is no current default tunnel, + * then this one is made the default. * * Does nothing if the tunnel class is already known. So adding * a bunch of tunnels takes quadratic time, but there will be * too few to care about. */ -void p_addtun(const tunnel_ops *tops) +int p_addtun(const tunnel_ops *tops) { struct tunnel_node *tn; for (tn = tunnels; tn; tn = tn->next) - if (tn->tops == tops) return; - tops->init(); + if (tn->tops == tops) return (0); + if (tops->init()) return (-1); tn = CREATE(struct tunnel_node); tn->next = 0; tn->tops = tops; *tunnels_tail = tn; tunnels_tail = &tn->next; if (!dflttun) dflttun = tops; + return (0); } /* --- @p_setdflttun@ --- * @@ -1229,12 +1240,12 @@ void p_destroy(peer *p, int bye) T( trace(T_PEER, "peer: destroying peer `%s'", p->spec.name); ) - if (bye && (p->spec.f&PSF_EPHEM)) { + if (bye) { b = p_txstart(p, MSG_MISC | MISC_BYE); buf_init(&bb, buf_t, sizeof(buf_t)); assert(BOK(&bb)); buf_flip(&bb); p_encrypt(p, MSG_MISC | MISC_BYE, &bb, b); - p_txend(p); + p_txend(p, 0); } a_notify("KILL", "%s", p->spec.name, A_END);