From: Peter Krystad Signed-off-by: Peter Krystad --- net/mptcp/protocol.c | 48 ++++++++++++++++++++++++++++++++++++++++++++++++ net/mptcp/subflow.c | 22 ++++++++++++++++++++++ 2 files changed, 70 insertions(+) diff --git a/net/mptcp/protocol.c b/net/mptcp/protocol.c index 63cf5ead52f2..3d517d6645fe 100644 --- a/net/mptcp/protocol.c +++ b/net/mptcp/protocol.c @@ -167,6 +167,52 @@ static void mptcp_destroy(struct sock *sk) token_destroy(msk->token); } +static int mptcp_setsockopt(struct sock *sk, int level, int optname, + char __user *uoptval, unsigned int optlen) +{ + struct mptcp_sock *msk = mptcp_sk(sk); + struct socket *subflow; + char __kernel *optval; + + pr_debug("msk=%p", msk); + if (msk->connection_list) { + subflow = msk->connection_list; + pr_debug("conn_list->subflow=%p", subflow->sk); + } else { + subflow = msk->subflow; + pr_debug("subflow=%p", subflow->sk); + } + + /* will be treated as __user in subflow_setsockopt */ + optval = (char __kernel __force *) uoptval; + + return kernel_setsockopt(subflow, level, optname, optval, optlen); +} + +static int mptcp_getsockopt(struct sock *sk, int level, int optname, + char __user *uoptval, int __user *uoption) +{ + struct mptcp_sock *msk = mptcp_sk(sk); + struct socket *subflow; + char __kernel *optval; + int __kernel *option; + + pr_debug("msk=%p", msk); + if (msk->connection_list) { + subflow = msk->connection_list; + pr_debug("conn_list->subflow=%p", subflow->sk); + } else { + subflow = msk->subflow; + pr_debug("subflow=%p", subflow->sk); + } + + /* will be treated as __user in subflow_getsockopt */ + optval = (char __kernel __force *) uoptval; + option = (int __kernel __force *) uoption; + + return kernel_getsockopt(subflow, level, optname, optval, option); +} + static int mptcp_get_port(struct sock *sk, unsigned short snum) { struct mptcp_sock *msk = mptcp_sk(sk); @@ -273,6 +319,8 @@ static struct proto mptcp_prot = { .connect = mptcp_connect, .shutdown = tcp_shutdown, .destroy = mptcp_destroy, + .setsockopt = mptcp_setsockopt, + .getsockopt = mptcp_getsockopt, .sendmsg = mptcp_sendmsg, .recvmsg = mptcp_recvmsg, .hash = inet_hash, diff --git a/net/mptcp/subflow.c b/net/mptcp/subflow.c index 9f417f3ed188..0a85f1418385 100644 --- a/net/mptcp/subflow.c +++ b/net/mptcp/subflow.c @@ -248,6 +248,26 @@ static void subflow_destroy(struct sock *sk) tcp_v4_destroy_sock(sk); } +static int subflow_setsockopt(struct sock *sk, int level, int optname, + char __user *optval, unsigned int optlen) +{ + struct subflow_sock *subflow = subflow_sk(sk); + + pr_debug("subflow=%p", subflow); + + return tcp_setsockopt(sk, level, optname, optval, optlen); +} + +static int subflow_getsockopt(struct sock *sk, int level, int optname, + char __user *optval, int __user *option) +{ + struct subflow_sock *subflow = subflow_sk(sk); + + pr_debug("subflow=%p", subflow); + + return tcp_getsockopt(sk, level, optname, optval, option); +} + static struct proto subflow_prot = { .name = "SUBFLOW", .owner = THIS_MODULE, @@ -259,6 +279,8 @@ static struct proto subflow_prot = { .init = subflow_init_sock, .destroy = subflow_destroy, .shutdown = tcp_shutdown, + .setsockopt = subflow_setsockopt, + .getsockopt = subflow_getsockopt, .keepalive = tcp_set_keepalive, .recvmsg = subflow_recvmsg, .sendmsg = subflow_sendmsg, -- 2.16.3