mptcp: fix relative DSN/ACK for additional v1 subflows.

In MPTCP v1, in the MPC handshake, the first key is carried by
the SYN/ACK packet: when the mptcp analysis context is created,
the forward direction comes from the server. That is the opposite
of what used to happen with MPTCP v0 - the initial SYN already
carried the sender key.

As a result, when a later MP_JOIN subflows attach to an existing
MPTCP connection v1, the mptcp_subflow meta points to the wrong
flow, and the relative DSN/ACK_SEQ decoding for such flows gives
pseudo-random results.

This change addresses the issue by swapping the MPTCP meta for
MP_JOIN flows after mptcp_get_meta_from_token(), if the negotiated
version for the relevant MPTCP connection is v1.
This commit is contained in:
Paolo Abeni 2020-12-23 18:01:52 +01:00 committed by AndersBroman
parent 1455b6e82d
commit 7844e267ec
1 changed files with 8 additions and 0 deletions

View File

@ -4576,6 +4576,7 @@ get_or_create_mptcpd_from_key(struct tcp_analysis* tcpd, tcp_flow_t *fwd, guint8
DISSECTOR_ASSERT(fwd->mptcp_subflow->meta);
fwd->mptcp_subflow->meta->version = version;
fwd->mptcp_subflow->meta->key = key;
fwd->mptcp_subflow->meta->static_flags |= MPTCP_META_HAS_KEY;
fwd->mptcp_subflow->meta->base_dsn = expected_idsn;
@ -4786,6 +4787,13 @@ dissect_tcpopt_mptcp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void*
offset += 4;
mptcpd = mptcp_get_meta_from_token(tcpd, tcpd->rev, mph->mh_token);
if (tcpd->fwd->mptcp_subflow->meta->version == 1) {
mptcp_meta_flow_t *tmp = tcpd->fwd->mptcp_subflow->meta;
/* if the negotiated version is v1 the first key was exchanged on SYN/ACK packet: we must swap the meta */
tcpd->fwd->mptcp_subflow->meta = tcpd->rev->mptcp_subflow->meta;
tcpd->rev->mptcp_subflow->meta = tmp;
}
proto_tree_add_item_ret_uint(mptcp_tree, hf_tcp_option_mptcp_sender_rand, tvb, offset,
4, ENC_BIG_ENDIAN, &tcpd->fwd->mptcp_subflow->nonce);