aboutsummaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
Diffstat (limited to 'net')
-rw-r--r--net/tipc/socket.c89
1 files changed, 48 insertions, 41 deletions
diff --git a/net/tipc/socket.c b/net/tipc/socket.c
index b5c9795cf15..9b4e4833a48 100644
--- a/net/tipc/socket.c
+++ b/net/tipc/socket.c
@@ -1509,8 +1509,13 @@ static int listen(struct socket *sock, int len)
1509 */ 1509 */
1510static int accept(struct socket *sock, struct socket *new_sock, int flags) 1510static int accept(struct socket *sock, struct socket *new_sock, int flags)
1511{ 1511{
1512 struct sock *sk = sock->sk; 1512 struct sock *new_sk, *sk = sock->sk;
1513 struct sk_buff *buf; 1513 struct sk_buff *buf;
1514 struct tipc_sock *new_tsock;
1515 struct tipc_port *new_tport;
1516 struct tipc_msg *msg;
1517 u32 new_ref;
1518
1514 int res; 1519 int res;
1515 1520
1516 lock_sock(sk); 1521 lock_sock(sk);
@@ -1536,49 +1541,51 @@ static int accept(struct socket *sock, struct socket *new_sock, int flags)
1536 buf = skb_peek(&sk->sk_receive_queue); 1541 buf = skb_peek(&sk->sk_receive_queue);
1537 1542
1538 res = tipc_create(sock_net(sock->sk), new_sock, 0, 0); 1543 res = tipc_create(sock_net(sock->sk), new_sock, 0, 0);
1539 if (!res) { 1544 if (res)
1540 struct sock *new_sk = new_sock->sk; 1545 goto exit;
1541 struct tipc_sock *new_tsock = tipc_sk(new_sk);
1542 struct tipc_port *new_tport = new_tsock->p;
1543 u32 new_ref = new_tport->ref;
1544 struct tipc_msg *msg = buf_msg(buf);
1545
1546 /* we lock on new_sk; but lockdep sees the lock on sk */
1547 lock_sock_nested(new_sk, SINGLE_DEPTH_NESTING);
1548
1549 /*
1550 * Reject any stray messages received by new socket
1551 * before the socket lock was taken (very, very unlikely)
1552 */
1553 reject_rx_queue(new_sk);
1554
1555 /* Connect new socket to it's peer */
1556 new_tsock->peer_name.ref = msg_origport(msg);
1557 new_tsock->peer_name.node = msg_orignode(msg);
1558 tipc_connect(new_ref, &new_tsock->peer_name);
1559 new_sock->state = SS_CONNECTED;
1560
1561 tipc_set_portimportance(new_ref, msg_importance(msg));
1562 if (msg_named(msg)) {
1563 new_tport->conn_type = msg_nametype(msg);
1564 new_tport->conn_instance = msg_nameinst(msg);
1565 }
1566 1546
1567 /* 1547 new_sk = new_sock->sk;
1568 * Respond to 'SYN-' by discarding it & returning 'ACK'-. 1548 new_tsock = tipc_sk(new_sk);
1569 * Respond to 'SYN+' by queuing it on new socket. 1549 new_tport = new_tsock->p;
1570 */ 1550 new_ref = new_tport->ref;
1571 if (!msg_data_sz(msg)) { 1551 msg = buf_msg(buf);
1572 struct msghdr m = {NULL,};
1573 1552
1574 advance_rx_queue(sk); 1553 /* we lock on new_sk; but lockdep sees the lock on sk */
1575 send_packet(NULL, new_sock, &m, 0); 1554 lock_sock_nested(new_sk, SINGLE_DEPTH_NESTING);
1576 } else { 1555
1577 __skb_dequeue(&sk->sk_receive_queue); 1556 /*
1578 __skb_queue_head(&new_sk->sk_receive_queue, buf); 1557 * Reject any stray messages received by new socket
1579 } 1558 * before the socket lock was taken (very, very unlikely)
1580 release_sock(new_sk); 1559 */
1560 reject_rx_queue(new_sk);
1561
1562 /* Connect new socket to it's peer */
1563 new_tsock->peer_name.ref = msg_origport(msg);
1564 new_tsock->peer_name.node = msg_orignode(msg);
1565 tipc_connect(new_ref, &new_tsock->peer_name);
1566 new_sock->state = SS_CONNECTED;
1567
1568 tipc_set_portimportance(new_ref, msg_importance(msg));
1569 if (msg_named(msg)) {
1570 new_tport->conn_type = msg_nametype(msg);
1571 new_tport->conn_instance = msg_nameinst(msg);
1581 } 1572 }
1573
1574 /*
1575 * Respond to 'SYN-' by discarding it & returning 'ACK'-.
1576 * Respond to 'SYN+' by queuing it on new socket.
1577 */
1578 if (!msg_data_sz(msg)) {
1579 struct msghdr m = {NULL,};
1580
1581 advance_rx_queue(sk);
1582 send_packet(NULL, new_sock, &m, 0);
1583 } else {
1584 __skb_dequeue(&sk->sk_receive_queue);
1585 __skb_queue_head(&new_sk->sk_receive_queue, buf);
1586 }
1587 release_sock(new_sk);
1588
1582exit: 1589exit:
1583 release_sock(sk); 1590 release_sock(sk);
1584 return res; 1591 return res;