From: bluhm Date: Tue, 11 Sep 2018 14:34:49 +0000 (+0000) Subject: Make the distribution of in_ and in6_ functions in in_pcb.c and X-Git-Url: http://artulab.com/gitweb/?a=commitdiff_plain;h=531c7ccd3c4946c34f25052adb2564797694e801;p=openbsd Make the distribution of in_ and in6_ functions in in_pcb.c and in6_pcb.c consistent, to ease comparing the code. Move all inet6 functions to in6_. Bring functions in both source files in same order. Cleanup the include section. Now in_pcb.c is a superset of in6_pcb.c. The latter contains all the special implementations. Just moving arround, no code change intended. OK mpi@ --- diff --git a/sys/netinet/in_pcb.c b/sys/netinet/in_pcb.c index 29b4227f809..614d15fa769 100644 --- a/sys/netinet/in_pcb.c +++ b/sys/netinet/in_pcb.c @@ -1,4 +1,4 @@ -/* $OpenBSD: in_pcb.c,v 1.242 2018/09/10 22:21:39 bluhm Exp $ */ +/* $OpenBSD: in_pcb.c,v 1.243 2018/09/11 14:34:49 bluhm Exp $ */ /* $NetBSD: in_pcb.c,v 1.25 1996/02/13 23:41:53 christos Exp $ */ /* @@ -76,30 +76,21 @@ #include #include #include -#include -#include #include +#include #include +#include #include #include +#include #include #include -#include -#include #include +#include #include - -#include - -#include -#include - -#ifdef INET6 -#include -#include -#endif /* INET6 */ +#include #ifdef IPSEC #include #endif /* IPSEC */ @@ -131,8 +122,6 @@ int in_pcbresize (struct inpcbtable *, int); struct inpcbhead *in_pcbhash(struct inpcbtable *, int, const struct in_addr *, u_short, const struct in_addr *, u_short); -struct inpcbhead *in6_pcbhash(struct inpcbtable *, int, - const struct in6_addr *, u_short, const struct in6_addr *, u_short); struct inpcbhead *in_pcblhash(struct inpcbtable *, int, u_short); struct inpcbhead * @@ -153,24 +142,6 @@ in_pcbhash(struct inpcbtable *table, int rdom, return (&table->inpt_hashtbl[SipHash24_End(&ctx) & table->inpt_mask]); } -struct inpcbhead * -in6_pcbhash(struct inpcbtable *table, int rdom, - const struct in6_addr *faddr, u_short fport, - const struct in6_addr *laddr, u_short lport) -{ - SIPHASH_CTX ctx; - u_int32_t nrdom = htonl(rdom); - - SipHash24_Init(&ctx, &table->inpt_key); - SipHash24_Update(&ctx, &nrdom, sizeof(nrdom)); - SipHash24_Update(&ctx, faddr, sizeof(*faddr)); - SipHash24_Update(&ctx, &fport, sizeof(fport)); - SipHash24_Update(&ctx, laddr, sizeof(*laddr)); - SipHash24_Update(&ctx, &lport, sizeof(lport)); - - return (&table->inpt_hashtbl[SipHash24_End(&ctx) & table->inpt_mask]); -} - struct inpcbhead * in_pcblhash(struct inpcbtable *table, int rdom, u_short lport) { @@ -1070,48 +1041,6 @@ in_pcbhashlookup(struct inpcbtable *table, struct in_addr faddr, return (inp); } -#ifdef INET6 -struct inpcb * -in6_pcbhashlookup(struct inpcbtable *table, const struct in6_addr *faddr, - u_int fport_arg, const struct in6_addr *laddr, u_int lport_arg, - u_int rtable) -{ - struct inpcbhead *head; - struct inpcb *inp; - u_int16_t fport = fport_arg, lport = lport_arg; - u_int rdomain; - - rdomain = rtable_l2(rtable); - head = in6_pcbhash(table, rdomain, faddr, fport, laddr, lport); - LIST_FOREACH(inp, head, inp_hash) { - if (!(inp->inp_flags & INP_IPV6)) - continue; - if (IN6_ARE_ADDR_EQUAL(&inp->inp_faddr6, faddr) && - inp->inp_fport == fport && inp->inp_lport == lport && - IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, laddr) && - rtable_l2(inp->inp_rtableid) == rdomain) { - /* - * Move this PCB to the head of hash chain so that - * repeated accesses are quicker. This is analogous to - * the historic single-entry PCB cache. - */ - if (inp != LIST_FIRST(head)) { - LIST_REMOVE(inp, inp_hash); - LIST_INSERT_HEAD(head, inp, inp_hash); - } - break; - } - } -#ifdef DIAGNOSTIC - if (inp == NULL && in_pcbnotifymiss) { - printf("%s: faddr= fport=%d laddr= lport=%d rdom=%u\n", - __func__, ntohs(fport), ntohs(lport), rdomain); - } -#endif - return (inp); -} -#endif /* INET6 */ - /* * The in(6)_pcblookup_listen functions are used to locate listening * sockets quickly. This are sockets with unspecified foreign address @@ -1207,87 +1136,3 @@ in_pcblookup_listen(struct inpcbtable *table, struct in_addr laddr, #endif return (inp); } - -#ifdef INET6 -struct inpcb * -in6_pcblookup_listen(struct inpcbtable *table, struct in6_addr *laddr, - u_int lport_arg, struct mbuf *m, u_int rtable) -{ - struct inpcbhead *head; - const struct in6_addr *key1, *key2; - struct inpcb *inp; - u_int16_t lport = lport_arg; - u_int rdomain; - - key1 = laddr; - key2 = &zeroin6_addr; -#if NPF > 0 - if (m && m->m_pkthdr.pf.flags & PF_TAG_DIVERTED) { - struct pf_divert *divert; - - divert = pf_find_divert(m); - KASSERT(divert != NULL); - switch (divert->type) { - case PF_DIVERT_TO: - key1 = key2 = &divert->addr.v6; - lport = divert->port; - break; - case PF_DIVERT_REPLY: - return (NULL); - default: - panic("%s: unknown divert type %d, mbuf %p, divert %p", - __func__, divert->type, m, divert); - } - } else if (m && m->m_pkthdr.pf.flags & PF_TAG_TRANSLATE_LOCALHOST) { - /* - * Redirected connections should not be treated the same - * as connections directed to ::1 since localhost - * can only be accessed from the host itself. - */ - key1 = &zeroin6_addr; - key2 = laddr; - } -#endif - - rdomain = rtable_l2(rtable); - head = in6_pcbhash(table, rdomain, &zeroin6_addr, 0, key1, lport); - LIST_FOREACH(inp, head, inp_hash) { - if (!(inp->inp_flags & INP_IPV6)) - continue; - if (inp->inp_lport == lport && inp->inp_fport == 0 && - IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, key1) && - IN6_IS_ADDR_UNSPECIFIED(&inp->inp_faddr6) && - rtable_l2(inp->inp_rtableid) == rdomain) - break; - } - if (inp == NULL && ! IN6_ARE_ADDR_EQUAL(key1, key2)) { - head = in6_pcbhash(table, rdomain, - &zeroin6_addr, 0, key2, lport); - LIST_FOREACH(inp, head, inp_hash) { - if (!(inp->inp_flags & INP_IPV6)) - continue; - if (inp->inp_lport == lport && inp->inp_fport == 0 && - IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, key2) && - IN6_IS_ADDR_UNSPECIFIED(&inp->inp_faddr6) && - rtable_l2(inp->inp_rtableid) == rdomain) - break; - } - } - /* - * Move this PCB to the head of hash chain so that - * repeated accesses are quicker. This is analogous to - * the historic single-entry PCB cache. - */ - if (inp != NULL && inp != LIST_FIRST(head)) { - LIST_REMOVE(inp, inp_hash); - LIST_INSERT_HEAD(head, inp, inp_hash); - } -#ifdef DIAGNOSTIC - if (inp == NULL && in_pcbnotifymiss) { - printf("%s: laddr= lport=%d rdom=%u\n", - __func__, ntohs(lport), rdomain); - } -#endif - return (inp); -} -#endif /* INET6 */ diff --git a/sys/netinet/in_pcb.h b/sys/netinet/in_pcb.h index 10f6081aa33..fdf1973fb17 100644 --- a/sys/netinet/in_pcb.h +++ b/sys/netinet/in_pcb.h @@ -1,4 +1,4 @@ -/* $OpenBSD: in_pcb.h,v 1.109 2018/06/03 21:00:15 bluhm Exp $ */ +/* $OpenBSD: in_pcb.h,v 1.110 2018/09/11 14:34:49 bluhm Exp $ */ /* $NetBSD: in_pcb.h,v 1.14 1996/02/13 23:42:00 christos Exp $ */ /* @@ -249,6 +249,7 @@ struct baddynamicports { extern struct inpcbtable rawcbtable, rawin6pcbtable; extern struct baddynamicports baddynamicports; extern struct baddynamicports rootonlyports; +extern int in_pcbnotifymiss; #define sotopf(so) (so->so_proto->pr_domain->dom_family) @@ -267,6 +268,9 @@ struct inpcb * in_pcblookup_listen(struct inpcbtable *, struct in_addr, u_int, struct mbuf *, u_int); #ifdef INET6 +struct inpcbhead * + in6_pcbhash(struct inpcbtable *, int, const struct in6_addr *, + u_short, const struct in6_addr *, u_short); struct inpcb * in6_pcbhashlookup(struct inpcbtable *, const struct in6_addr *, u_int, const struct in6_addr *, u_int, u_int); diff --git a/sys/netinet6/in6_pcb.c b/sys/netinet6/in6_pcb.c index 803729e1441..a1c19967147 100644 --- a/sys/netinet6/in6_pcb.c +++ b/sys/netinet6/in6_pcb.c @@ -1,4 +1,4 @@ -/* $OpenBSD: in6_pcb.c,v 1.104 2018/06/14 17:00:58 bluhm Exp $ */ +/* $OpenBSD: in6_pcb.c,v 1.105 2018/09/11 14:34:49 bluhm Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -99,30 +99,25 @@ * */ +#include "pf.h" + #include #include #include -#include #include #include #include -#include -#include -#include -#include #include #include -#include +#include #include #include -#include #include +#include #include -#include -#include /* * External globals @@ -150,6 +145,24 @@ u_char inet6ctlerrmap[PRC_NCMDS] = { }; #endif +struct inpcbhead * +in6_pcbhash(struct inpcbtable *table, int rdom, + const struct in6_addr *faddr, u_short fport, + const struct in6_addr *laddr, u_short lport) +{ + SIPHASH_CTX ctx; + u_int32_t nrdom = htonl(rdom); + + SipHash24_Init(&ctx, &table->inpt_key); + SipHash24_Update(&ctx, &nrdom, sizeof(nrdom)); + SipHash24_Update(&ctx, faddr, sizeof(*faddr)); + SipHash24_Update(&ctx, &fport, sizeof(fport)); + SipHash24_Update(&ctx, laddr, sizeof(*laddr)); + SipHash24_Update(&ctx, &lport, sizeof(lport)); + + return (&table->inpt_hashtbl[SipHash24_End(&ctx) & table->inpt_mask]); +} + int in6_pcbaddrisavail(struct inpcb *inp, struct sockaddr_in6 *sin6, int wild, struct proc *p) @@ -312,6 +325,52 @@ in6_pcbconnect(struct inpcb *inp, struct mbuf *nam) return (0); } +/* + * Get the local address/port, and put it in a sockaddr_in6. + * This services the getsockname(2) call. + */ +int +in6_setsockaddr(struct inpcb *inp, struct mbuf *nam) +{ + struct sockaddr_in6 *sin6; + + nam->m_len = sizeof(struct sockaddr_in6); + sin6 = mtod(nam,struct sockaddr_in6 *); + + bzero ((caddr_t)sin6,sizeof(struct sockaddr_in6)); + sin6->sin6_family = AF_INET6; + sin6->sin6_len = sizeof(struct sockaddr_in6); + sin6->sin6_port = inp->inp_lport; + sin6->sin6_addr = inp->inp_laddr6; + /* KAME hack: recover scopeid */ + in6_recoverscope(sin6, &inp->inp_laddr6); + + return 0; +} + +/* + * Get the foreign address/port, and put it in a sockaddr_in6. + * This services the getpeername(2) call. + */ +int +in6_setpeeraddr(struct inpcb *inp, struct mbuf *nam) +{ + struct sockaddr_in6 *sin6; + + nam->m_len = sizeof(struct sockaddr_in6); + sin6 = mtod(nam,struct sockaddr_in6 *); + + bzero ((caddr_t)sin6,sizeof(struct sockaddr_in6)); + sin6->sin6_family = AF_INET6; + sin6->sin6_len = sizeof(struct sockaddr_in6); + sin6->sin6_port = inp->inp_fport; + sin6->sin6_addr = inp->inp_faddr6; + /* KAME hack: recover scopeid */ + in6_recoverscope(sin6, &inp->inp_faddr6); + + return 0; +} + /* * Pass some notification to all connections of a protocol * associated with address dst. The local address and/or port numbers @@ -455,48 +514,124 @@ in6_pcbnotify(struct inpcbtable *table, struct sockaddr_in6 *dst, return (nmatch); } -/* - * Get the local address/port, and put it in a sockaddr_in6. - * This services the getsockname(2) call. - */ -int -in6_setsockaddr(struct inpcb *inp, struct mbuf *nam) +struct inpcb * +in6_pcbhashlookup(struct inpcbtable *table, const struct in6_addr *faddr, + u_int fport_arg, const struct in6_addr *laddr, u_int lport_arg, + u_int rtable) { - struct sockaddr_in6 *sin6; - - nam->m_len = sizeof(struct sockaddr_in6); - sin6 = mtod(nam,struct sockaddr_in6 *); - - bzero ((caddr_t)sin6,sizeof(struct sockaddr_in6)); - sin6->sin6_family = AF_INET6; - sin6->sin6_len = sizeof(struct sockaddr_in6); - sin6->sin6_port = inp->inp_lport; - sin6->sin6_addr = inp->inp_laddr6; - /* KAME hack: recover scopeid */ - in6_recoverscope(sin6, &inp->inp_laddr6); + struct inpcbhead *head; + struct inpcb *inp; + u_int16_t fport = fport_arg, lport = lport_arg; + u_int rdomain; - return 0; + rdomain = rtable_l2(rtable); + head = in6_pcbhash(table, rdomain, faddr, fport, laddr, lport); + LIST_FOREACH(inp, head, inp_hash) { + if (!(inp->inp_flags & INP_IPV6)) + continue; + if (IN6_ARE_ADDR_EQUAL(&inp->inp_faddr6, faddr) && + inp->inp_fport == fport && inp->inp_lport == lport && + IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, laddr) && + rtable_l2(inp->inp_rtableid) == rdomain) { + /* + * Move this PCB to the head of hash chain so that + * repeated accesses are quicker. This is analogous to + * the historic single-entry PCB cache. + */ + if (inp != LIST_FIRST(head)) { + LIST_REMOVE(inp, inp_hash); + LIST_INSERT_HEAD(head, inp, inp_hash); + } + break; + } + } +#ifdef DIAGNOSTIC + if (inp == NULL && in_pcbnotifymiss) { + printf("%s: faddr= fport=%d laddr= lport=%d rdom=%u\n", + __func__, ntohs(fport), ntohs(lport), rdomain); + } +#endif + return (inp); } -/* - * Get the foreign address/port, and put it in a sockaddr_in6. - * This services the getpeername(2) call. - */ -int -in6_setpeeraddr(struct inpcb *inp, struct mbuf *nam) +struct inpcb * +in6_pcblookup_listen(struct inpcbtable *table, struct in6_addr *laddr, + u_int lport_arg, struct mbuf *m, u_int rtable) { - struct sockaddr_in6 *sin6; - - nam->m_len = sizeof(struct sockaddr_in6); - sin6 = mtod(nam,struct sockaddr_in6 *); + struct inpcbhead *head; + const struct in6_addr *key1, *key2; + struct inpcb *inp; + u_int16_t lport = lport_arg; + u_int rdomain; - bzero ((caddr_t)sin6,sizeof(struct sockaddr_in6)); - sin6->sin6_family = AF_INET6; - sin6->sin6_len = sizeof(struct sockaddr_in6); - sin6->sin6_port = inp->inp_fport; - sin6->sin6_addr = inp->inp_faddr6; - /* KAME hack: recover scopeid */ - in6_recoverscope(sin6, &inp->inp_faddr6); + key1 = laddr; + key2 = &zeroin6_addr; +#if NPF > 0 + if (m && m->m_pkthdr.pf.flags & PF_TAG_DIVERTED) { + struct pf_divert *divert; + + divert = pf_find_divert(m); + KASSERT(divert != NULL); + switch (divert->type) { + case PF_DIVERT_TO: + key1 = key2 = &divert->addr.v6; + lport = divert->port; + break; + case PF_DIVERT_REPLY: + return (NULL); + default: + panic("%s: unknown divert type %d, mbuf %p, divert %p", + __func__, divert->type, m, divert); + } + } else if (m && m->m_pkthdr.pf.flags & PF_TAG_TRANSLATE_LOCALHOST) { + /* + * Redirected connections should not be treated the same + * as connections directed to ::1 since localhost + * can only be accessed from the host itself. + */ + key1 = &zeroin6_addr; + key2 = laddr; + } +#endif - return 0; + rdomain = rtable_l2(rtable); + head = in6_pcbhash(table, rdomain, &zeroin6_addr, 0, key1, lport); + LIST_FOREACH(inp, head, inp_hash) { + if (!(inp->inp_flags & INP_IPV6)) + continue; + if (inp->inp_lport == lport && inp->inp_fport == 0 && + IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, key1) && + IN6_IS_ADDR_UNSPECIFIED(&inp->inp_faddr6) && + rtable_l2(inp->inp_rtableid) == rdomain) + break; + } + if (inp == NULL && ! IN6_ARE_ADDR_EQUAL(key1, key2)) { + head = in6_pcbhash(table, rdomain, + &zeroin6_addr, 0, key2, lport); + LIST_FOREACH(inp, head, inp_hash) { + if (!(inp->inp_flags & INP_IPV6)) + continue; + if (inp->inp_lport == lport && inp->inp_fport == 0 && + IN6_ARE_ADDR_EQUAL(&inp->inp_laddr6, key2) && + IN6_IS_ADDR_UNSPECIFIED(&inp->inp_faddr6) && + rtable_l2(inp->inp_rtableid) == rdomain) + break; + } + } + /* + * Move this PCB to the head of hash chain so that + * repeated accesses are quicker. This is analogous to + * the historic single-entry PCB cache. + */ + if (inp != NULL && inp != LIST_FIRST(head)) { + LIST_REMOVE(inp, inp_hash); + LIST_INSERT_HEAD(head, inp, inp_hash); + } +#ifdef DIAGNOSTIC + if (inp == NULL && in_pcbnotifymiss) { + printf("%s: laddr= lport=%d rdom=%u\n", + __func__, ntohs(lport), rdomain); + } +#endif + return (inp); }