]> git.proxmox.com Git - mirror_edk2.git/blobdiff - NetworkPkg/TcpDxe/TcpInput.c
BaseTools: Update Makefile to work at absolute path
[mirror_edk2.git] / NetworkPkg / TcpDxe / TcpInput.c
index d0118f1d886d8bd128669047ae066d360ad50f60..f8845dca470e97732482077ef6770b78533347df 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   TCP input process routines.\r
 \r
-  Copyright (c) 2009 - 2015, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2017, Intel Corporation. All rights reserved.<BR>\r
 \r
   This program and the accompanying materials\r
   are licensed and made available under the terms and conditions of the BSD License\r
@@ -31,7 +31,7 @@ TcpSeqAcceptable (
   IN TCP_SEG *Seg\r
   )\r
 {\r
-  return (TCP_SEQ_LEQ (Tcb->RcvWl2, Seg->End) &&\r
+  return (TCP_SEQ_LEQ (Tcb->RcvNxt, Seg->End) &&\r
           TCP_SEQ_LT (Seg->Seq, Tcb->RcvWl2 + Tcb->RcvWnd));\r
 }\r
 \r
@@ -74,7 +74,7 @@ TcpFastRecover (
     Tcb->CWnd = Tcb->Ssthresh + 3 * Tcb->SndMss;\r
 \r
     DEBUG (\r
-      (EFI_D_INFO,\r
+      (EFI_D_NET,\r
       "TcpFastRecover: enter fast retransmission for TCB %p, recover point is %d\n",\r
       Tcb,\r
       Tcb->Recover)\r
@@ -97,7 +97,7 @@ TcpFastRecover (
     //\r
     Tcb->CWnd += Tcb->SndMss;\r
     DEBUG (\r
-      (EFI_D_INFO,\r
+      (EFI_D_NET,\r
       "TcpFastRecover: received another duplicated ACK (%d) for TCB %p\n",\r
       Seg->Ack,\r
       Tcb)\r
@@ -121,7 +121,7 @@ TcpFastRecover (
 \r
       Tcb->CongestState = TCP_CONGEST_OPEN;\r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpFastRecover: received a full ACK(%d) for TCB %p, exit fast recovery\n",\r
         Seg->Ack,\r
         Tcb)\r
@@ -150,7 +150,7 @@ TcpFastRecover (
       Tcb->CWnd -= Acked;\r
 \r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpFastRecover: received a partial ACK(%d) for TCB %p\n",\r
         Seg->Ack,\r
         Tcb)\r
@@ -188,7 +188,7 @@ TcpFastLossRecover (
       Tcb->CongestState = TCP_CONGEST_OPEN;\r
 \r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpFastLossRecover: received a full ACK(%d) for TCB %p\n",\r
         Seg->Ack,\r
         Tcb)\r
@@ -202,7 +202,7 @@ TcpFastLossRecover (
       //\r
       TcpRetransmit (Tcb, Seg->Ack);\r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpFastLossRecover: received a partial ACK(%d) for TCB %p\n",\r
         Seg->Ack,\r
         Tcb)\r
@@ -264,7 +264,7 @@ TcpComputeRtt (
   }\r
 \r
   DEBUG (\r
-    (EFI_D_INFO,\r
+    (EFI_D_NET,\r
     "TcpComputeRtt: new RTT for TCB %p computed SRTT: %d RTTVAR: %d RTO: %d\n",\r
     Tcb,\r
     Tcb->SRtt,\r
@@ -455,7 +455,7 @@ TcpDeliverData (
       }\r
 \r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpDeliverData: processing FIN from peer of TCB %p\n",\r
         Tcb)\r
         );\r
@@ -738,6 +738,7 @@ TcpInput (
   TCP_SEQNO   Right;\r
   TCP_SEQNO   Urg;\r
   UINT16      Checksum;\r
+  INT32       Usable;\r
 \r
   ASSERT ((Version == IP_VERSION_4) || (Version == IP_VERSION_6));\r
 \r
@@ -748,11 +749,18 @@ TcpInput (
 \r
   Head    = (TCP_HEAD *) NetbufGetByte (Nbuf, 0, NULL);\r
   ASSERT (Head != NULL);\r
+  \r
+  if (Nbuf->TotalSize < sizeof (TCP_HEAD)) {\r
+    DEBUG ((EFI_D_NET, "TcpInput: received a malformed packet\n"));\r
+    goto DISCARD;\r
+  }\r
+  \r
   Len     = Nbuf->TotalSize - (Head->HeadLen << 2);\r
 \r
   if ((Head->HeadLen < 5) || (Len < 0)) {\r
 \r
-    DEBUG ((EFI_D_INFO, "TcpInput: received a malformed packet\n"));\r
+    DEBUG ((EFI_D_NET, "TcpInput: received a malformed packet\n"));\r
+    \r
     goto DISCARD;\r
   }\r
 \r
@@ -787,7 +795,7 @@ TcpInput (
           );\r
 \r
   if ((Tcb == NULL) || (Tcb->State == TCP_CLOSED)) {\r
-    DEBUG ((EFI_D_INFO, "TcpInput: send reset because no TCB found\n"));\r
+    DEBUG ((EFI_D_NET, "TcpInput: send reset because no TCB found\n"));\r
 \r
     Tcb = NULL;\r
     goto SEND_RESET;\r
@@ -867,7 +875,7 @@ TcpInput (
       }\r
 \r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpInput: create a child for TCB %p in listening\n",\r
         Tcb)\r
         );\r
@@ -972,7 +980,7 @@ TcpInput (
         TCP_SET_FLG (Tcb->CtrlFlag, TCP_CTRL_ACK_NOW);\r
 \r
         DEBUG (\r
-          (EFI_D_INFO,\r
+          (EFI_D_NET,\r
           "TcpInput: connection established for TCB %p in SYN_SENT\n",\r
           Tcb)\r
           );\r
@@ -1127,7 +1135,7 @@ TcpInput (
       TcpDeliverData (Tcb);\r
 \r
       DEBUG (\r
-        (EFI_D_INFO,\r
+        (EFI_D_NET,\r
         "TcpInput: connection established for TCB %p in SYN_RCVD\n",\r
         Tcb)\r
         );\r
@@ -1299,9 +1307,27 @@ TcpInput (
       }\r
 \r
       if (TCP_SEQ_LT (Right, Tcb->SndNxt)) {\r
-\r
-        Tcb->SndNxt = Right;\r
-\r
+        //\r
+        // Check for Window Retraction in RFC7923 section 2.4.\r
+        // The lower n bits of the peer's actual receive window is wiped out if TCP\r
+        // window scale is enabled, it will look like the peer is shrinking the window.\r
+        // Check whether the SndNxt is out of the advertised receive window by more than\r
+        // 2^Rcv.Wind.Shift before moving the SndNxt to the left.\r
+        //\r
+        DEBUG (\r
+          (EFI_D_WARN,\r
+          "TcpInput: peer advise negative useable window for connected TCB %p\n",\r
+          Tcb)\r
+          );\r
+        Usable = TCP_SUB_SEQ (Tcb->SndNxt, Right);\r
+        if ((Usable >> Tcb->SndWndScale) > 0) {\r
+          DEBUG (\r
+            (EFI_D_WARN,\r
+            "TcpInput: SndNxt is out of window by more than window scale for TCB %p\n",\r
+            Tcb)\r
+            );\r
+          Tcb->SndNxt = Right;\r
+        }\r
         if (Right == Tcb->SndUna) {\r
 \r
           TcpClearTimer (Tcb, TCP_TIMER_REXMIT);\r
@@ -1323,7 +1349,7 @@ NO_UPDATE:
   {\r
 \r
     DEBUG (\r
-      (EFI_D_INFO,\r
+      (EFI_D_NET,\r
       "TcpInput: local FIN is ACKed by peer for connected TCB %p\n",\r
       Tcb)\r
       );\r
@@ -1419,7 +1445,7 @@ StepSix:
   if (TCP_FLG_ON (Seg->Flag, TCP_FLG_URG) && !TCP_FIN_RCVD (Tcb->State)) {\r
 \r
     DEBUG (\r
-      (EFI_D_INFO,\r
+      (EFI_D_NET,\r
       "TcpInput: received urgent data from peer for connected TCB %p\n",\r
       Tcb)\r
       );\r
@@ -1560,6 +1586,10 @@ TcpIcmpInput (
   BOOLEAN          IcmpErrIsHard;\r
   BOOLEAN          IcmpErrNotify;\r
 \r
+  if (Nbuf->TotalSize < sizeof (TCP_HEAD)) {\r
+    goto CLEAN_EXIT;\r
+  }\r
+  \r
   Head = (TCP_HEAD *) NetbufGetByte (Nbuf, 0, NULL);\r
   ASSERT (Head != NULL);\r
 \r