tcp: add tcp_sock_set_cork
Add a helper to directly set the TCP_CORK sockopt from kernel space without going through a fake uaccess. Cleanup the callers to avoid pointless wrappers now that this is a simple function call. Signed-off-by: Christoph Hellwig <hch@lst.de> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
fe31a326a4
commit
db10538a4b
|
@ -1570,20 +1570,6 @@ extern void drbd_set_recv_tcq(struct drbd_device *device, int tcq_enabled);
|
|||
extern void _drbd_clear_done_ee(struct drbd_device *device, struct list_head *to_be_freed);
|
||||
extern int drbd_connected(struct drbd_peer_device *);
|
||||
|
||||
static inline void drbd_tcp_cork(struct socket *sock)
|
||||
{
|
||||
int val = 1;
|
||||
(void) kernel_setsockopt(sock, SOL_TCP, TCP_CORK,
|
||||
(char*)&val, sizeof(val));
|
||||
}
|
||||
|
||||
static inline void drbd_tcp_uncork(struct socket *sock)
|
||||
{
|
||||
int val = 0;
|
||||
(void) kernel_setsockopt(sock, SOL_TCP, TCP_CORK,
|
||||
(char*)&val, sizeof(val));
|
||||
}
|
||||
|
||||
static inline void drbd_tcp_nodelay(struct socket *sock)
|
||||
{
|
||||
int val = 1;
|
||||
|
|
|
@ -6162,7 +6162,7 @@ void drbd_send_acks_wf(struct work_struct *ws)
|
|||
rcu_read_unlock();
|
||||
|
||||
if (tcp_cork)
|
||||
drbd_tcp_cork(connection->meta.socket);
|
||||
tcp_sock_set_cork(connection->meta.socket->sk, true);
|
||||
|
||||
err = drbd_finish_peer_reqs(device);
|
||||
kref_put(&device->kref, drbd_destroy_device);
|
||||
|
@ -6175,7 +6175,7 @@ void drbd_send_acks_wf(struct work_struct *ws)
|
|||
}
|
||||
|
||||
if (tcp_cork)
|
||||
drbd_tcp_uncork(connection->meta.socket);
|
||||
tcp_sock_set_cork(connection->meta.socket->sk, false);
|
||||
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -2098,7 +2098,7 @@ static void wait_for_work(struct drbd_connection *connection, struct list_head *
|
|||
if (uncork) {
|
||||
mutex_lock(&connection->data.mutex);
|
||||
if (connection->data.socket)
|
||||
drbd_tcp_uncork(connection->data.socket);
|
||||
tcp_sock_set_cork(connection->data.socket->sk, false);
|
||||
mutex_unlock(&connection->data.mutex);
|
||||
}
|
||||
|
||||
|
@ -2153,9 +2153,9 @@ static void wait_for_work(struct drbd_connection *connection, struct list_head *
|
|||
mutex_lock(&connection->data.mutex);
|
||||
if (connection->data.socket) {
|
||||
if (cork)
|
||||
drbd_tcp_cork(connection->data.socket);
|
||||
tcp_sock_set_cork(connection->data.socket->sk, true);
|
||||
else if (!uncork)
|
||||
drbd_tcp_uncork(connection->data.socket);
|
||||
tcp_sock_set_cork(connection->data.socket->sk, false);
|
||||
}
|
||||
mutex_unlock(&connection->data.mutex);
|
||||
}
|
||||
|
|
|
@ -325,7 +325,6 @@ __smb_send_rqst(struct TCP_Server_Info *server, int num_rqst,
|
|||
size_t total_len = 0, sent, size;
|
||||
struct socket *ssocket = server->ssocket;
|
||||
struct msghdr smb_msg;
|
||||
int val = 1;
|
||||
__be32 rfc1002_marker;
|
||||
|
||||
if (cifs_rdma_enabled(server)) {
|
||||
|
@ -345,8 +344,7 @@ __smb_send_rqst(struct TCP_Server_Info *server, int num_rqst,
|
|||
}
|
||||
|
||||
/* cork the socket */
|
||||
kernel_setsockopt(ssocket, SOL_TCP, TCP_CORK,
|
||||
(char *)&val, sizeof(val));
|
||||
tcp_sock_set_cork(ssocket->sk, true);
|
||||
|
||||
for (j = 0; j < num_rqst; j++)
|
||||
send_length += smb_rqst_len(server, &rqst[j]);
|
||||
|
@ -435,9 +433,7 @@ __smb_send_rqst(struct TCP_Server_Info *server, int num_rqst,
|
|||
}
|
||||
|
||||
/* uncork it */
|
||||
val = 0;
|
||||
kernel_setsockopt(ssocket, SOL_TCP, TCP_CORK,
|
||||
(char *)&val, sizeof(val));
|
||||
tcp_sock_set_cork(ssocket->sk, false);
|
||||
|
||||
if ((total_len > 0) && (total_len != send_length)) {
|
||||
cifs_dbg(FYI, "partial send (wanted=%u sent=%zu): terminating session\n",
|
||||
|
|
|
@ -497,4 +497,6 @@ static inline u16 tcp_mss_clamp(const struct tcp_sock *tp, u16 mss)
|
|||
int tcp_skb_shift(struct sk_buff *to, struct sk_buff *from, int pcount,
|
||||
int shiftlen);
|
||||
|
||||
void tcp_sock_set_cork(struct sock *sk, bool on);
|
||||
|
||||
#endif /* _LINUX_TCP_H */
|
||||
|
|
|
@ -2801,6 +2801,37 @@ static void tcp_enable_tx_delay(void)
|
|||
}
|
||||
}
|
||||
|
||||
/* When set indicates to always queue non-full frames. Later the user clears
|
||||
* this option and we transmit any pending partial frames in the queue. This is
|
||||
* meant to be used alongside sendfile() to get properly filled frames when the
|
||||
* user (for example) must write out headers with a write() call first and then
|
||||
* use sendfile to send out the data parts.
|
||||
*
|
||||
* TCP_CORK can be set together with TCP_NODELAY and it is stronger than
|
||||
* TCP_NODELAY.
|
||||
*/
|
||||
static void __tcp_sock_set_cork(struct sock *sk, bool on)
|
||||
{
|
||||
struct tcp_sock *tp = tcp_sk(sk);
|
||||
|
||||
if (on) {
|
||||
tp->nonagle |= TCP_NAGLE_CORK;
|
||||
} else {
|
||||
tp->nonagle &= ~TCP_NAGLE_CORK;
|
||||
if (tp->nonagle & TCP_NAGLE_OFF)
|
||||
tp->nonagle |= TCP_NAGLE_PUSH;
|
||||
tcp_push_pending_frames(sk);
|
||||
}
|
||||
}
|
||||
|
||||
void tcp_sock_set_cork(struct sock *sk, bool on)
|
||||
{
|
||||
lock_sock(sk);
|
||||
__tcp_sock_set_cork(sk, on);
|
||||
release_sock(sk);
|
||||
}
|
||||
EXPORT_SYMBOL(tcp_sock_set_cork);
|
||||
|
||||
/*
|
||||
* Socket option code for TCP.
|
||||
*/
|
||||
|
@ -2979,25 +3010,7 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
|
|||
break;
|
||||
|
||||
case TCP_CORK:
|
||||
/* When set indicates to always queue non-full frames.
|
||||
* Later the user clears this option and we transmit
|
||||
* any pending partial frames in the queue. This is
|
||||
* meant to be used alongside sendfile() to get properly
|
||||
* filled frames when the user (for example) must write
|
||||
* out headers with a write() call first and then use
|
||||
* sendfile to send out the data parts.
|
||||
*
|
||||
* TCP_CORK can be set together with TCP_NODELAY and it is
|
||||
* stronger than TCP_NODELAY.
|
||||
*/
|
||||
if (val) {
|
||||
tp->nonagle |= TCP_NAGLE_CORK;
|
||||
} else {
|
||||
tp->nonagle &= ~TCP_NAGLE_CORK;
|
||||
if (tp->nonagle&TCP_NAGLE_OFF)
|
||||
tp->nonagle |= TCP_NAGLE_PUSH;
|
||||
tcp_push_pending_frames(sk);
|
||||
}
|
||||
__tcp_sock_set_cork(sk, val);
|
||||
break;
|
||||
|
||||
case TCP_KEEPIDLE:
|
||||
|
|
|
@ -38,23 +38,18 @@
|
|||
#include "rds.h"
|
||||
#include "tcp.h"
|
||||
|
||||
static void rds_tcp_cork(struct socket *sock, int val)
|
||||
{
|
||||
kernel_setsockopt(sock, SOL_TCP, TCP_CORK, (void *)&val, sizeof(val));
|
||||
}
|
||||
|
||||
void rds_tcp_xmit_path_prepare(struct rds_conn_path *cp)
|
||||
{
|
||||
struct rds_tcp_connection *tc = cp->cp_transport_data;
|
||||
|
||||
rds_tcp_cork(tc->t_sock, 1);
|
||||
tcp_sock_set_cork(tc->t_sock->sk, true);
|
||||
}
|
||||
|
||||
void rds_tcp_xmit_path_complete(struct rds_conn_path *cp)
|
||||
{
|
||||
struct rds_tcp_connection *tc = cp->cp_transport_data;
|
||||
|
||||
rds_tcp_cork(tc->t_sock, 0);
|
||||
tcp_sock_set_cork(tc->t_sock->sk, false);
|
||||
}
|
||||
|
||||
/* the core send_sem serializes this with other xmit and shutdown */
|
||||
|
|
Loading…
Reference in New Issue