diff options
author | jesper <jesper@FreeBSD.org> | 2001-02-22 21:23:45 +0000 |
---|---|---|
committer | jesper <jesper@FreeBSD.org> | 2001-02-22 21:23:45 +0000 |
commit | 65fa889a568f28016bc5b0bec0e238ae1ba5f299 (patch) | |
tree | 01d0c2e0ae3ce1757ab23b1a35913eb437998527 /sys/netinet/in_pcb.c | |
parent | c3777b879606a977b736ee62694097a83a1fa76a (diff) | |
download | FreeBSD-src-65fa889a568f28016bc5b0bec0e238ae1ba5f299.zip FreeBSD-src-65fa889a568f28016bc5b0bec0e238ae1ba5f299.tar.gz |
Redo the security update done in rev 1.54 of src/sys/netinet/tcp_subr.c
and 1.84 of src/sys/netinet/udp_usrreq.c
The changes broken down:
- remove 0 as a wildcard for addresses and port numbers in
src/sys/netinet/in_pcb.c:in_pcbnotify()
- add src/sys/netinet/in_pcb.c:in_pcbnotifyall() used to notify
all sessions with the specific remote address.
- change
- src/sys/netinet/udp_usrreq.c:udp_ctlinput()
- src/sys/netinet/tcp_subr.c:tcp_ctlinput()
to use in_pcbnotifyall() to notify multiple sessions, instead of
using in_pcbnotify() with 0 as src address and as port numbers.
- remove check for src port == 0 in
- src/sys/netinet/tcp_subr.c:tcp_ctlinput()
- src/sys/netinet/udp_usrreq.c:udp_ctlinput()
as they are no longer needed.
- move handling of redirects and host dead from in_pcbnotify() to
udp_ctlinput() and tcp_ctlinput(), so they will call
in_pcbnotifyall() to notify all sessions with the specific
remote address.
Approved by: jlemon
Inspired by: NetBSD
Diffstat (limited to 'sys/netinet/in_pcb.c')
-rw-r--r-- | sys/netinet/in_pcb.c | 68 |
1 files changed, 45 insertions, 23 deletions
diff --git a/sys/netinet/in_pcb.c b/sys/netinet/in_pcb.c index c114eca..0a8e952 100644 --- a/sys/netinet/in_pcb.c +++ b/sys/netinet/in_pcb.c @@ -78,8 +78,6 @@ struct in_addr zeroin_addr; -static void in_rtchange __P((struct inpcb *, int)); - /* * These configure the range of local port addresses assigned to * "unspecified" outgoing connections/packets/whatever. @@ -693,20 +691,6 @@ in_pcbnotify(head, dst, fport_arg, laddr, lport_arg, cmd, notify, tcp_sequence, if (faddr.s_addr == INADDR_ANY) return; - /* - * Redirects go to all references to the destination, - * and use in_rtchange to invalidate the route cache. - * Dead host indications: notify all references to the destination. - * Otherwise, if we have knowledge of the local port and address, - * deliver only to that socket. - */ - if (PRC_IS_REDIRECT(cmd) || cmd == PRC_HOSTDEAD) { - fport = 0; - lport = 0; - laddr.s_addr = 0; - if (cmd != PRC_HOSTDEAD) - notify = in_rtchange; - } errno = inetctlerrmap[cmd]; s = splnet(); for (inp = LIST_FIRST(head); inp != NULL;) { @@ -717,12 +701,11 @@ in_pcbnotify(head, dst, fport_arg, laddr, lport_arg, cmd, notify, tcp_sequence, } #endif if (inp->inp_faddr.s_addr != faddr.s_addr || - inp->inp_socket == 0 || - (lport && inp->inp_lport != lport) || - (laddr.s_addr && inp->inp_laddr.s_addr != laddr.s_addr) || - (fport && inp->inp_fport != fport)) { - inp = LIST_NEXT(inp, inp_list); - continue; + inp->inp_socket == 0 || inp->inp_lport != lport || + inp->inp_laddr.s_addr != laddr.s_addr || + inp->inp_fport != fport) { + inp = LIST_NEXT(inp, inp_list); + continue; } /* * If tcp_seq_check is set, then skip sessions where @@ -743,6 +726,45 @@ in_pcbnotify(head, dst, fport_arg, laddr, lport_arg, cmd, notify, tcp_sequence, splx(s); } +void +in_pcbnotifyall(head, dst, cmd, notify) + struct inpcbhead *head; + struct sockaddr *dst; + int cmd; + void (*notify) __P((struct inpcb *, int)); +{ + register struct inpcb *inp, *oinp; + struct in_addr faddr; + int errno, s; + + if ((unsigned)cmd > PRC_NCMDS || dst->sa_family != AF_INET) + return; + faddr = ((struct sockaddr_in *)dst)->sin_addr; + if (faddr.s_addr == INADDR_ANY) + return; + + errno = inetctlerrmap[cmd]; + s = splnet(); + for (inp = LIST_FIRST(head); inp != NULL;) { +#ifdef INET6 + if ((inp->inp_vflag & INP_IPV4) == 0) { + inp = LIST_NEXT(inp, inp_list); + continue; + } +#endif + if (inp->inp_faddr.s_addr != faddr.s_addr || + inp->inp_socket == 0) { + inp = LIST_NEXT(inp, inp_list); + continue; + } + oinp = inp; + inp = LIST_NEXT(inp, inp_list); + if (notify) + (*notify)(oinp, errno); + } + splx(s); +} + /* * Check for alternatives when higher level complains * about service problems. For now, invalidate cached @@ -781,7 +803,7 @@ in_losing(inp) * After a routing change, flush old routing * and allocate a (hopefully) better one. */ -static void +void in_rtchange(inp, errno) register struct inpcb *inp; int errno; |