[DCCP] [RFT/Bug-Fix] [Patch 1/1]: Special case for client-PARTOPEN with DataAcks

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



     (This is an update for the test-tree, not meant for mainline now)

--------------------------> Patch <-------------------------------------
[DCCP]: Special case for client-PARTOPEN with DataAcks

There are two conflicting goals: providing a large room for options and allowing
the client to send DataAcks in the "half-open" PARTOPEN state. 

To increase robustness, it is necessary to resend Confirm feature-negotiation
options, even though the RFC does not mandate it. But feature negotiation
options can take (much) more room than the options on common DataAck packets.

Instead of reducing the MPS always for a case which only applies to the three
messages send during initial handshake, this patch devises a special case:
if the payload length of the DataAck in PARTOPEN is too large, an Ack is sent
to carry the options, and the feature-negotiation list is then flushed.

This means that the server gets two Acks for one Response. If both Acks get
lost, it is probably better to restart the connection anyway and devising yet
another special-case does not seem worth the extra complexity.

Signed-off-by: Gerrit Renker <gerrit@xxxxxxxxxxxxxx>
---
 net/dccp/feat.h   |    3 +++
 net/dccp/output.c |   16 +++++++++++++++-
 2 files changed, 18 insertions(+), 1 deletion(-)

--- a/net/dccp/feat.h
+++ b/net/dccp/feat.h
@@ -23,6 +23,9 @@
 #define DCCPF_SEQ_WMIN		32
 #define DCCPF_SEQ_WMAX		0x3FFFFFFFFFFFull
 
+/* Feature-negotiation overhead in multiples of 4-byte words */
+#define DCCP_FEATNEG_OVERHEAD_FACTOR	32
+
 enum dccp_feat_type {
 	FEAT_AT_RX   = 1,	/* located at RX side of half-connection  */
 	FEAT_AT_TX   = 2,	/* located at TX side of half-connection  */
--- a/net/dccp/output.c
+++ b/net/dccp/output.c
@@ -245,7 +245,21 @@ static void dccp_xmit_packet(struct sock
 	len = skb->len;
 
 	if (sk->sk_state == DCCP_PARTOPEN) {
-		/* See 8.1.5.  Handshake Completion */
+		const u32 overhead = DCCP_FEATNEG_OVERHEAD_FACTOR << 2;
+		/*
+		 * See 8.1.5 - Handshake Completion.
+		 * For robustness we resend Confirm options until the client has
+		 * entered OPEN. Unfortunately, the "copious space for options"
+		 * (RFC 4340, 4.6) means that there is less space for payload.
+		 * For overly large payloads, send second Ack to carry options.
+		 */
+		if (!list_empty(&dp->dccps_featneg) &&
+		    len + overhead >= dp->dccps_mss_cache) {
+			DCCP_WARN("Payload too large (%d) for featneg.\n", len);
+			dccp_send_ack(sk);
+			dccp_feat_list_purge(&dp->dccps_featneg);
+		}
+
 		inet_csk_schedule_ack(sk);
 		inet_csk_reset_xmit_timer(sk, ICSK_TIME_DACK,
 					      inet_csk(sk)->icsk_rto,
--
To unsubscribe from this list: send the line "unsubscribe dccp" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Kernel]     [IETF DCCP]     [Linux Networking]     [Git]     [Security]     [Linux Assembly]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]

  Powered by Linux