BOOLEAN IsDone;\r
BOOLEAN IsMatched;\r
UINTN CopiedLen;\r
+ UINTN HeaderLen;\r
+ UINTN HeaderCopiedLen;\r
+ UINTN BufferCopiedLen;\r
+ UINT32 FragmentLength;\r
+ UINTN FragmentIndex;\r
+ UINT8 *FragmentBuffer;\r
\r
if (This == NULL || DestIp == NULL || DestPort == NULL) {\r
return EFI_INVALID_PARAMETER;\r
//\r
// Copy the rececived packet to user if matched by filter.\r
//\r
- CopiedLen = 0;\r
if (Mode->UsingIpv6) {\r
Udp6Rx = Udp6Token.Packet.RxData;\r
ASSERT (Udp6Rx != NULL);\r
- //\r
- // Copy the header part of received data.\r
- //\r
+\r
+ HeaderLen = 0;\r
if (HeaderSize != NULL) {\r
- CopiedLen = MIN (*HeaderSize, Udp6Rx->DataLength);\r
- *HeaderSize = CopiedLen;\r
- CopyMem (HeaderPtr, Udp6Rx->FragmentTable[0].FragmentBuffer, *HeaderSize);\r
+ HeaderLen = MIN (*HeaderSize, Udp6Rx->DataLength);\r
}\r
- //\r
- // Copy the other part of received data.\r
- //\r
- if (Udp6Rx->DataLength - CopiedLen > *BufferSize) {\r
+\r
+ if (Udp6Rx->DataLength - HeaderLen > *BufferSize) {\r
Status = EFI_BUFFER_TOO_SMALL;\r
} else {\r
- *BufferSize = Udp6Rx->DataLength - CopiedLen;\r
- CopyMem (BufferPtr, (UINT8 *) Udp6Rx->FragmentTable[0].FragmentBuffer + CopiedLen, *BufferSize);\r
+ *HeaderSize = HeaderLen;\r
+ *BufferSize = Udp6Rx->DataLength - HeaderLen;\r
+\r
+ HeaderCopiedLen = 0;\r
+ BufferCopiedLen = 0;\r
+ for (FragmentIndex = 0; FragmentIndex < Udp6Rx->FragmentCount; FragmentIndex++) {\r
+ FragmentLength = Udp6Rx->FragmentTable[FragmentIndex].FragmentLength;\r
+ FragmentBuffer = Udp6Rx->FragmentTable[FragmentIndex].FragmentBuffer;\r
+ if (HeaderCopiedLen + FragmentLength < HeaderLen) {\r
+ //\r
+ // Copy the header part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) HeaderPtr + HeaderCopiedLen, FragmentBuffer, FragmentLength);\r
+ HeaderCopiedLen += FragmentLength;\r
+ } else if (HeaderCopiedLen < HeaderLen) {\r
+ //\r
+ // Copy the header part of received data.\r
+ //\r
+ CopiedLen = HeaderLen - HeaderCopiedLen;\r
+ CopyMem ((UINT8 *) HeaderPtr + HeaderCopiedLen, FragmentBuffer, CopiedLen);\r
+ HeaderCopiedLen += CopiedLen;\r
+\r
+ //\r
+ // Copy the other part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) BufferPtr + BufferCopiedLen, FragmentBuffer + CopiedLen, FragmentLength - CopiedLen);\r
+ BufferCopiedLen += (FragmentLength - CopiedLen);\r
+ } else {\r
+ //\r
+ // Copy the other part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) BufferPtr + BufferCopiedLen, FragmentBuffer, FragmentLength);\r
+ BufferCopiedLen += FragmentLength;\r
+ }\r
+ }\r
}\r
//\r
// Recycle the receiving buffer after copy to user.\r
} else {\r
Udp4Rx = Udp4Token.Packet.RxData;\r
ASSERT (Udp4Rx != NULL);\r
- //\r
- // Copy the header part of received data.\r
- //\r
+\r
+ HeaderLen = 0;\r
if (HeaderSize != NULL) {\r
- CopiedLen = MIN (*HeaderSize, Udp4Rx->DataLength);\r
- *HeaderSize = CopiedLen;\r
- CopyMem (HeaderPtr, Udp4Rx->FragmentTable[0].FragmentBuffer, *HeaderSize);\r
+ HeaderLen = MIN (*HeaderSize, Udp4Rx->DataLength);\r
}\r
- //\r
- // Copy the other part of received data.\r
- //\r
- if (Udp4Rx->DataLength - CopiedLen > *BufferSize) {\r
+\r
+ if (Udp4Rx->DataLength - HeaderLen > *BufferSize) {\r
Status = EFI_BUFFER_TOO_SMALL;\r
} else {\r
- *BufferSize = Udp4Rx->DataLength - CopiedLen;\r
- CopyMem (BufferPtr, (UINT8 *) Udp4Rx->FragmentTable[0].FragmentBuffer + CopiedLen, *BufferSize);\r
+ *HeaderSize = HeaderLen;\r
+ *BufferSize = Udp4Rx->DataLength - HeaderLen;\r
+\r
+ HeaderCopiedLen = 0;\r
+ BufferCopiedLen = 0;\r
+ for (FragmentIndex = 0; FragmentIndex < Udp4Rx->FragmentCount; FragmentIndex++) {\r
+ FragmentLength = Udp4Rx->FragmentTable[FragmentIndex].FragmentLength;\r
+ FragmentBuffer = Udp4Rx->FragmentTable[FragmentIndex].FragmentBuffer;\r
+ if (HeaderCopiedLen + FragmentLength < HeaderLen) {\r
+ //\r
+ // Copy the header part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) HeaderPtr + HeaderCopiedLen, FragmentBuffer, FragmentLength);\r
+ HeaderCopiedLen += FragmentLength;\r
+ } else if (HeaderCopiedLen < HeaderLen) {\r
+ //\r
+ // Copy the header part of received data.\r
+ //\r
+ CopiedLen = HeaderLen - HeaderCopiedLen;\r
+ CopyMem ((UINT8 *) HeaderPtr + HeaderCopiedLen, FragmentBuffer, CopiedLen);\r
+ HeaderCopiedLen += CopiedLen;\r
+\r
+ //\r
+ // Copy the other part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) BufferPtr + BufferCopiedLen, FragmentBuffer + CopiedLen, FragmentLength - CopiedLen);\r
+ BufferCopiedLen += (FragmentLength - CopiedLen);\r
+ } else {\r
+ //\r
+ // Copy the other part of received data.\r
+ //\r
+ CopyMem ((UINT8 *) BufferPtr + BufferCopiedLen, FragmentBuffer, FragmentLength);\r
+ BufferCopiedLen += FragmentLength;\r
+ }\r
+ }\r
}\r
//\r
// Recycle the receiving buffer after copy to user.\r