Skip to content

Commit

Permalink
mptcp: consolidate in_opt sub-options fields in a bitmask
Browse files Browse the repository at this point in the history
This makes input options processing more consistent with
output ones and will simplify the next patch.

Also avoid clearing the suboption field after processing
it, since it's not needed.

Reviewed-by: Mat Martineau <[email protected]>
Signed-off-by: Paolo Abeni <[email protected]>
  • Loading branch information
Paolo Abeni authored and matttbe committed Aug 20, 2021
1 parent f2ce74f commit 8b88edd
Show file tree
Hide file tree
Showing 4 changed files with 63 additions and 73 deletions.
74 changes: 30 additions & 44 deletions net/mptcp/options.c
Original file line number Diff line number Diff line change
Expand Up @@ -81,11 +81,11 @@ static void mptcp_parse_option(const struct sk_buff *skb,
* is if both hosts in their SYNs set A=0."
*/
if (flags & MPTCP_CAP_CHECKSUM_REQD)
mp_opt->csum_reqd = 1;
mp_opt->suboptions |= OPTION_MPTCP_CSUMREQD;

mp_opt->deny_join_id0 = !!(flags & MPTCP_CAP_DENY_JOIN_ID0);

mp_opt->mp_capable = 1;
mp_opt->suboptions |= OPTIONS_MPTCP_MPC;
if (opsize >= TCPOLEN_MPTCP_MPC_SYNACK) {
mp_opt->sndr_key = get_unaligned_be64(ptr);
ptr += 8;
Expand All @@ -100,15 +100,15 @@ static void mptcp_parse_option(const struct sk_buff *skb,
* equivalent to those in a DSS option and can be used
* interchangeably."
*/
mp_opt->dss = 1;
mp_opt->suboptions |= OPTION_MPTCP_DSS;
mp_opt->use_map = 1;
mp_opt->mpc_map = 1;
mp_opt->data_len = get_unaligned_be16(ptr);
ptr += 2;
}
if (opsize == TCPOLEN_MPTCP_MPC_ACK_DATA_CSUM) {
mp_opt->csum = (__force __sum16)get_unaligned_be16(ptr);
mp_opt->csum_reqd = 1;
mp_opt->suboptions |= OPTION_MPTCP_CSUMREQD;
ptr += 2;
}
pr_debug("MP_CAPABLE version=%x, flags=%x, optlen=%d sndr=%llu, rcvr=%llu len=%d csum=%u",
Expand All @@ -117,7 +117,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
break;

case MPTCPOPT_MP_JOIN:
mp_opt->mp_join = 1;
mp_opt->suboptions |= OPTIONS_MPTCP_MPJ;
if (opsize == TCPOLEN_MPTCP_MPJ_SYN) {
mp_opt->backup = *ptr++ & MPTCPOPT_BACKUP;
mp_opt->join_id = *ptr++;
Expand All @@ -143,7 +143,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
memcpy(mp_opt->hmac, ptr, MPTCPOPT_HMAC_LEN);
pr_debug("MP_JOIN hmac");
} else {
mp_opt->mp_join = 0;
mp_opt->suboptions &= ~OPTIONS_MPTCP_MPJ;
}
break;

Expand Down Expand Up @@ -191,8 +191,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
opsize != expected_opsize + TCPOLEN_MPTCP_DSS_CHECKSUM)
break;

mp_opt->dss = 1;

mp_opt->suboptions |= OPTION_MPTCP_DSS;
if (mp_opt->use_ack) {
if (mp_opt->ack64) {
mp_opt->data_ack = get_unaligned_be64(ptr);
Expand Down Expand Up @@ -221,14 +220,15 @@ static void mptcp_parse_option(const struct sk_buff *skb,
ptr += 2;

if (opsize == expected_opsize + TCPOLEN_MPTCP_DSS_CHECKSUM) {
mp_opt->csum_reqd = 1;
mp_opt->suboptions |= OPTION_MPTCP_CSUMREQD;
mp_opt->csum = (__force __sum16)get_unaligned_be16(ptr);
ptr += 2;
}

pr_debug("data_seq=%llu subflow_seq=%u data_len=%u csum=%d:%u",
mp_opt->data_seq, mp_opt->subflow_seq,
mp_opt->data_len, mp_opt->csum_reqd, mp_opt->csum);
mp_opt->data_len, !!(mp_opt->suboptions & OPTION_MPTCP_CSUMREQD),
mp_opt->csum);
}

break;
Expand Down Expand Up @@ -259,7 +259,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
break;
}

mp_opt->add_addr = 1;
mp_opt->suboptions |= OPTION_MPTCP_ADD_ADDR;
mp_opt->addr.id = *ptr++;
mp_opt->addr.port = 0;
mp_opt->ahmac = 0;
Expand Down Expand Up @@ -299,7 +299,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,

ptr++;

mp_opt->rm_addr = 1;
mp_opt->suboptions |= OPTION_MPTCP_RM_ADDR;
mp_opt->rm_list.nr = opsize - TCPOLEN_MPTCP_RM_ADDR_BASE;
for (i = 0; i < mp_opt->rm_list.nr; i++)
mp_opt->rm_list.ids[i] = *ptr++;
Expand All @@ -310,7 +310,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
if (opsize != TCPOLEN_MPTCP_PRIO)
break;

mp_opt->mp_prio = 1;
mp_opt->suboptions |= OPTION_MPTCP_PRIO;
mp_opt->backup = *ptr++ & MPTCP_PRIO_BKUP;
pr_debug("MP_PRIO: prio=%d", mp_opt->backup);
break;
Expand All @@ -322,7 +322,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
ptr += 2;
mp_opt->rcvr_key = get_unaligned_be64(ptr);
ptr += 8;
mp_opt->fastclose = 1;
mp_opt->suboptions |= OPTION_MPTCP_FASTCLOSE;
break;

case MPTCPOPT_RST:
Expand All @@ -331,7 +331,8 @@ static void mptcp_parse_option(const struct sk_buff *skb,

if (!(TCP_SKB_CB(skb)->tcp_flags & TCPHDR_RST))
break;
mp_opt->reset = 1;

mp_opt->suboptions |= OPTION_MPTCP_RST;
flags = *ptr++;
mp_opt->reset_transient = flags & MPTCP_RST_TRANSIENT;
mp_opt->reset_reason = *ptr;
Expand All @@ -342,7 +343,7 @@ static void mptcp_parse_option(const struct sk_buff *skb,
break;

ptr += 2;
mp_opt->mp_fail = 1;
mp_opt->suboptions |= OPTION_MPTCP_FAIL;
mp_opt->fail_seq = get_unaligned_be64(ptr);
pr_debug("MP_FAIL: data_seq=%llu", mp_opt->fail_seq);
break;
Expand All @@ -361,16 +362,7 @@ void mptcp_get_options(const struct sock *sk,
int length;

/* initialize option status */
mp_opt->mp_capable = 0;
mp_opt->mp_join = 0;
mp_opt->add_addr = 0;
mp_opt->fastclose = 0;
mp_opt->rm_addr = 0;
mp_opt->dss = 0;
mp_opt->mp_prio = 0;
mp_opt->reset = 0;
mp_opt->csum_reqd = 0;
mp_opt->mp_fail = 0;
mp_opt->suboptions = 0;

length = (th->doff * 4) - sizeof(struct tcphdr);
ptr = (const unsigned char *)(th + 1);
Expand Down Expand Up @@ -924,7 +916,7 @@ static bool check_fully_established(struct mptcp_sock *msk, struct sock *ssk,
*/
if (TCP_SKB_CB(skb)->seq == subflow->ssn_offset + 1 &&
TCP_SKB_CB(skb)->end_seq == TCP_SKB_CB(skb)->seq &&
subflow->mp_join && mp_opt->mp_join &&
subflow->mp_join && (mp_opt->suboptions & OPTIONS_MPTCP_MPJ) &&
READ_ONCE(msk->pm.server_side))
tcp_send_ack(ssk);
goto fully_established;
Expand All @@ -941,8 +933,8 @@ static bool check_fully_established(struct mptcp_sock *msk, struct sock *ssk,
return subflow->mp_capable;
}

if ((mp_opt->dss && mp_opt->use_ack) ||
(mp_opt->add_addr && !mp_opt->echo)) {
if (((mp_opt->suboptions & OPTION_MPTCP_DSS) && mp_opt->use_ack) ||
((mp_opt->suboptions & OPTION_MPTCP_ADD_ADDR) && !mp_opt->echo)) {
/* subflows are fully established as soon as we get any
* additional ack, including ADD_ADDR.
*/
Expand All @@ -955,7 +947,7 @@ static bool check_fully_established(struct mptcp_sock *msk, struct sock *ssk,
* then fallback to TCP. Fallback scenarios requires a reset for
* MP_JOIN subflows.
*/
if (!mp_opt->mp_capable) {
if (!(mp_opt->suboptions & OPTIONS_MPTCP_MPC)) {
if (subflow->mp_join)
goto reset;
subflow->mp_capable = 0;
Expand Down Expand Up @@ -1119,13 +1111,13 @@ bool mptcp_incoming_options(struct sock *sk, struct sk_buff *skb)
if (!check_fully_established(msk, sk, subflow, skb, &mp_opt))
return sk->sk_state != TCP_CLOSE;

if (mp_opt.fastclose &&
if ((mp_opt.suboptions & OPTION_MPTCP_FASTCLOSE) &&
msk->local_key == mp_opt.rcvr_key) {
WRITE_ONCE(msk->rcv_fastclose, true);
mptcp_schedule_work((struct sock *)msk);
}

if (mp_opt.add_addr && add_addr_hmac_valid(msk, &mp_opt)) {
if ((mp_opt.suboptions & OPTION_MPTCP_ADD_ADDR) && add_addr_hmac_valid(msk, &mp_opt)) {
if (!mp_opt.echo) {
mptcp_pm_add_addr_received(msk, &mp_opt.addr);
MPTCP_INC_STATS(sock_net(sk), MPTCP_MIB_ADDADDR);
Expand All @@ -1137,34 +1129,28 @@ bool mptcp_incoming_options(struct sock *sk, struct sk_buff *skb)

if (mp_opt.addr.port)
MPTCP_INC_STATS(sock_net(sk), MPTCP_MIB_PORTADD);

mp_opt.add_addr = 0;
}

if (mp_opt.rm_addr) {
if (mp_opt.suboptions & OPTION_MPTCP_RM_ADDR)
mptcp_pm_rm_addr_received(msk, &mp_opt.rm_list);
mp_opt.rm_addr = 0;
}

if (mp_opt.mp_prio) {
if (mp_opt.suboptions & OPTION_MPTCP_PRIO) {
mptcp_pm_mp_prio_received(sk, mp_opt.backup);
MPTCP_INC_STATS(sock_net(sk), MPTCP_MIB_MPPRIORX);
mp_opt.mp_prio = 0;
}

if (mp_opt.mp_fail) {
if (mp_opt.suboptions & OPTION_MPTCP_FAIL) {
mptcp_pm_mp_fail_received(sk, mp_opt.fail_seq);
MPTCP_INC_STATS(sock_net(sk), MPTCP_MIB_MPFAILRX);
mp_opt.mp_fail = 0;
}

if (mp_opt.reset) {
if (mp_opt.suboptions & OPTION_MPTCP_RST) {
subflow->reset_seen = 1;
subflow->reset_reason = mp_opt.reset_reason;
subflow->reset_transient = mp_opt.reset_transient;
}

if (!mp_opt.dss)
if (!(mp_opt.suboptions & OPTION_MPTCP_DSS))
return true;

/* we can't wait for recvmsg() to update the ack_seq, otherwise
Expand Down Expand Up @@ -1213,7 +1199,7 @@ bool mptcp_incoming_options(struct sock *sk, struct sk_buff *skb)
}
mpext->data_len = mp_opt.data_len;
mpext->use_map = 1;
mpext->csum_reqd = mp_opt.csum_reqd;
mpext->csum_reqd = !!(mp_opt.suboptions & OPTION_MPTCP_CSUMREQD);

if (mpext->csum_reqd)
mpext->csum = mp_opt.csum;
Expand Down
4 changes: 2 additions & 2 deletions net/mptcp/protocol.c
Original file line number Diff line number Diff line change
Expand Up @@ -2832,7 +2832,7 @@ struct sock *mptcp_sk_clone(const struct sock *sk,
msk->token = subflow_req->token;
msk->subflow = NULL;
WRITE_ONCE(msk->fully_established, false);
if (mp_opt->csum_reqd)
if (mp_opt->suboptions & OPTION_MPTCP_CSUMREQD)
WRITE_ONCE(msk->csum_enabled, true);

msk->write_seq = subflow_req->idsn + 1;
Expand All @@ -2841,7 +2841,7 @@ struct sock *mptcp_sk_clone(const struct sock *sk,
msk->wnd_end = msk->snd_nxt + req->rsk_rcv_wnd;
msk->setsockopt_seq = mptcp_sk(sk)->setsockopt_seq;

if (mp_opt->mp_capable) {
if (mp_opt->suboptions & OPTIONS_MPTCP_MPC) {
msk->can_ack = true;
msk->remote_key = mp_opt->sndr_key;
mptcp_crypto_key_sha(msk->remote_key, NULL, &ack_seq);
Expand Down
18 changes: 8 additions & 10 deletions net/mptcp/protocol.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,13 @@
#define OPTION_MPTCP_DSS BIT(11)
#define OPTION_MPTCP_FAIL BIT(12)

#define OPTION_MPTCP_CSUMREQD BIT(13)

#define OPTIONS_MPTCP_MPC (OPTION_MPTCP_MPC_SYN | OPTION_MPTCP_MPC_SYNACK | \
OPTION_MPTCP_MPC_ACK)
#define OPTIONS_MPTCP_MPJ (OPTION_MPTCP_MPJ_SYN | OPTION_MPTCP_MPJ_SYNACK | \
OPTION_MPTCP_MPJ_SYNACK)

/* MPTCP option subtypes */
#define MPTCPOPT_MP_CAPABLE 0
#define MPTCPOPT_MP_JOIN 1
Expand Down Expand Up @@ -132,16 +139,7 @@ struct mptcp_options_received {
u32 subflow_seq;
u16 data_len;
__sum16 csum;
u16 mp_capable : 1,
mp_join : 1,
fastclose : 1,
reset : 1,
dss : 1,
add_addr : 1,
rm_addr : 1,
mp_prio : 1,
csum_reqd : 1,
mp_fail : 1;
u16 suboptions;
u32 token;
u32 nonce;
u16 use_map:1,
Expand Down
Loading

0 comments on commit 8b88edd

Please sign in to comment.