]> git.proxmox.com Git - mirror_edk2.git/commitdiff
For network dynamic media support:
authorxdu2 <xdu2@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 3 Feb 2010 04:37:53 +0000 (04:37 +0000)
committerxdu2 <xdu2@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 3 Feb 2010 04:37:53 +0000 (04:37 +0000)
1. add library function NetLibDetectMedia to NetLib for media detection
2. update MnpDxe to periodically poll for media status update and check for media status before packet transmit
3. update Ip4Dxe to return ModeData using Mnp->GetModeData()
4. update IScsiDxe to check for media status before try to do DHCP and session login
5. update UefiPxeBcDxe to check for media status before PXE start

git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@9919 6f19259b-4bc3-4df7-8a09-765794883524

16 files changed:
MdeModulePkg/Include/Library/NetLib.h
MdeModulePkg/Library/DxeNetLib/DxeNetLib.c
MdeModulePkg/Universal/Network/Dhcp4Dxe/Dhcp4Impl.c
MdeModulePkg/Universal/Network/IScsiDxe/IScsiDhcp.c
MdeModulePkg/Universal/Network/IScsiDxe/IScsiDhcp.h
MdeModulePkg/Universal/Network/IScsiDxe/IScsiProto.c
MdeModulePkg/Universal/Network/IScsiDxe/IScsiProto.h
MdeModulePkg/Universal/Network/Ip4Dxe/Ip4Impl.c
MdeModulePkg/Universal/Network/MnpDxe/MnpConfig.c
MdeModulePkg/Universal/Network/MnpDxe/MnpDriver.c
MdeModulePkg/Universal/Network/MnpDxe/MnpDriver.h
MdeModulePkg/Universal/Network/MnpDxe/MnpImpl.h
MdeModulePkg/Universal/Network/MnpDxe/MnpIo.c
MdeModulePkg/Universal/Network/MnpDxe/MnpMain.c
MdeModulePkg/Universal/Network/Mtftp4Dxe/Mtftp4Impl.c
MdeModulePkg/Universal/Network/UefiPxeBcDxe/PxeBcImpl.c

index 3a3b1901f62e3300631d352cb243233fb83c14d2..854aa0fee0dd21dd4c349c170a2b2a6f58363129 100644 (file)
@@ -1092,6 +1092,40 @@ NetLibGetMacString (
   OUT CHAR16                **MacString\r
   );\r
 \r
+/**\r
+  Detect media status for specified network device.\r
+\r
+  The underlying UNDI driver may or may not support reporting media status from\r
+  GET_STATUS command (PXE_STATFLAGS_GET_STATUS_NO_MEDIA_SUPPORTED). This routine\r
+  will try to invoke Snp->GetStatus() to get the media status: if media already\r
+  present, it return directly; if media not present, it will stop SNP and then\r
+  restart SNP to get the latest media status, this give chance to get the correct\r
+  media status for old UNDI driver which doesn't support reporting media status\r
+  from GET_STATUS command.\r
+  Note: there will be two limitations for current algorithm:\r
+  1) for UNDI with this capability, in case of cable is not attached, there will\r
+     be an redundant Stop/Start() process;\r
+  2) for UNDI without this capability, in case cable is attached in UNDI\r
+     initialize while unattached latter, NetLibDetectMedia() will report\r
+     MediaPresent as TRUE, this cause upper layer apps wait for timeout time.\r
+\r
+  @param[in]   ServiceHandle    The handle where network service binding protocols are\r
+                                installed on.\r
+  @param[out]  MediaPresent     The pointer to store the media status.\r
+\r
+  @retval EFI_SUCCESS           Media detection success.\r
+  @retval EFI_INVALID_PARAMETER ServiceHandle is not valid network device handle.\r
+  @retval EFI_UNSUPPORTED       Network device does not support media detection.\r
+  @retval EFI_DEVICE_ERROR      SNP is in unknown state.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+NetLibDetectMedia (\r
+  IN  EFI_HANDLE            ServiceHandle,\r
+  OUT BOOLEAN               *MediaPresent\r
+  );\r
+\r
 /**\r
   Create an IPv4 device path node.\r
 \r
@@ -1201,7 +1235,7 @@ NetLibDefaultUnload (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip4Address     The pointer to the converted IPv4 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv4 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv4 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip4Address is NULL.\r
 \r
 **/\r
@@ -1218,7 +1252,7 @@ NetLibAsciiStrToIp4 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
 \r
 **/\r
@@ -1234,7 +1268,7 @@ NetLibAsciiStrToIp6 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip4Address     The pointer to the converted IPv4 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv4 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv4 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip4Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
@@ -1252,7 +1286,7 @@ NetLibStrToIp4 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
@@ -1272,7 +1306,7 @@ NetLibStrToIp6 (
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
   @param[out]     PrefixLength   The pointer to the converted prefix length.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
index a5a6762985567590b7d97be3de815a949dd14c1a..5037243b37407a5cab8171824187b7e49ff65394 100644 (file)
@@ -2145,6 +2145,213 @@ NetLibGetMacString (
   return EFI_SUCCESS;\r
 }\r
 \r
+/**\r
+  Detect media status for specified network device.\r
+\r
+  The underlying UNDI driver may or may not support reporting media status from\r
+  GET_STATUS command (PXE_STATFLAGS_GET_STATUS_NO_MEDIA_SUPPORTED). This routine\r
+  will try to invoke Snp->GetStatus() to get the media status: if media already\r
+  present, it return directly; if media not present, it will stop SNP and then\r
+  restart SNP to get the latest media status, this give chance to get the correct\r
+  media status for old UNDI driver which doesn't support reporting media status\r
+  from GET_STATUS command.\r
+  Note: there will be two limitations for current algorithm:\r
+  1) for UNDI with this capability, in case of cable is not attached, there will\r
+     be an redundant Stop/Start() process;\r
+  2) for UNDI without this capability, in case cable is attached in UNDI\r
+     initialize while unattached latter, NetLibDetectMedia() will report\r
+     MediaPresent as TRUE, this cause upper layer apps wait for timeout time.\r
+\r
+  @param[in]   ServiceHandle    The handle where network service binding protocols are\r
+                                installed on.\r
+  @param[out]  MediaPresent     The pointer to store the media status.\r
+\r
+  @retval EFI_SUCCESS           Media detection success.\r
+  @retval EFI_INVALID_PARAMETER ServiceHandle is not valid network device handle.\r
+  @retval EFI_UNSUPPORTED       Network device does not support media detection.\r
+  @retval EFI_DEVICE_ERROR      SNP is in unknown state.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+NetLibDetectMedia (\r
+  IN  EFI_HANDLE            ServiceHandle,\r
+  OUT BOOLEAN               *MediaPresent\r
+  )\r
+{\r
+  EFI_STATUS                   Status;\r
+  EFI_HANDLE                   SnpHandle;\r
+  EFI_SIMPLE_NETWORK_PROTOCOL  *Snp;\r
+  UINT32                       InterruptStatus;\r
+  UINT32                       OldState;\r
+  EFI_MAC_ADDRESS              *MCastFilter;\r
+  UINT32                       MCastFilterCount;\r
+  UINT32                       EnableFilterBits;\r
+  UINT32                       DisableFilterBits;\r
+  BOOLEAN                      ResetMCastFilters;\r
+\r
+  ASSERT (MediaPresent != NULL);\r
+\r
+  //\r
+  // Get SNP handle\r
+  //\r
+  Snp = NULL;\r
+  SnpHandle = NetLibGetSnpHandle (ServiceHandle, &Snp);\r
+  if (SnpHandle == NULL) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
+  //\r
+  // Check whether SNP support media detection\r
+  //\r
+  if (!Snp->Mode->MediaPresentSupported) {\r
+    return EFI_UNSUPPORTED;\r
+  }\r
+\r
+  //\r
+  // Invoke Snp->GetStatus() to refresh MediaPresent field in SNP mode data\r
+  //\r
+  Status = Snp->GetStatus (Snp, &InterruptStatus, NULL);\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
+  }\r
+\r
+  if (Snp->Mode->MediaPresent) {\r
+    //\r
+    // Media is present, return directly\r
+    //\r
+    *MediaPresent = TRUE;\r
+    return EFI_SUCCESS;\r
+  }\r
+\r
+  //\r
+  // Till now, GetStatus() report no media; while, in case UNDI not support\r
+  // reporting media status from GetStatus(), this media status may be incorrect.\r
+  // So, we will stop SNP and then restart it to get the correct media status.\r
+  //\r
+  OldState = Snp->Mode->State;\r
+  if (OldState >= EfiSimpleNetworkMaxState) {\r
+    return EFI_DEVICE_ERROR;\r
+  }\r
+\r
+  MCastFilter = NULL;\r
+\r
+  if (OldState == EfiSimpleNetworkInitialized) {\r
+    //\r
+    // SNP is already in use, need Shutdown/Stop and then Start/Initialize\r
+    //\r
+\r
+    //\r
+    // Backup current SNP receive filter settings\r
+    //\r
+    EnableFilterBits  = Snp->Mode->ReceiveFilterSetting;\r
+    DisableFilterBits = Snp->Mode->ReceiveFilterMask ^ EnableFilterBits;\r
+\r
+    ResetMCastFilters = TRUE;\r
+    MCastFilterCount  = Snp->Mode->MCastFilterCount;\r
+    if (MCastFilterCount != 0) {\r
+      MCastFilter = AllocateCopyPool (\r
+                      MCastFilterCount * sizeof (EFI_MAC_ADDRESS),\r
+                      Snp->Mode->MCastFilter\r
+                      );\r
+      ASSERT (MCastFilter != NULL);\r
+\r
+      ResetMCastFilters = FALSE;\r
+    }\r
+\r
+    //\r
+    // Shutdown/Stop the simple network\r
+    //\r
+    Status = Snp->Shutdown (Snp);\r
+    if (!EFI_ERROR (Status)) {\r
+      Status = Snp->Stop (Snp);\r
+    }\r
+    if (EFI_ERROR (Status)) {\r
+      goto Exit;\r
+    }\r
+\r
+    //\r
+    // Start/Initialize the simple network\r
+    //\r
+    Status = Snp->Start (Snp);\r
+    if (!EFI_ERROR (Status)) {\r
+      Status = Snp->Initialize (Snp, 0, 0);\r
+    }\r
+    if (EFI_ERROR (Status)) {\r
+      goto Exit;\r
+    }\r
+\r
+    //\r
+    // Here we get the correct media status\r
+    //\r
+    *MediaPresent = Snp->Mode->MediaPresent;\r
+\r
+    //\r
+    // Restore SNP receive filter settings\r
+    //\r
+    Status = Snp->ReceiveFilters (\r
+                    Snp,\r
+                    EnableFilterBits,\r
+                    DisableFilterBits,\r
+                    ResetMCastFilters,\r
+                    MCastFilterCount,\r
+                    MCastFilter\r
+                    );\r
+\r
+    if (MCastFilter != NULL) {\r
+      FreePool (MCastFilter);\r
+    }\r
+\r
+    return Status;\r
+  }\r
+\r
+  //\r
+  // SNP is not in use, it's in state of EfiSimpleNetworkStopped or EfiSimpleNetworkStarted\r
+  //\r
+  if (OldState == EfiSimpleNetworkStopped) {\r
+    //\r
+    // SNP not start yet, start it\r
+    //\r
+    Status = Snp->Start (Snp);\r
+    if (EFI_ERROR (Status)) {\r
+      goto Exit;\r
+    }\r
+  }\r
+\r
+  //\r
+  // Initialize the simple network\r
+  //\r
+  Status = Snp->Initialize (Snp, 0, 0);\r
+  if (EFI_ERROR (Status)) {\r
+    Status = EFI_DEVICE_ERROR;\r
+    goto Exit;\r
+  }\r
+\r
+  //\r
+  // Here we get the correct media status\r
+  //\r
+  *MediaPresent = Snp->Mode->MediaPresent;\r
+\r
+  //\r
+  // Shut down the simple network\r
+  //\r
+  Snp->Shutdown (Snp);\r
+\r
+Exit:\r
+  if (OldState == EfiSimpleNetworkStopped) {\r
+    //\r
+    // Original SNP sate is Stopped, restore to original state\r
+    //\r
+    Snp->Stop (Snp);\r
+  }\r
+\r
+  if (MCastFilter != NULL) {\r
+    FreePool (MCastFilter);\r
+  }\r
+\r
+  return Status;\r
+}\r
+\r
 /**\r
   Check the default address used by the IPv4 driver is static or dynamic (acquired\r
   from DHCP).\r
@@ -2417,7 +2624,7 @@ NetLibGetNicHandle (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip4Address     The pointer to the converted IPv4 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv4 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv4 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip4Address is NULL.\r
 \r
 **/\r
@@ -2460,7 +2667,7 @@ NetLibAsciiStrToIp4 (
 \r
     //\r
     // Convert the string to IPv4 address. AsciiStrDecimalToUintn stops at the\r
-    // first character that is not a valid decimal character, '.' or '\0' here. \r
+    // first character that is not a valid decimal character, '.' or '\0' here.\r
     //\r
     NodeVal = AsciiStrDecimalToUintn (TempStr);\r
     if (NodeVal > 0xFF) {\r
@@ -2483,7 +2690,7 @@ NetLibAsciiStrToIp4 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
 \r
 **/\r
@@ -2519,7 +2726,7 @@ NetLibAsciiStrToIp6 (
       return EFI_INVALID_PARAMETER;\r
     } else {\r
       AllowedCnt = 7;\r
-    }    \r
+    }\r
   }\r
 \r
   ZeroMem (Ip6Address, sizeof (EFI_IPv6_ADDRESS));\r
@@ -2547,7 +2754,7 @@ NetLibAsciiStrToIp6 (
           // ::0 looks strange. report error to user.\r
           //\r
           return EFI_INVALID_PARAMETER;\r
-        }           \r
+        }\r
 \r
         //\r
         // Skip the abbreviation part of IPv6 address.\r
@@ -2561,7 +2768,7 @@ NetLibAsciiStrToIp6 (
               //\r
               return EFI_INVALID_PARAMETER;\r
             }\r
-            \r
+\r
             TailNodeCnt++;\r
             if (TailNodeCnt >= (AllowedCnt - NodeCnt)) {\r
               //\r
@@ -2572,7 +2779,7 @@ NetLibAsciiStrToIp6 (
           }\r
 \r
           TempStr2++;\r
-        }       \r
+        }\r
 \r
         Short  = TRUE;\r
         Update = TRUE;\r
@@ -2587,12 +2794,12 @@ NetLibAsciiStrToIp6 (
           //\r
           return EFI_INVALID_PARAMETER;\r
         }\r
-      }      \r
-    }    \r
+      }\r
+    }\r
 \r
     //\r
     // Convert the string to IPv6 address. AsciiStrHexToUintn stops at the first\r
-    // character that is not a valid hexadecimal character, ':' or '\0' here. \r
+    // character that is not a valid hexadecimal character, ':' or '\0' here.\r
     //\r
     NodeVal = AsciiStrHexToUintn (TempStr);\r
     if ((NodeVal > 0xFFFF) || (Index > 14)) {\r
@@ -2625,7 +2832,7 @@ NetLibAsciiStrToIp6 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip4Address     The pointer to the converted IPv4 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv4 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv4 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip4Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
@@ -2638,7 +2845,7 @@ NetLibStrToIp4 (
 {\r
   CHAR8                          *Ip4Str;\r
   EFI_STATUS                     Status;\r
-  \r
+\r
   if ((String == NULL) || (Ip4Address == NULL)) {\r
     return EFI_INVALID_PARAMETER;\r
   }\r
@@ -2665,7 +2872,7 @@ NetLibStrToIp4 (
   @param[in]      String         The pointer to the Ascii string.\r
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
@@ -2674,11 +2881,11 @@ EFI_STATUS
 NetLibStrToIp6 (\r
   IN CONST CHAR16                *String,\r
   OUT      EFI_IPv6_ADDRESS      *Ip6Address\r
-  ) \r
+  )\r
 {\r
   CHAR8                          *Ip6Str;\r
   EFI_STATUS                     Status;\r
-  \r
+\r
   if ((String == NULL) || (Ip6Address == NULL)) {\r
     return EFI_INVALID_PARAMETER;\r
   }\r
@@ -2706,7 +2913,7 @@ NetLibStrToIp6 (
   @param[out]     Ip6Address     The pointer to the converted IPv6 address.\r
   @param[out]     PrefixLength   The pointer to the converted prefix length.\r
 \r
-  @retval EFI_SUCCESS            Convert to IPv6 address successfully.  \r
+  @retval EFI_SUCCESS            Convert to IPv6 address successfully.\r
   @retval EFI_INVALID_PARAMETER  The string is mal-formated or Ip6Address is NULL.\r
   @retval EFI_OUT_OF_RESOURCES   Fail to perform the operation due to lack of resource.\r
 \r
@@ -2716,14 +2923,14 @@ NetLibStrToIp6andPrefix (
   IN CONST CHAR16                *String,\r
   OUT      EFI_IPv6_ADDRESS      *Ip6Address,\r
   OUT      UINT8                 *PrefixLength\r
-  ) \r
+  )\r
 {\r
-  CHAR8                          *Ip6Str;  \r
+  CHAR8                          *Ip6Str;\r
   CHAR8                          *PrefixStr;\r
   CHAR8                          *TempStr;\r
   EFI_STATUS                     Status;\r
   UINT8                          Length;\r
-  \r
+\r
   if ((String == NULL) || (Ip6Address == NULL) || (PrefixLength == NULL)) {\r
     return EFI_INVALID_PARAMETER;\r
   }\r
index a0a53a4e33665cc160ad1a00d94f4eb9253e0cdb..f470844ee4d9930b975900cd3867290b1a41bc51 100644 (file)
@@ -770,6 +770,7 @@ ON_EXIT:
   @retval EFI_ALREADY_STARTED   Some other EFI DHCPv4 Protocol instance already started the\r
                                 DHCP process.\r
   @retval EFI_DEVICE_ERROR      An unexpected system or network error occurred.\r
+  @retval EFI_NO_MEDIA          There was a media error.\r
 \r
 **/\r
 EFI_STATUS\r
index 996a29061049eaf4102f6f5c82d25b2f3a2706bf..c770e27631dc93f6a49e98a0adc7a76d07fdd86c 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   iSCSI DHCP related configuration routines.\r
 \r
-Copyright (c) 2004 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2004 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -344,7 +344,9 @@ IScsiParseDhcpAck (
 \r
   @retval EFI_SUCCESS           The DNS information is got from the DHCP ACK.\r
   @retval EFI_OUT_OF_RESOURCES  Failed to allocate memory.\r
+  @retval EFI_NO_MEDIA          There was a media error.\r
   @retval Others                Other errors as indicated.\r
+\r
 **/\r
 EFI_STATUS\r
 IScsiDoDhcp (\r
@@ -358,11 +360,21 @@ IScsiDoDhcp (
   EFI_STATUS              Status;\r
   EFI_DHCP4_PACKET_OPTION *ParaList;\r
   EFI_DHCP4_CONFIG_DATA   Dhcp4ConfigData;\r
+  BOOLEAN                 MediaPresent;\r
 \r
   Dhcp4Handle = NULL;\r
   Dhcp4       = NULL;\r
   ParaList    = NULL;\r
 \r
+  //\r
+  // Check media status before do DHCP\r
+  //\r
+  MediaPresent = TRUE;\r
+  NetLibDetectMedia (Controller, &MediaPresent);\r
+  if (!MediaPresent) {\r
+    return EFI_NO_MEDIA;\r
+  }\r
+\r
   //\r
   // Create a DHCP4 child instance and get the protocol.\r
   //\r
index 07b30a936c6c87b01342907e23519f1c1492db0f..eefc5b37a8320b3fb48a1b6fea46f1fb19c05f14 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   The header file of IScsiDhcp.\r
 \r
-Copyright (c) 2004 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2004 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -47,7 +47,9 @@ typedef struct _ISCSI_ROOT_PATH_FIELD {
 \r
   @retval EFI_SUCCESS           The DNS information is got from the DHCP ACK.\r
   @retval EFI_OUT_OF_RESOURCES  Failed to allocate memory.\r
+  @retval EFI_NO_MEDIA          There was a media error.\r
   @retval Others                Other errors as indicated.\r
+\r
 **/\r
 EFI_STATUS\r
 IScsiDoDhcp (\r
index ac0d8d821f5d15521d415a0adedb41e7966f823f..2261bc17f0216cd3e018846d00c82b60c965cb00 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   The implementation of iSCSI protocol based on RFC3720.\r
 \r
-Copyright (c) 2004 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2004 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -276,7 +276,9 @@ IScsiDestroyConnection (
 \r
   @retval EFI_SUCCESS          The iSCSI session login procedure finished.\r
   @retval EFI_OUT_OF_RESOURCES Failed to allocate memory.\r
+  @retval EFI_NO_MEDIA         There was a media error.\r
   @retval Others               Other errors as indicated.\r
+\r
 **/\r
 EFI_STATUS\r
 IScsiSessionLogin (\r
@@ -287,9 +289,19 @@ IScsiSessionLogin (
   ISCSI_SESSION     *Session;\r
   ISCSI_CONNECTION  *Conn;\r
   EFI_TCP4_PROTOCOL *Tcp4;\r
+  BOOLEAN           MediaPresent;\r
 \r
   Session = &Private->Session;\r
 \r
+  //\r
+  // Check media status before session login\r
+  //\r
+  MediaPresent = TRUE;\r
+  NetLibDetectMedia (Private->Controller, &MediaPresent);\r
+  if (!MediaPresent) {\r
+    return EFI_NO_MEDIA;\r
+  }\r
+\r
   //\r
   // Create a connection for the session.\r
   //\r
index 93fe2af5b76198ff7a5efea3b2eae145f686b016..e11565e3015dd6b6cdd517d06218a55f99274178 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   The header file of iSCSI Protocol that defines many specific data structures.\r
 \r
-Copyright (c) 2004 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2004 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -692,7 +692,9 @@ IScsiDestroyConnection (
 \r
   @retval EFI_SUCCESS          The iSCSI session login procedure finished.\r
   @retval EFI_OUT_OF_RESOURCES Failed to allocate memory.\r
+  @retval EFI_NO_MEDIA         There was a media error.\r
   @retval Others               Other errors as indicated.\r
+\r
 **/\r
 EFI_STATUS\r
 IScsiSessionLogin (\r
index ec545a6c542e9e8d9a80a97360b6f057973c4c09..06358f06ef46ce26e882f755f8e51e387cbaeeda 100644 (file)
@@ -440,16 +440,13 @@ EfiIp4GetModeData (
     }\r
   }\r
 \r
-  if (MnpConfigData != NULL) {\r
-    CopyMem (MnpConfigData, &IpSb->MnpConfigData, sizeof (*MnpConfigData));\r
-  }\r
-\r
-  if (SnpModeData != NULL) {\r
-    CopyMem (SnpModeData, &IpSb->SnpMode, sizeof (*SnpModeData));\r
-  }\r
+  //\r
+  // Get fresh mode data from MNP, since underlying media status may change\r
+  //\r
+  Status = IpSb->Mnp->GetModeData (IpSb->Mnp, MnpConfigData, SnpModeData);\r
 \r
   gBS->RestoreTPL (OldTpl);\r
-  return EFI_SUCCESS;\r
+  return Status;\r
 }\r
 \r
 \r
index af642a50d9ff4092c206e6255214e7fe83e7c13e..115185afe246b4150796659a7ad5dd115f8d6260 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Implementation of Managed Network Protocol private services.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -355,6 +355,22 @@ MnpInitializeDeviceData (
     goto ERROR;\r
   }\r
 \r
+  //\r
+  // Create the timer for media detection.\r
+  //\r
+  Status = gBS->CreateEvent (\r
+                  EVT_NOTIFY_SIGNAL | EVT_TIMER,\r
+                  TPL_CALLBACK,\r
+                  MnpCheckMediaStatus,\r
+                  MnpDeviceData,\r
+                  &MnpDeviceData->MediaDetectTimer\r
+                  );\r
+  if (EFI_ERROR (Status)) {\r
+    DEBUG ((EFI_D_ERROR, "MnpInitializeDeviceData: CreateEvent for media detection failed.\n"));\r
+\r
+    goto ERROR;\r
+  }\r
+\r
   //\r
   // Create the timer for tx timeout check.\r
   //\r
@@ -382,6 +398,10 @@ ERROR:
       gBS->CloseEvent (MnpDeviceData->TimeoutCheckTimer);\r
     }\r
 \r
+    if (MnpDeviceData->MediaDetectTimer != NULL) {\r
+      gBS->CloseEvent (MnpDeviceData->MediaDetectTimer);\r
+    }\r
+\r
     if (MnpDeviceData->PollTimer != NULL) {\r
       gBS->CloseEvent (MnpDeviceData->PollTimer);\r
     }\r
@@ -443,9 +463,10 @@ MnpDestroyDeviceData (
   //\r
   // Close the event.\r
   //\r
-  gBS->CloseEvent (&MnpDeviceData->TxTimeoutEvent);\r
-  gBS->CloseEvent (&MnpDeviceData->TimeoutCheckTimer);\r
-  gBS->CloseEvent (&MnpDeviceData->PollTimer);\r
+  gBS->CloseEvent (MnpDeviceData->TxTimeoutEvent);\r
+  gBS->CloseEvent (MnpDeviceData->TimeoutCheckTimer);\r
+  gBS->CloseEvent (MnpDeviceData->MediaDetectTimer);\r
+  gBS->CloseEvent (MnpDeviceData->PollTimer);\r
 \r
   //\r
   // Free the tx buffer.\r
@@ -1010,6 +1031,24 @@ MnpStart (
 \r
         goto ErrorExit;\r
       }\r
+\r
+      //\r
+      // Start the media detection timer.\r
+      //\r
+      Status = gBS->SetTimer (\r
+                      MnpDeviceData->MediaDetectTimer,\r
+                      TimerPeriodic,\r
+                      MNP_MEDIA_DETECT_INTERVAL\r
+                      );\r
+      if (EFI_ERROR (Status)) {\r
+        DEBUG (\r
+          (EFI_D_ERROR,\r
+          "MnpStart, gBS->SetTimer for MediaDetectTimer %r.\n",\r
+          Status)\r
+          );\r
+\r
+        goto ErrorExit;\r
+      }\r
     }\r
   }\r
 \r
@@ -1095,6 +1134,11 @@ MnpStop (
   //\r
   Status = gBS->SetTimer (MnpDeviceData->TimeoutCheckTimer, TimerCancel, 0);\r
 \r
+  //\r
+  // Cancel the media detect timer.\r
+  //\r
+  Status = gBS->SetTimer (MnpDeviceData->MediaDetectTimer, TimerCancel, 0);\r
+\r
   //\r
   // Stop the simple network.\r
   //\r
index e3abd48cf393072fff81e4d2388f7e4fdd2bb68f..d2d5924c776907389ba8081a7d783c554b61646f 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Implementation of driver entry point and driver binding protocol.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -336,7 +336,7 @@ MnpDriverBindingStop (
     }\r
 \r
     //\r
-    // Destroy the Mnp device data\r
+    // Destroy Mnp Device Data\r
     //\r
     MnpDestroyDeviceData (MnpDeviceData, This->DriverBindingHandle);\r
     FreePool (MnpDeviceData);\r
index e9698d2aacd8c0ad70d083875da0589e2222b27f..d410af2726ac82ad07fc611a36d04d7ea1bc5c7d 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Declaration of strctures and functions for MnpDxe driver.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -70,6 +70,7 @@ typedef struct {
   BOOLEAN                       EnableSystemPoll;\r
 \r
   EFI_EVENT                     TimeoutCheckTimer;\r
+  EFI_EVENT                     MediaDetectTimer;\r
 \r
   UINT32                        UnicastCount;\r
   UINT32                        BroadcastCount;\r
index d35086221e0956eb3adba35fa2201e2e353b41e9..54a61c39612b31aa745e3e3af493c933b8fe1ff4 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Declaration of structures and functions of MnpDxe driver.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -22,6 +22,7 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
 \r
 #define MNP_SYS_POLL_INTERVAL         (10 * TICKS_PER_MS)   // 10 milliseconds\r
 #define MNP_TIMEOUT_CHECK_INTERVAL    (50 * TICKS_PER_MS)   // 50 milliseconds\r
+#define MNP_MEDIA_DETECT_INTERVAL     (500 * TICKS_PER_MS)  // 500 milliseconds\r
 #define MNP_TX_TIMEOUT_TIME           (500 * TICKS_PER_MS)  // 500 milliseconds\r
 #define MNP_INIT_NET_BUFFER_NUM       512\r
 #define MNP_NET_BUFFER_INCREASEMENT   64\r
@@ -448,9 +449,8 @@ MnpFreeNbuf (
 /**\r
   Remove the received packets if timeout occurs.\r
 \r
-  @param[in]  Event             The event this notify function registered to.\r
-  @param[in]  Context           Pointer to the context data registered to the\r
-                                event.\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
 \r
 **/\r
 VOID\r
@@ -460,19 +460,33 @@ MnpCheckPacketTimeout (
   IN VOID          *Context\r
   );\r
 \r
+/**\r
+  Poll to update MediaPresent field in SNP ModeData by Snp.GetStatus().\r
+\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
+\r
+**/\r
+VOID\r
+EFIAPI\r
+MnpCheckMediaStatus (\r
+  IN EFI_EVENT     Event,\r
+  IN VOID          *Context\r
+  );\r
+\r
 /**\r
   Poll to receive the packets from Snp. This function is either called by upperlayer\r
   protocols/applications or the system poll timer notify mechanism.\r
 \r
-  @param[in]       Event        The event this notify function registered to.\r
-  @param[in, out]  Context      Pointer to the context data registered to the event.\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
 \r
 **/\r
 VOID\r
 EFIAPI\r
 MnpSystemPoll (\r
-  IN     EFI_EVENT   Event,\r
-  IN OUT VOID        *Context\r
+  IN EFI_EVENT     Event,\r
+  IN VOID          *Context\r
   );\r
 \r
 /**\r
index 65268a8d74202419a069b8463038ce0bb537d205..32cffd5730be524f1706e3eff1c8fa61dcf97aa0 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Implementation of Managed Network Protocol I/O functions.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -210,6 +210,18 @@ MnpSyncSendPacket (
 \r
   HeaderSize    = Snp->Mode->MediaHeaderSize - TxData->HeaderLength;\r
 \r
+  //\r
+  // Check media status before transmit packet.\r
+  // Note: media status will be updated by periodic timer MediaDetectTimer.\r
+  //\r
+  if (!Snp->Mode->MediaPresent) {\r
+    //\r
+    // Media not present, skip packet transmit and report EFI_NO_MEDIA\r
+    //\r
+    Status = EFI_NO_MEDIA;\r
+    goto SIGNAL_TOKEN;\r
+  }\r
+\r
   //\r
   // Start the timeout event.\r
   //\r
@@ -998,9 +1010,8 @@ EXIT:
 /**\r
   Remove the received packets if timeout occurs.\r
 \r
-  @param[in]  Event             The event this notify function registered to.\r
-  @param[in]  Context           Pointer to the context data registered to the\r
-                                event.\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
 \r
 **/\r
 VOID\r
@@ -1065,19 +1076,50 @@ MnpCheckPacketTimeout (
   }\r
 }\r
 \r
+/**\r
+  Poll to update MediaPresent field in SNP ModeData by Snp->GetStatus().\r
+\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
+\r
+**/\r
+VOID\r
+EFIAPI\r
+MnpCheckMediaStatus (\r
+  IN EFI_EVENT     Event,\r
+  IN VOID          *Context\r
+  )\r
+{\r
+  MNP_DEVICE_DATA             *MnpDeviceData;\r
+  EFI_SIMPLE_NETWORK_PROTOCOL *Snp;\r
+  UINT32                      InterruptStatus;\r
+\r
+  MnpDeviceData = (MNP_DEVICE_DATA *) Context;\r
+  NET_CHECK_SIGNATURE (MnpDeviceData, MNP_DEVICE_DATA_SIGNATURE);\r
+\r
+  Snp = MnpDeviceData->Snp;\r
+  if (Snp->Mode->MediaPresentSupported) {\r
+    //\r
+    // Upon successful return of GetStatus(), the MediaPresent field of\r
+    // EFI_SIMPLE_NETWORK_MODE will be updated to reflect any change of media status\r
+    //\r
+    Snp->GetStatus (Snp, &InterruptStatus, NULL);\r
+  }\r
+}\r
+\r
 /**\r
   Poll to receive the packets from Snp. This function is either called by upperlayer\r
   protocols/applications or the system poll timer notify mechanism.\r
 \r
-  @param[in]       Event        The event this notify function registered to.\r
-  @param[in, out]  Context      Pointer to the context data registered to the event.\r
+  @param[in]  Event        The event this notify function registered to.\r
+  @param[in]  Context      Pointer to the context data registered to the event.\r
 \r
 **/\r
 VOID\r
 EFIAPI\r
 MnpSystemPoll (\r
-  IN     EFI_EVENT   Event,\r
-  IN OUT VOID        *Context\r
+  IN EFI_EVENT     Event,\r
+  IN VOID          *Context\r
   )\r
 {\r
   MNP_DEVICE_DATA  *MnpDeviceData;\r
index e34936f3b861c0736f423bef7d8c3897e64f6770..1f7b1e6bf067dd9fe0722c6df71a0177e46492b0 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Implementation of Managed Network Protocol public services.\r
 \r
-Copyright (c) 2005 - 2009, Intel Corporation.<BR>\r
+Copyright (c) 2005 - 2010, Intel Corporation.<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 of the BSD License which accompanies this distribution.  The full\r
@@ -52,6 +52,7 @@ MnpGetModeData (
   EFI_SIMPLE_NETWORK_PROTOCOL *Snp;\r
   EFI_TPL                     OldTpl;\r
   EFI_STATUS                  Status;\r
+  UINT32                      InterruptStatus;\r
 \r
   if (This == NULL) {\r
     return EFI_INVALID_PARAMETER;\r
@@ -73,6 +74,12 @@ MnpGetModeData (
     // Copy the underlayer Snp mode data.\r
     //\r
     Snp = Instance->MnpServiceData->MnpDeviceData->Snp;\r
+\r
+    //\r
+    // Upon successful return of GetStatus(), the Snp->Mode->MediaPresent\r
+    // will be updated to reflect any change of media status\r
+    //\r
+    Snp->GetStatus (Snp, &InterruptStatus, NULL);\r
     CopyMem (SnpModeData, Snp->Mode, sizeof (*SnpModeData));\r
   }\r
 \r
index 3d92ba3dd172c4974737f3dabf1f747075f5e5ac..8652ba525651234afd5f9fe4c9b2b9b084172e43 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Interface routine for Mtftp4.\r
   \r
-Copyright (c) 2006 - 2009, Intel Corporation<BR>\r
+Copyright (c) 2006 - 2010, Intel Corporation<BR>\r
 All rights reserved. This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -776,6 +776,7 @@ EfiMtftp4ParseOptions (
   @retval EFI_TIMEOUT           No responses were received from the MTFTPv4 server.\r
   @retval EFI_TFTP_ERROR        An MTFTPv4 ERROR packet was received.\r
   @retval EFI_DEVICE_ERROR      An unexpected network error or system error occurred.\r
+  @retval EFI_NO_MEDIA          There was a media error.\r
 \r
 **/\r
 EFI_STATUS\r
@@ -971,7 +972,8 @@ EfiMtftp4ReadDirectory (
                                  in the Buffer.\r
   @retval EFI_TIMEOUT            No responses were received from the MTFTPv4 server.\r
   @retval EFI_DEVICE_ERROR       An unexpected network error or system error occurred.\r
-  \r
+  @retval EFI_NO_MEDIA           There was a media error.\r
+\r
 **/\r
 EFI_STATUS\r
 EFIAPI\r
index df9d2df5be2ad76c4b9d6c6e2540101528aed2fb..f0fc48f8ac29371bef06f0bf44bee052dd4a015e 100644 (file)
@@ -2585,6 +2585,7 @@ EfiPxeLoadFile (
   BOOLEAN                     NewMakeCallback;\r
   EFI_STATUS                  Status;\r
   UINT64                      TmpBufSize;\r
+  BOOLEAN                     MediaPresent;\r
 \r
   Private         = PXEBC_PRIVATE_DATA_FROM_LOADFILE (This);\r
   PxeBc           = &Private->PxeBc;\r
@@ -2603,6 +2604,15 @@ EfiPxeLoadFile (
     return EFI_UNSUPPORTED;\r
   }\r
 \r
+  //\r
+  // Check media status before PXE start\r
+  //\r
+  MediaPresent = TRUE;\r
+  NetLibDetectMedia (Private->Controller, &MediaPresent);\r
+  if (!MediaPresent) {\r
+    return EFI_NO_MEDIA;\r
+  }\r
+\r
   Status = PxeBc->Start (PxeBc, FALSE);\r
   if (EFI_ERROR (Status) && (Status != EFI_ALREADY_STARTED)) {\r
     return Status;\r