Revert "net: socket ioctl to reset connections matching local address"

Use SOCK_DESTROY from now instead of SIOCKILLADDR

This reverts commit 38f0ec724f.

Change-Id: I2dcd833b66c88a48de8978dce9d72ab78f9af549
This commit is contained in:
Dmitry Shmidt 2016-04-21 15:47:01 -07:00 committed by Amit Pundir
parent d8c5b6f850
commit 3094efd84c
6 changed files with 1 additions and 133 deletions

View file

@ -1681,8 +1681,6 @@ static inline bool tcp_stream_memory_free(const struct sock *sk)
return notsent_bytes < tcp_notsent_lowat(tp); return notsent_bytes < tcp_notsent_lowat(tp);
} }
extern int tcp_nuke_addr(struct net *net, struct sockaddr *addr);
#ifdef CONFIG_PROC_FS #ifdef CONFIG_PROC_FS
int tcp4_proc_init(void); int tcp4_proc_init(void);
void tcp4_proc_exit(void); void tcp4_proc_exit(void);

View file

@ -65,7 +65,6 @@
#define SIOCDIFADDR 0x8936 /* delete PA address */ #define SIOCDIFADDR 0x8936 /* delete PA address */
#define SIOCSIFHWBROADCAST 0x8937 /* set hardware broadcast addr */ #define SIOCSIFHWBROADCAST 0x8937 /* set hardware broadcast addr */
#define SIOCGIFCOUNT 0x8938 /* get number of devices */ #define SIOCGIFCOUNT 0x8938 /* get number of devices */
#define SIOCKILLADDR 0x8939 /* kill sockets with this local addr */
#define SIOCGIFBR 0x8940 /* Bridging support */ #define SIOCGIFBR 0x8940 /* Bridging support */
#define SIOCSIFBR 0x8941 /* Set bridging options */ #define SIOCSIFBR 0x8941 /* Set bridging options */

View file

@ -886,7 +886,6 @@ int inet_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
case SIOCSIFPFLAGS: case SIOCSIFPFLAGS:
case SIOCGIFPFLAGS: case SIOCGIFPFLAGS:
case SIOCSIFFLAGS: case SIOCSIFFLAGS:
case SIOCKILLADDR:
err = devinet_ioctl(net, cmd, (void __user *)arg); err = devinet_ioctl(net, cmd, (void __user *)arg);
break; break;
default: default:

View file

@ -59,7 +59,6 @@
#include <net/arp.h> #include <net/arp.h>
#include <net/ip.h> #include <net/ip.h>
#include <net/tcp.h>
#include <net/route.h> #include <net/route.h>
#include <net/ip_fib.h> #include <net/ip_fib.h>
#include <net/rtnetlink.h> #include <net/rtnetlink.h>
@ -969,7 +968,6 @@ int devinet_ioctl(struct net *net, unsigned int cmd, void __user *arg)
case SIOCSIFBRDADDR: /* Set the broadcast address */ case SIOCSIFBRDADDR: /* Set the broadcast address */
case SIOCSIFDSTADDR: /* Set the destination address */ case SIOCSIFDSTADDR: /* Set the destination address */
case SIOCSIFNETMASK: /* Set the netmask for the interface */ case SIOCSIFNETMASK: /* Set the netmask for the interface */
case SIOCKILLADDR: /* Nuke all sockets on this address */
ret = -EPERM; ret = -EPERM;
if (!ns_capable(net->user_ns, CAP_NET_ADMIN)) if (!ns_capable(net->user_ns, CAP_NET_ADMIN))
goto out; goto out;
@ -1021,8 +1019,7 @@ int devinet_ioctl(struct net *net, unsigned int cmd, void __user *arg)
} }
ret = -EADDRNOTAVAIL; ret = -EADDRNOTAVAIL;
if (!ifa && cmd != SIOCSIFADDR && cmd != SIOCSIFFLAGS if (!ifa && cmd != SIOCSIFADDR && cmd != SIOCSIFFLAGS)
&& cmd != SIOCKILLADDR)
goto done; goto done;
switch (cmd) { switch (cmd) {
@ -1149,9 +1146,6 @@ int devinet_ioctl(struct net *net, unsigned int cmd, void __user *arg)
inet_insert_ifa(ifa); inet_insert_ifa(ifa);
} }
break; break;
case SIOCKILLADDR: /* Nuke all connections on this address */
ret = tcp_nuke_addr(net, (struct sockaddr *) sin);
break;
} }
done: done:
rtnl_unlock(); rtnl_unlock();

View file

@ -276,9 +276,6 @@
#include <net/tcp.h> #include <net/tcp.h>
#include <net/xfrm.h> #include <net/xfrm.h>
#include <net/ip.h> #include <net/ip.h>
#include <net/ip6_route.h>
#include <net/ipv6.h>
#include <net/transp_v6.h>
#include <net/sock.h> #include <net/sock.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
@ -3254,105 +3251,3 @@ void __init tcp_init(void)
BUG_ON(tcp_register_congestion_control(&tcp_reno) != 0); BUG_ON(tcp_register_congestion_control(&tcp_reno) != 0);
tcp_tasklet_init(); tcp_tasklet_init();
} }
static int tcp_is_local(struct net *net, __be32 addr) {
struct rtable *rt;
struct flowi4 fl4 = { .daddr = addr };
rt = ip_route_output_key(net, &fl4);
if (IS_ERR_OR_NULL(rt))
return 0;
return rt->dst.dev && (rt->dst.dev->flags & IFF_LOOPBACK);
}
#if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE)
static int tcp_is_local6(struct net *net, struct in6_addr *addr) {
struct rt6_info *rt6 = rt6_lookup(net, addr, addr, 0, 0);
return rt6 && rt6->dst.dev && (rt6->dst.dev->flags & IFF_LOOPBACK);
}
#endif
/*
* tcp_nuke_addr - destroy all sockets on the given local address
* if local address is the unspecified address (0.0.0.0 or ::), destroy all
* sockets with local addresses that are not configured.
*/
int tcp_nuke_addr(struct net *net, struct sockaddr *addr)
{
int family = addr->sa_family;
unsigned int bucket;
struct in_addr *in;
#if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE)
struct in6_addr *in6 = NULL;
#endif
if (family == AF_INET) {
in = &((struct sockaddr_in *)addr)->sin_addr;
#if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE)
} else if (family == AF_INET6) {
in6 = &((struct sockaddr_in6 *)addr)->sin6_addr;
#endif
} else {
return -EAFNOSUPPORT;
}
for (bucket = 0; bucket < tcp_hashinfo.ehash_mask; bucket++) {
struct hlist_nulls_node *node;
struct sock *sk;
spinlock_t *lock = inet_ehash_lockp(&tcp_hashinfo, bucket);
restart:
spin_lock_bh(lock);
sk_nulls_for_each(sk, node, &tcp_hashinfo.ehash[bucket].chain) {
struct inet_sock *inet = inet_sk(sk);
if (sysctl_ip_dynaddr && sk->sk_state == TCP_SYN_SENT)
continue;
if (sock_flag(sk, SOCK_DEAD))
continue;
if (family == AF_INET) {
__be32 s4 = inet->inet_rcv_saddr;
if (s4 == LOOPBACK4_IPV6)
continue;
if (in->s_addr != s4 &&
!(in->s_addr == INADDR_ANY &&
!tcp_is_local(net, s4)))
continue;
}
#if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE)
if (family == AF_INET6) {
struct in6_addr *s6;
s6 = &sk->sk_v6_rcv_saddr;
if (ipv6_addr_type(s6) == IPV6_ADDR_MAPPED)
continue;
if (!ipv6_addr_equal(in6, s6) &&
!(ipv6_addr_equal(in6, &in6addr_any) &&
!tcp_is_local6(net, s6)))
continue;
}
#endif
sock_hold(sk);
spin_unlock_bh(lock);
local_bh_disable();
bh_lock_sock(sk);
sk->sk_err = ETIMEDOUT;
sk->sk_error_report(sk);
tcp_done(sk);
bh_unlock_sock(sk);
local_bh_enable();
sock_put(sk);
goto restart;
}
spin_unlock_bh(lock);
}
return 0;
}

View file

@ -495,21 +495,6 @@ int inet6_getname(struct socket *sock, struct sockaddr *uaddr,
} }
EXPORT_SYMBOL(inet6_getname); EXPORT_SYMBOL(inet6_getname);
int inet6_killaddr_ioctl(struct net *net, void __user *arg) {
struct in6_ifreq ireq;
struct sockaddr_in6 sin6;
if (!capable(CAP_NET_ADMIN))
return -EACCES;
if (copy_from_user(&ireq, arg, sizeof(struct in6_ifreq)))
return -EFAULT;
sin6.sin6_family = AF_INET6;
sin6.sin6_addr = ireq.ifr6_addr;
return tcp_nuke_addr(net, (struct sockaddr *) &sin6);
}
int inet6_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg) int inet6_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
{ {
struct sock *sk = sock->sk; struct sock *sk = sock->sk;
@ -533,8 +518,6 @@ int inet6_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
return addrconf_del_ifaddr(net, (void __user *) arg); return addrconf_del_ifaddr(net, (void __user *) arg);
case SIOCSIFDSTADDR: case SIOCSIFDSTADDR:
return addrconf_set_dstaddr(net, (void __user *) arg); return addrconf_set_dstaddr(net, (void __user *) arg);
case SIOCKILLADDR:
return inet6_killaddr_ioctl(net, (void __user *) arg);
default: default:
if (!sk->sk_prot->ioctl) if (!sk->sk_prot->ioctl)
return -ENOIOCTLCMD; return -ENOIOCTLCMD;