diff options
Diffstat (limited to 'net')
-rw-r--r-- | net/sunrpc/xprtsock.c | 96 |
1 files changed, 56 insertions, 40 deletions
diff --git a/net/sunrpc/xprtsock.c b/net/sunrpc/xprtsock.c index 8ff57c59b445..df53dc55841d 100644 --- a/net/sunrpc/xprtsock.c +++ b/net/sunrpc/xprtsock.c | |||
@@ -1660,37 +1660,22 @@ static void xs_udp_finish_connecting(struct rpc_xprt *xprt, struct socket *sock) | |||
1660 | xs_udp_do_set_buffer_size(xprt); | 1660 | xs_udp_do_set_buffer_size(xprt); |
1661 | } | 1661 | } |
1662 | 1662 | ||
1663 | /** | 1663 | static void xs_udp_setup_socket(struct sock_xprt *transport, |
1664 | * xs_udp_connect_worker4 - set up a UDP socket | 1664 | struct socket *(*create_sock)(struct rpc_xprt *, |
1665 | * @work: RPC transport to connect | 1665 | struct sock_xprt *)) |
1666 | * | ||
1667 | * Invoked by a work queue tasklet. | ||
1668 | */ | ||
1669 | static void xs_udp_connect_worker4(struct work_struct *work) | ||
1670 | { | 1666 | { |
1671 | struct sock_xprt *transport = | ||
1672 | container_of(work, struct sock_xprt, connect_worker.work); | ||
1673 | struct rpc_xprt *xprt = &transport->xprt; | 1667 | struct rpc_xprt *xprt = &transport->xprt; |
1674 | struct socket *sock = transport->sock; | 1668 | struct socket *sock = transport->sock; |
1675 | int err, status = -EIO; | 1669 | int status = -EIO; |
1676 | 1670 | ||
1677 | if (xprt->shutdown) | 1671 | if (xprt->shutdown) |
1678 | goto out; | 1672 | goto out; |
1679 | 1673 | ||
1680 | /* Start by resetting any existing state */ | 1674 | /* Start by resetting any existing state */ |
1681 | xs_reset_transport(transport); | 1675 | xs_reset_transport(transport); |
1682 | 1676 | sock = create_sock(xprt, transport); | |
1683 | err = __sock_create(xprt->xprt_net, PF_INET, SOCK_DGRAM, IPPROTO_UDP, &sock, 1); | 1677 | if (IS_ERR(sock)) |
1684 | if (err < 0) { | ||
1685 | dprintk("RPC: can't create UDP transport socket (%d).\n", -err); | ||
1686 | goto out; | 1678 | goto out; |
1687 | } | ||
1688 | xs_reclassify_socket4(sock); | ||
1689 | |||
1690 | if (xs_bind4(transport, sock)) { | ||
1691 | sock_release(sock); | ||
1692 | goto out; | ||
1693 | } | ||
1694 | 1679 | ||
1695 | dprintk("RPC: worker connecting xprt %p via %s to " | 1680 | dprintk("RPC: worker connecting xprt %p via %s to " |
1696 | "%s (port %s)\n", xprt, | 1681 | "%s (port %s)\n", xprt, |
@@ -1706,24 +1691,55 @@ out: | |||
1706 | } | 1691 | } |
1707 | 1692 | ||
1708 | /** | 1693 | /** |
1709 | * xs_udp_connect_worker6 - set up a UDP socket | 1694 | * xs_udp_connect_worker4 - set up a UDP socket |
1710 | * @work: RPC transport to connect | 1695 | * @work: RPC transport to connect |
1711 | * | 1696 | * |
1712 | * Invoked by a work queue tasklet. | 1697 | * Invoked by a work queue tasklet. |
1713 | */ | 1698 | */ |
1714 | static void xs_udp_connect_worker6(struct work_struct *work) | 1699 | |
1700 | static struct socket *xs_create_udp_sock4(struct rpc_xprt *xprt, | ||
1701 | struct sock_xprt *transport) | ||
1702 | { | ||
1703 | struct socket *sock; | ||
1704 | int err; | ||
1705 | |||
1706 | err = __sock_create(xprt->xprt_net, PF_INET, SOCK_DGRAM, IPPROTO_UDP, &sock, 1); | ||
1707 | if (err < 0) { | ||
1708 | dprintk("RPC: can't create UDP transport socket (%d).\n", -err); | ||
1709 | goto out; | ||
1710 | } | ||
1711 | xs_reclassify_socket4(sock); | ||
1712 | |||
1713 | if (xs_bind4(transport, sock)) { | ||
1714 | sock_release(sock); | ||
1715 | goto out; | ||
1716 | } | ||
1717 | |||
1718 | return sock; | ||
1719 | out: | ||
1720 | return ERR_PTR(err); | ||
1721 | } | ||
1722 | |||
1723 | static void xs_udp_connect_worker4(struct work_struct *work) | ||
1715 | { | 1724 | { |
1716 | struct sock_xprt *transport = | 1725 | struct sock_xprt *transport = |
1717 | container_of(work, struct sock_xprt, connect_worker.work); | 1726 | container_of(work, struct sock_xprt, connect_worker.work); |
1718 | struct rpc_xprt *xprt = &transport->xprt; | ||
1719 | struct socket *sock = transport->sock; | ||
1720 | int err, status = -EIO; | ||
1721 | 1727 | ||
1722 | if (xprt->shutdown) | 1728 | xs_udp_setup_socket(transport, xs_create_udp_sock4); |
1723 | goto out; | 1729 | } |
1724 | 1730 | ||
1725 | /* Start by resetting any existing state */ | 1731 | /** |
1726 | xs_reset_transport(transport); | 1732 | * xs_udp_connect_worker6 - set up a UDP socket |
1733 | * @work: RPC transport to connect | ||
1734 | * | ||
1735 | * Invoked by a work queue tasklet. | ||
1736 | */ | ||
1737 | |||
1738 | static struct socket *xs_create_udp_sock6(struct rpc_xprt *xprt, | ||
1739 | struct sock_xprt *transport) | ||
1740 | { | ||
1741 | struct socket *sock; | ||
1742 | int err; | ||
1727 | 1743 | ||
1728 | err = __sock_create(xprt->xprt_net, PF_INET6, SOCK_DGRAM, IPPROTO_UDP, &sock, 1); | 1744 | err = __sock_create(xprt->xprt_net, PF_INET6, SOCK_DGRAM, IPPROTO_UDP, &sock, 1); |
1729 | if (err < 0) { | 1745 | if (err < 0) { |
@@ -1737,17 +1753,17 @@ static void xs_udp_connect_worker6(struct work_struct *work) | |||
1737 | goto out; | 1753 | goto out; |
1738 | } | 1754 | } |
1739 | 1755 | ||
1740 | dprintk("RPC: worker connecting xprt %p via %s to " | 1756 | return sock; |
1741 | "%s (port %s)\n", xprt, | ||
1742 | xprt->address_strings[RPC_DISPLAY_PROTO], | ||
1743 | xprt->address_strings[RPC_DISPLAY_ADDR], | ||
1744 | xprt->address_strings[RPC_DISPLAY_PORT]); | ||
1745 | |||
1746 | xs_udp_finish_connecting(xprt, sock); | ||
1747 | status = 0; | ||
1748 | out: | 1757 | out: |
1749 | xprt_clear_connecting(xprt); | 1758 | return ERR_PTR(err); |
1750 | xprt_wake_pending_tasks(xprt, status); | 1759 | } |
1760 | |||
1761 | static void xs_udp_connect_worker6(struct work_struct *work) | ||
1762 | { | ||
1763 | struct sock_xprt *transport = | ||
1764 | container_of(work, struct sock_xprt, connect_worker.work); | ||
1765 | |||
1766 | xs_udp_setup_socket(transport, xs_create_udp_sock6); | ||
1751 | } | 1767 | } |
1752 | 1768 | ||
1753 | /* | 1769 | /* |