summaryrefslogtreecommitdiffstats
path: root/net/tipc/socket.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2019-12-01 20:35:03 -0800
committerLinus Torvalds <torvalds@linux-foundation.org>2019-12-01 20:35:03 -0800
commitc3bfc5dd73c6f519ff0636d4e709515f06edef78 (patch)
treee4e0ab6d67c44a96ca06e05d7d074e39320cc7e2 /net/tipc/socket.c
parente5b3fc125d768eacd73bb4dc5019f0ce95635af4 (diff)
parentc5d728113532c695c894c2a88a10453ac83b0f3b (diff)
Merge git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net
Pull networking fixes from David Miller: 1) Fix several scatter gather list issues in kTLS code, from Jakub Kicinski. 2) macb driver device remove has to kill the hresp_err_tasklet. From Chuhong Yuan. 3) Several memory leak and reference count bug fixes in tipc, from Tung Nguyen. 4) Fix mlx5 build error w/o ipv6, from Yue Haibing. 5) Fix jumbo frame and other regressions in r8169, from Heiner Kallweit. 6) Undo some BUG_ON()'s and replace them with WARN_ON_ONCE and proper error propagation/handling. From Paolo Abeni. * git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net: (24 commits) openvswitch: remove another BUG_ON() openvswitch: drop unneeded BUG_ON() in ovs_flow_cmd_build_info() net: phy: realtek: fix using paged operations with RTL8105e / RTL8208 r8169: fix resume on cable plug-in r8169: fix jumbo configuration for RTL8168evl net: emulex: benet: indent a Kconfig depends continuation line selftests: forwarding: fix race between packet receive and tc check net: sched: fix `tc -s class show` no bstats on class with nolock subqueues net: ethernet: ti: ale: ensure vlan/mdb deleted when no members net/mlx5e: Fix build error without IPV6 selftests: pmtu: use -oneline for ip route list cache tipc: fix duplicate SYN messages under link congestion tipc: fix wrong timeout input for tipc_wait_for_cond() tipc: fix wrong socket reference counter after tipc_sk_timeout() returns tipc: fix potential memory leak in __tipc_sendmsg() net: macb: add missed tasklet_kill selftests: bpf: correct perror strings selftests: bpf: test_sockmap: handle file creation failures gracefully net/tls: use sg_next() to walk sg entries net/tls: remove the dead inplace_crypto code ...
Diffstat (limited to 'net/tipc/socket.c')
-rw-r--r--net/tipc/socket.c24
1 files changed, 15 insertions, 9 deletions
diff --git a/net/tipc/socket.c b/net/tipc/socket.c
index a1c8d722ca20..41688da233ab 100644
--- a/net/tipc/socket.c
+++ b/net/tipc/socket.c
@@ -532,7 +532,7 @@ static void __tipc_shutdown(struct socket *sock, int error)
struct sock *sk = sock->sk;
struct tipc_sock *tsk = tipc_sk(sk);
struct net *net = sock_net(sk);
- long timeout = CONN_TIMEOUT_DEFAULT;
+ long timeout = msecs_to_jiffies(CONN_TIMEOUT_DEFAULT);
u32 dnode = tsk_peer_node(tsk);
struct sk_buff *skb;
@@ -540,12 +540,10 @@ static void __tipc_shutdown(struct socket *sock, int error)
tipc_wait_for_cond(sock, &timeout, (!tsk->cong_link_cnt &&
!tsk_conn_cong(tsk)));
- /* Push out unsent messages or remove if pending SYN */
- skb = skb_peek(&sk->sk_write_queue);
- if (skb && !msg_is_syn(buf_msg(skb)))
- tipc_sk_push_backlog(tsk);
- else
- __skb_queue_purge(&sk->sk_write_queue);
+ /* Push out delayed messages if in Nagle mode */
+ tipc_sk_push_backlog(tsk);
+ /* Remove pending SYN */
+ __skb_queue_purge(&sk->sk_write_queue);
/* Reject all unreceived messages, except on an active connection
* (which disconnects locally & sends a 'FIN+' to peer).
@@ -1248,9 +1246,14 @@ static void tipc_sk_push_backlog(struct tipc_sock *tsk)
struct sk_buff_head *txq = &tsk->sk.sk_write_queue;
struct net *net = sock_net(&tsk->sk);
u32 dnode = tsk_peer_node(tsk);
+ struct sk_buff *skb = skb_peek(txq);
int rc;
- if (skb_queue_empty(txq) || tsk->cong_link_cnt)
+ if (!skb || tsk->cong_link_cnt)
+ return;
+
+ /* Do not send SYN again after congestion */
+ if (msg_is_syn(buf_msg(skb)))
return;
tsk->snt_unacked += tsk->snd_backlog;
@@ -1447,8 +1450,10 @@ static int __tipc_sendmsg(struct socket *sock, struct msghdr *m, size_t dlen)
rc = tipc_msg_build(hdr, m, 0, dlen, mtu, &pkts);
if (unlikely(rc != dlen))
return rc;
- if (unlikely(syn && !tipc_msg_skb_clone(&pkts, &sk->sk_write_queue)))
+ if (unlikely(syn && !tipc_msg_skb_clone(&pkts, &sk->sk_write_queue))) {
+ __skb_queue_purge(&pkts);
return -ENOMEM;
+ }
trace_tipc_sk_sendmsg(sk, skb_peek(&pkts), TIPC_DUMP_SK_SNDQ, " ");
rc = tipc_node_xmit(net, &pkts, dnode, tsk->portid);
@@ -2757,6 +2762,7 @@ static void tipc_sk_timeout(struct timer_list *t)
if (sock_owned_by_user(sk)) {
sk_reset_timer(sk, &sk->sk_timer, jiffies + HZ / 20);
bh_unlock_sock(sk);
+ sock_put(sk);
return;
}