+\r
+ if (!HttpInstance->LocalAddressIsIPv6) {\r
+ //\r
+ // Configure TCP instance.\r
+ //\r
+ if (Configure) {\r
+ Status = HttpConfigureTcp4 (HttpInstance, Wrap);\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
+ }\r
+\r
+ //\r
+ // Connect TCP.\r
+ //\r
+ Status = HttpConnectTcp4 (HttpInstance);\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
+ } else {\r
+ //\r
+ // Configure TCP instance.\r
+ //\r
+ if (Configure) {\r
+ Status = HttpConfigureTcp6 (HttpInstance, Wrap);\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
+ }\r
+\r
+ //\r
+ // Connect TCP.\r
+ //\r
+ Status = HttpConnectTcp6 (HttpInstance);\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
+ }\r
+ \r
+ return EFI_SUCCESS;\r
+ \r
+}\r
+\r
+/**\r
+ Send the HTTP or HTTPS message through TCP4 or TCP6.\r
+\r
+ @param[in] HttpInstance The HTTP instance private data.\r
+ @param[in] Wrap The HTTP token's wrap data.\r
+ @param[in] TxString Buffer containing the HTTP message string.\r
+ @param[in] TxStringLen Length of the HTTP message string in bytes.\r
+\r
+ @retval EFI_SUCCESS The HTTP message is queued into TCP transmit queue.\r
+ @retval Others Other error as indicated.\r
+\r
+**/\r
+EFI_STATUS\r
+HttpTransmitTcp (\r
+ IN HTTP_PROTOCOL *HttpInstance,\r
+ IN HTTP_TOKEN_WRAP *Wrap,\r
+ IN UINT8 *TxString,\r
+ IN UINTN TxStringLen\r
+ )\r
+{\r
+ EFI_STATUS Status;\r
+ EFI_TCP4_IO_TOKEN *Tx4Token;\r
+ EFI_TCP4_PROTOCOL *Tcp4;\r
+ EFI_TCP6_IO_TOKEN *Tx6Token;\r
+ EFI_TCP6_PROTOCOL *Tcp6;\r
+ UINT8 *Buffer; \r
+ UINTN BufferSize;\r
+ NET_FRAGMENT TempFragment;\r
+\r
+ Status = EFI_SUCCESS;\r
+ Buffer = NULL;\r
+\r
+ //\r
+ // Need to encrypt data.\r
+ //\r
+ if (HttpInstance->UseHttps) {\r
+ //\r
+ // Build BufferOut data\r
+ //\r
+ BufferSize = sizeof (TLS_RECORD_HEADER) + TxStringLen;\r
+ Buffer = AllocateZeroPool (BufferSize);\r
+ if (Buffer == NULL) {\r
+ Status = EFI_OUT_OF_RESOURCES;\r
+ return Status;\r
+ }\r
+ ((TLS_RECORD_HEADER *) Buffer)->ContentType = TLS_CONTENT_TYPE_APPLICATION_DATA;\r
+ ((TLS_RECORD_HEADER *) Buffer)->Version.Major = HttpInstance->TlsConfigData.Version.Major;\r
+ ((TLS_RECORD_HEADER *) Buffer)->Version.Minor = HttpInstance->TlsConfigData.Version.Minor;\r
+ ((TLS_RECORD_HEADER *) Buffer)->Length = (UINT16) (TxStringLen);\r
+ CopyMem (Buffer + sizeof (TLS_RECORD_HEADER), TxString, TxStringLen);\r
+ \r
+ //\r
+ // Encrypt Packet.\r
+ //\r
+ Status = TlsProcessMessage (\r
+ HttpInstance, \r
+ Buffer, \r
+ BufferSize, \r
+ EfiTlsEncrypt, \r
+ &TempFragment\r
+ );\r
+ \r
+ FreePool (Buffer);\r
+\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
+ }\r
+ \r
+ if (!HttpInstance->LocalAddressIsIPv6) {\r
+ Tcp4 = HttpInstance->Tcp4;\r
+ Tx4Token = &Wrap->TcpWrap.Tx4Token;\r
+\r
+ if (HttpInstance->UseHttps) {\r
+ Tx4Token->Packet.TxData->DataLength = TempFragment.Len;\r
+ Tx4Token->Packet.TxData->FragmentTable[0].FragmentLength = TempFragment.Len;\r
+ Tx4Token->Packet.TxData->FragmentTable[0].FragmentBuffer = (VOID *) TempFragment.Bulk;\r
+ } else {\r
+ Tx4Token->Packet.TxData->DataLength = (UINT32) TxStringLen;\r
+ Tx4Token->Packet.TxData->FragmentTable[0].FragmentLength = (UINT32) TxStringLen;\r
+ Tx4Token->Packet.TxData->FragmentTable[0].FragmentBuffer = (VOID *) TxString;\r
+ }\r
+ \r
+ Tx4Token->CompletionToken.Status = EFI_NOT_READY; \r
+ \r
+ Wrap->TcpWrap.IsTxDone = FALSE;\r
+ Status = Tcp4->Transmit (Tcp4, Tx4Token);\r
+ if (EFI_ERROR (Status)) {\r
+ DEBUG ((EFI_D_ERROR, "Transmit failed: %r\n", Status));\r
+ return Status;\r
+ }\r
+\r
+ } else {\r
+ Tcp6 = HttpInstance->Tcp6;\r
+ Tx6Token = &Wrap->TcpWrap.Tx6Token;\r
+ \r
+ if (HttpInstance->UseHttps) {\r
+ Tx6Token->Packet.TxData->DataLength = TempFragment.Len;\r
+ Tx6Token->Packet.TxData->FragmentTable[0].FragmentLength = TempFragment.Len;\r
+ Tx6Token->Packet.TxData->FragmentTable[0].FragmentBuffer = (VOID *) TempFragment.Bulk;\r
+ } else {\r
+ Tx6Token->Packet.TxData->DataLength = (UINT32) TxStringLen;\r
+ Tx6Token->Packet.TxData->FragmentTable[0].FragmentLength = (UINT32) TxStringLen;\r
+ Tx6Token->Packet.TxData->FragmentTable[0].FragmentBuffer = (VOID *) TxString;\r
+ }\r
+ \r
+ Tx6Token->CompletionToken.Status = EFI_NOT_READY;\r
+\r
+ Wrap->TcpWrap.IsTxDone = FALSE;\r
+ Status = Tcp6->Transmit (Tcp6, Tx6Token);\r
+ if (EFI_ERROR (Status)) {\r
+ DEBUG ((EFI_D_ERROR, "Transmit failed: %r\n", Status));\r
+ return Status;\r
+ }\r
+ }\r
+ \r
+ return Status;\r