mirror of
				https://git.proxmox.com/git/mirror_edk2
				synced 2025-11-04 10:19:50 +00:00 
			
		
		
		
	Since new Api NetLibDetectMediaWaitTimeout was involved to support connecting state handling, and it is forward compatible. So apply this Api in ShellPkg. V2: *Define time period in a macro instead of hard code. Cc: Ye Ting <ting.ye@intel.com> Cc: Fu Siyuan <siyuan.fu@intel.com> Cc: Wu Jiaxin <jiaxin.wu@intel.com> Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Wang Fan <fan.wang@intel.com> Reviewed-by: Fu Siyuan <siyuan.fu@intel.com> Signed-off-by: fanwang2 <fan.wang@intel.com>
		
			
				
	
	
		
			1447 lines
		
	
	
		
			40 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			1447 lines
		
	
	
		
			40 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
/** @file
 | 
						|
  The implementation for Shell command ifconfig based on IP4Config2 protocol.
 | 
						|
 | 
						|
  (C) Copyright 2013-2015 Hewlett-Packard Development Company, L.P.<BR>
 | 
						|
  Copyright (c) 2006 - 2017, Intel Corporation. All rights reserved.<BR>
 | 
						|
 | 
						|
  This program and the accompanying materials
 | 
						|
  are licensed and made available under the terms and conditions of the BSD License
 | 
						|
  which accompanies this distribution.  The full text of the license may be found at
 | 
						|
  http://opensource.org/licenses/bsd-license.php.
 | 
						|
 | 
						|
  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
 | 
						|
  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
 | 
						|
 | 
						|
**/
 | 
						|
 | 
						|
#include "UefiShellNetwork1CommandsLib.h"
 | 
						|
 | 
						|
typedef enum {
 | 
						|
  IfConfigOpList     = 1,
 | 
						|
  IfConfigOpSet      = 2,
 | 
						|
  IfConfigOpClear    = 3
 | 
						|
} IFCONFIG_OPCODE;
 | 
						|
 | 
						|
typedef enum {
 | 
						|
  VarCheckReserved      = -1,
 | 
						|
  VarCheckOk            = 0,
 | 
						|
  VarCheckDuplicate,
 | 
						|
  VarCheckConflict,
 | 
						|
  VarCheckUnknown,
 | 
						|
  VarCheckLackValue,
 | 
						|
  VarCheckOutOfMem
 | 
						|
} VAR_CHECK_CODE;
 | 
						|
 | 
						|
typedef enum {
 | 
						|
  FlagTypeSingle         = 0,
 | 
						|
  FlagTypeNeedVar,
 | 
						|
  FlagTypeNeedSet,
 | 
						|
  FlagTypeSkipUnknown
 | 
						|
} VAR_CHECK_FLAG_TYPE;
 | 
						|
 | 
						|
#define MACADDRMAXSIZE    32
 | 
						|
 | 
						|
typedef struct _IFCONFIG_INTERFACE_CB {
 | 
						|
  EFI_HANDLE                                  NicHandle;
 | 
						|
  LIST_ENTRY                                  Link;
 | 
						|
  EFI_IP4_CONFIG2_PROTOCOL                    *IfCfg;
 | 
						|
  EFI_IP4_CONFIG2_INTERFACE_INFO              *IfInfo; 
 | 
						|
  EFI_IP4_CONFIG2_POLICY                      Policy;
 | 
						|
  UINT32                                      DnsCnt;
 | 
						|
  EFI_IPv4_ADDRESS                            DnsAddr[1];
 | 
						|
} IFCONFIG_INTERFACE_CB;
 | 
						|
 | 
						|
typedef struct _ARG_LIST ARG_LIST;
 | 
						|
 | 
						|
struct _ARG_LIST {
 | 
						|
  ARG_LIST    *Next;
 | 
						|
  CHAR16      *Arg;
 | 
						|
};
 | 
						|
 | 
						|
typedef struct _IFCONFIG4_PRIVATE_DATA {
 | 
						|
  LIST_ENTRY  IfList;
 | 
						|
 | 
						|
  UINT32      OpCode;
 | 
						|
  CHAR16      *IfName;
 | 
						|
  ARG_LIST    *VarArg;
 | 
						|
} IFCONFIG_PRIVATE_DATA;
 | 
						|
 | 
						|
typedef struct _VAR_CHECK_ITEM{
 | 
						|
  CHAR16                 *FlagStr;
 | 
						|
  UINT32                 FlagID;
 | 
						|
  UINT32                 ConflictMask;
 | 
						|
  VAR_CHECK_FLAG_TYPE    FlagType;
 | 
						|
} VAR_CHECK_ITEM;
 | 
						|
 | 
						|
SHELL_PARAM_ITEM    mIfConfigCheckList[] = {
 | 
						|
  {
 | 
						|
    L"-b",
 | 
						|
    TypeFlag
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"-l",
 | 
						|
    TypeValue
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"-r",
 | 
						|
    TypeValue
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"-c",
 | 
						|
    TypeValue
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"-s",
 | 
						|
    TypeMaxValue
 | 
						|
  },
 | 
						|
  {
 | 
						|
    NULL,
 | 
						|
    TypeMax
 | 
						|
  },
 | 
						|
};
 | 
						|
 | 
						|
VAR_CHECK_ITEM  mSetCheckList[] = {
 | 
						|
  {
 | 
						|
   L"static",
 | 
						|
    0x00000001,
 | 
						|
    0x00000001,
 | 
						|
    FlagTypeSingle
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"dhcp",
 | 
						|
    0x00000002,
 | 
						|
    0x00000001,
 | 
						|
    FlagTypeSingle
 | 
						|
  },
 | 
						|
  {
 | 
						|
    L"dns",
 | 
						|
    0x00000008,
 | 
						|
    0x00000004,
 | 
						|
    FlagTypeSingle
 | 
						|
  },
 | 
						|
  {
 | 
						|
    NULL,
 | 
						|
    0x0,
 | 
						|
    0x0,
 | 
						|
    FlagTypeSkipUnknown
 | 
						|
  },
 | 
						|
};
 | 
						|
 | 
						|
STATIC CONST CHAR16 PermanentString[10] = L"PERMANENT";
 | 
						|
 | 
						|
/**
 | 
						|
  Free the ARG_LIST.
 | 
						|
 | 
						|
  @param List Pointer to ARG_LIST to free.
 | 
						|
**/
 | 
						|
VOID
 | 
						|
FreeArgList (
 | 
						|
  ARG_LIST       *List
 | 
						|
)
 | 
						|
{
 | 
						|
  ARG_LIST       *Next;
 | 
						|
  while (List->Next != NULL) {
 | 
						|
    Next = List->Next;
 | 
						|
    FreePool (List);
 | 
						|
    List = Next;
 | 
						|
  }
 | 
						|
 | 
						|
  FreePool (List);
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  Split a string with specified separator and save the substring to a list.
 | 
						|
 | 
						|
  @param[in]    String       The pointer of the input string.
 | 
						|
  @param[in]    Separator    The specified separator.
 | 
						|
 | 
						|
  @return The pointer of headnode of ARG_LIST.
 | 
						|
 | 
						|
**/
 | 
						|
ARG_LIST *
 | 
						|
SplitStrToList (
 | 
						|
  IN CONST CHAR16    *String,
 | 
						|
  IN CHAR16          Separator
 | 
						|
  )
 | 
						|
{
 | 
						|
  CHAR16      *Str;
 | 
						|
  CHAR16      *ArgStr;
 | 
						|
  ARG_LIST    *ArgList;
 | 
						|
  ARG_LIST    *ArgNode;
 | 
						|
 | 
						|
  if (*String == L'\0') {
 | 
						|
    return NULL;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Copy the CONST string to a local copy.
 | 
						|
  //
 | 
						|
  Str = AllocateCopyPool (StrSize (String), String);
 | 
						|
  if (Str == NULL) {
 | 
						|
    return NULL;
 | 
						|
  }
 | 
						|
  ArgStr  = Str;
 | 
						|
 | 
						|
  //
 | 
						|
  // init a node for the list head.
 | 
						|
  //
 | 
						|
  ArgNode = (ARG_LIST *) AllocateZeroPool (sizeof (ARG_LIST));
 | 
						|
  if (ArgNode == NULL) {
 | 
						|
    return NULL;
 | 
						|
  }
 | 
						|
  ArgList = ArgNode;
 | 
						|
 | 
						|
  //
 | 
						|
  // Split the local copy and save in the list node.
 | 
						|
  //
 | 
						|
  while (*Str != L'\0') {
 | 
						|
    if (*Str == Separator) {
 | 
						|
      *Str          = L'\0';
 | 
						|
      ArgNode->Arg  = ArgStr;
 | 
						|
      ArgStr        = Str + 1;
 | 
						|
      ArgNode->Next = (ARG_LIST *) AllocateZeroPool (sizeof (ARG_LIST));
 | 
						|
      if (ArgNode->Next == NULL) {
 | 
						|
        //
 | 
						|
        // Free the local copy of string stored in the first node
 | 
						|
        //
 | 
						|
        FreePool (ArgList->Arg);
 | 
						|
        FreeArgList (ArgList);
 | 
						|
        return NULL;
 | 
						|
      }
 | 
						|
      ArgNode = ArgNode->Next;
 | 
						|
    }
 | 
						|
 | 
						|
    Str++;
 | 
						|
  }
 | 
						|
 | 
						|
  ArgNode->Arg  = ArgStr;
 | 
						|
  ArgNode->Next = NULL;
 | 
						|
 | 
						|
  return ArgList;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  Check the correctness of input Args with '-s' option.
 | 
						|
 | 
						|
  @param[in]    CheckList    The pointer of VAR_CHECK_ITEM array.
 | 
						|
  @param[in]    Name         The pointer of input arg.
 | 
						|
  @param[in]    Init         The switch to execute the check.
 | 
						|
 | 
						|
  @return   VarCheckOk          Valid parameter or Initialize check successfully.
 | 
						|
  @return   VarCheckDuplicate   Duplicated parameter happened.
 | 
						|
  @return   VarCheckConflict    Conflicted parameter happened
 | 
						|
  @return   VarCheckUnknown     Unknown parameter.
 | 
						|
 | 
						|
**/
 | 
						|
VAR_CHECK_CODE
 | 
						|
IfConfigRetriveCheckListByName(
 | 
						|
  IN VAR_CHECK_ITEM    *CheckList,
 | 
						|
  IN CHAR16            *Name,
 | 
						|
  IN BOOLEAN           Init
 | 
						|
)
 | 
						|
{
 | 
						|
  STATIC UINT32     CheckDuplicate;
 | 
						|
  STATIC UINT32     CheckConflict;
 | 
						|
  VAR_CHECK_CODE    RtCode;
 | 
						|
  UINT32            Index;
 | 
						|
  VAR_CHECK_ITEM    Arg;
 | 
						|
 | 
						|
  if (Init) {
 | 
						|
    CheckDuplicate = 0;
 | 
						|
    CheckConflict  = 0;
 | 
						|
    return VarCheckOk;
 | 
						|
  }
 | 
						|
 | 
						|
  RtCode  = VarCheckOk;
 | 
						|
  Index   = 0;
 | 
						|
  Arg     = CheckList[Index];
 | 
						|
 | 
						|
  //
 | 
						|
  // Check the Duplicated/Conflicted/Unknown input Args.
 | 
						|
  //
 | 
						|
  while (Arg.FlagStr != NULL) {
 | 
						|
    if (StrCmp (Arg.FlagStr, Name) == 0) {
 | 
						|
 | 
						|
      if (CheckDuplicate & Arg.FlagID) {
 | 
						|
        RtCode = VarCheckDuplicate;
 | 
						|
        break;
 | 
						|
      }
 | 
						|
 | 
						|
      if (CheckConflict & Arg.ConflictMask) {
 | 
						|
        RtCode = VarCheckConflict;
 | 
						|
        break;
 | 
						|
      }
 | 
						|
 | 
						|
      CheckDuplicate |= Arg.FlagID;
 | 
						|
      CheckConflict  |= Arg.ConflictMask;
 | 
						|
      break;
 | 
						|
    }
 | 
						|
 | 
						|
    Arg = CheckList[++Index];
 | 
						|
  }
 | 
						|
 | 
						|
  if (Arg.FlagStr == NULL) {
 | 
						|
    RtCode = VarCheckUnknown;
 | 
						|
  }
 | 
						|
 | 
						|
  return RtCode;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The notify function of create event when performing a manual config.
 | 
						|
 | 
						|
  @param[in]    Event        The event this notify function registered to.
 | 
						|
  @param[in]    Context      Pointer to the context data registered to the event.
 | 
						|
 | 
						|
**/
 | 
						|
VOID
 | 
						|
EFIAPI
 | 
						|
IfConfigManualAddressNotify (
 | 
						|
  IN EFI_EVENT    Event,
 | 
						|
  IN VOID         *Context
 | 
						|
  )
 | 
						|
{
 | 
						|
  *((BOOLEAN *) Context) = TRUE;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  Print MAC address.
 | 
						|
 | 
						|
  @param[in]    Node    The pointer of MAC address buffer.
 | 
						|
  @param[in]    Size    The size of MAC address buffer.
 | 
						|
 | 
						|
**/
 | 
						|
VOID
 | 
						|
IfConfigPrintMacAddr (
 | 
						|
  IN UINT8     *Node,
 | 
						|
  IN UINT32    Size
 | 
						|
  )
 | 
						|
{
 | 
						|
  UINTN    Index;
 | 
						|
 | 
						|
  ASSERT (Size <= MACADDRMAXSIZE);
 | 
						|
 | 
						|
  for (Index = 0; Index < Size; Index++) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_MAC_ADDR_BODY), gShellNetwork1HiiHandle, Node[Index]);
 | 
						|
    if (Index + 1 < Size) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_COLON), gShellNetwork1HiiHandle);
 | 
						|
    }
 | 
						|
  }
 | 
						|
 | 
						|
  ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_NEWLINE), gShellNetwork1HiiHandle);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
/**
 | 
						|
  The get current status of all handles.
 | 
						|
 | 
						|
  @param[in]   IfName         The pointer of IfName(interface name).
 | 
						|
  @param[in]   IfList         The pointer of IfList(interface list).
 | 
						|
 | 
						|
  @retval EFI_SUCCESS    The get status processed successfully.
 | 
						|
  @retval others         The get status process failed.
 | 
						|
 | 
						|
**/
 | 
						|
EFI_STATUS
 | 
						|
IfConfigGetInterfaceInfo (
 | 
						|
  IN CHAR16        *IfName,
 | 
						|
  IN LIST_ENTRY    *IfList
 | 
						|
  )
 | 
						|
{
 | 
						|
  EFI_STATUS                       Status;
 | 
						|
  UINTN                            HandleIndex;
 | 
						|
  UINTN                            HandleNum;
 | 
						|
  EFI_HANDLE                       *HandleBuffer;
 | 
						|
  EFI_IP4_CONFIG2_PROTOCOL         *Ip4Cfg2;
 | 
						|
  EFI_IP4_CONFIG2_INTERFACE_INFO   *IfInfo;
 | 
						|
  IFCONFIG_INTERFACE_CB            *IfCb;
 | 
						|
  UINTN                            DataSize;
 | 
						|
 | 
						|
  HandleBuffer = NULL;
 | 
						|
  HandleNum    = 0;
 | 
						|
 | 
						|
  IfInfo       = NULL;
 | 
						|
  IfCb         = NULL;
 | 
						|
 | 
						|
  //
 | 
						|
  // Locate all the handles with ip4 service binding protocol.
 | 
						|
  //
 | 
						|
  Status = gBS->LocateHandleBuffer (
 | 
						|
                  ByProtocol,
 | 
						|
                  &gEfiIp4ServiceBindingProtocolGuid,
 | 
						|
                  NULL,
 | 
						|
                  &HandleNum,
 | 
						|
                  &HandleBuffer
 | 
						|
                 );
 | 
						|
  if (EFI_ERROR (Status) || (HandleNum == 0)) {
 | 
						|
    return Status;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Enumerate all handles that installed with ip4 service binding protocol.
 | 
						|
  //
 | 
						|
  for (HandleIndex = 0; HandleIndex < HandleNum; HandleIndex++) {
 | 
						|
    IfCb      = NULL;
 | 
						|
    IfInfo    = NULL;
 | 
						|
    DataSize  = 0;
 | 
						|
 | 
						|
    //
 | 
						|
    // Ip4config protocol and ip4 service binding protocol are installed
 | 
						|
    // on the same handle.
 | 
						|
    //
 | 
						|
    ASSERT (HandleBuffer != NULL);
 | 
						|
    Status = gBS->HandleProtocol (
 | 
						|
                    HandleBuffer[HandleIndex],
 | 
						|
                    &gEfiIp4Config2ProtocolGuid,
 | 
						|
                    (VOID **) &Ip4Cfg2
 | 
						|
                    );
 | 
						|
 | 
						|
    if (EFI_ERROR (Status)) {
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
    
 | 
						|
    //
 | 
						|
    // Get the interface information size.
 | 
						|
    //
 | 
						|
    Status = Ip4Cfg2->GetData (
 | 
						|
                       Ip4Cfg2,
 | 
						|
                       Ip4Config2DataTypeInterfaceInfo,
 | 
						|
                       &DataSize,
 | 
						|
                       NULL
 | 
						|
                       );
 | 
						|
 | 
						|
    if (Status != EFI_BUFFER_TOO_SMALL) {
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
 | 
						|
    IfInfo = AllocateZeroPool (DataSize);
 | 
						|
 | 
						|
    if (IfInfo == NULL) {
 | 
						|
      Status = EFI_OUT_OF_RESOURCES;
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
    
 | 
						|
    //
 | 
						|
    // Get the interface info.
 | 
						|
    //
 | 
						|
    Status = Ip4Cfg2->GetData (
 | 
						|
                       Ip4Cfg2,
 | 
						|
                       Ip4Config2DataTypeInterfaceInfo,
 | 
						|
                       &DataSize,
 | 
						|
                       IfInfo
 | 
						|
                       );
 | 
						|
 | 
						|
    if (EFI_ERROR (Status)) {
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
    
 | 
						|
    //
 | 
						|
    // Check the interface name if required.
 | 
						|
    //
 | 
						|
    if ((IfName != NULL) && (StrCmp (IfName, IfInfo->Name) != 0)) {
 | 
						|
      FreePool (IfInfo);
 | 
						|
      continue;
 | 
						|
    }
 | 
						|
 | 
						|
    DataSize = 0;
 | 
						|
    
 | 
						|
    //
 | 
						|
    // Get the size of dns server list.
 | 
						|
    //
 | 
						|
    Status = Ip4Cfg2->GetData (
 | 
						|
                       Ip4Cfg2,
 | 
						|
                       Ip4Config2DataTypeDnsServer,
 | 
						|
                       &DataSize,
 | 
						|
                       NULL
 | 
						|
                       );
 | 
						|
 | 
						|
    if ((Status != EFI_BUFFER_TOO_SMALL) && (Status != EFI_NOT_FOUND)) {
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
 | 
						|
    IfCb = AllocateZeroPool (sizeof (IFCONFIG_INTERFACE_CB) + DataSize);
 | 
						|
 | 
						|
    if (IfCb == NULL) {
 | 
						|
      Status = EFI_OUT_OF_RESOURCES;
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
 | 
						|
    IfCb->NicHandle = HandleBuffer[HandleIndex];
 | 
						|
    IfCb->IfInfo    = IfInfo;
 | 
						|
    IfCb->IfCfg     = Ip4Cfg2;
 | 
						|
    IfCb->DnsCnt    = (UINT32) (DataSize / sizeof (EFI_IPv4_ADDRESS));
 | 
						|
 | 
						|
    //
 | 
						|
    // Get the dns server list if has.
 | 
						|
    //
 | 
						|
    if (DataSize > 0) {
 | 
						|
      Status = Ip4Cfg2->GetData (
 | 
						|
                         Ip4Cfg2,
 | 
						|
                         Ip4Config2DataTypeDnsServer,
 | 
						|
                         &DataSize,
 | 
						|
                         IfCb->DnsAddr
 | 
						|
                         );
 | 
						|
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        goto ON_ERROR;
 | 
						|
      }
 | 
						|
    }
 | 
						|
 | 
						|
    //
 | 
						|
    // Get the config policy.
 | 
						|
    //
 | 
						|
    DataSize = sizeof (EFI_IP4_CONFIG2_POLICY);
 | 
						|
    Status   = Ip4Cfg2->GetData (
 | 
						|
                         Ip4Cfg2,
 | 
						|
                         Ip4Config2DataTypePolicy,
 | 
						|
                         &DataSize,
 | 
						|
                         &IfCb->Policy
 | 
						|
                         );
 | 
						|
 | 
						|
    if (EFI_ERROR (Status)) {
 | 
						|
      goto ON_ERROR;
 | 
						|
    }
 | 
						|
 | 
						|
    InsertTailList (IfList, &IfCb->Link);
 | 
						|
 | 
						|
    if ((IfName != NULL) && (StrCmp (IfName, IfInfo->Name) == 0)) {
 | 
						|
      //
 | 
						|
      // Only need the appointed interface, keep the allocated buffer.
 | 
						|
      //
 | 
						|
      IfCb   = NULL;
 | 
						|
      IfInfo = NULL;
 | 
						|
      break;
 | 
						|
    }
 | 
						|
  }
 | 
						|
 | 
						|
  if (HandleBuffer != NULL) {
 | 
						|
    FreePool (HandleBuffer);
 | 
						|
  }
 | 
						|
 | 
						|
  return EFI_SUCCESS;
 | 
						|
 | 
						|
ON_ERROR:
 | 
						|
 | 
						|
  if (IfInfo != NULL) {
 | 
						|
    FreePool (IfInfo);
 | 
						|
  }
 | 
						|
 | 
						|
  if (IfCb != NULL) {
 | 
						|
    FreePool (IfCb);
 | 
						|
  }
 | 
						|
 | 
						|
  return Status;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The list process of the ifconfig command.
 | 
						|
 | 
						|
  @param[in]   IfList    The pointer of IfList(interface list).
 | 
						|
 | 
						|
  @retval SHELL_SUCCESS  The ifconfig command list processed successfully.
 | 
						|
  @retval others         The ifconfig command list process failed.
 | 
						|
 | 
						|
**/
 | 
						|
SHELL_STATUS
 | 
						|
IfConfigShowInterfaceInfo (
 | 
						|
  IN LIST_ENTRY    *IfList
 | 
						|
  )
 | 
						|
{
 | 
						|
  LIST_ENTRY                   *Entry;
 | 
						|
  LIST_ENTRY                   *Next;
 | 
						|
  IFCONFIG_INTERFACE_CB        *IfCb;
 | 
						|
  EFI_STATUS                    MediaStatus;
 | 
						|
  EFI_IPv4_ADDRESS              Gateway;
 | 
						|
  UINT32                        Index;
 | 
						|
  
 | 
						|
  MediaStatus = EFI_SUCCESS;
 | 
						|
 | 
						|
  if (IsListEmpty (IfList)) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INVALID_INTERFACE), gShellNetwork1HiiHandle);
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Go through the interface list.
 | 
						|
  //
 | 
						|
  NET_LIST_FOR_EACH_SAFE (Entry, Next, IfList) {
 | 
						|
    IfCb = NET_LIST_USER_STRUCT (Entry, IFCONFIG_INTERFACE_CB, Link);
 | 
						|
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_BREAK), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    //
 | 
						|
    // Print interface name.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_IF_NAME), gShellNetwork1HiiHandle, IfCb->IfInfo->Name); 
 | 
						|
 | 
						|
    //
 | 
						|
    // Get Media State.
 | 
						|
    //
 | 
						|
    if (EFI_SUCCESS == NetLibDetectMediaWaitTimeout (IfCb->NicHandle, 0, &MediaStatus)) {
 | 
						|
      if (MediaStatus != EFI_SUCCESS) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_MEDIA_STATE), gShellNetwork1HiiHandle, L"Media disconnected");
 | 
						|
      } else {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_MEDIA_STATE), gShellNetwork1HiiHandle, L"Media present");
 | 
						|
      }
 | 
						|
    } else {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_MEDIA_STATE), gShellNetwork1HiiHandle, L"Media state unknown");
 | 
						|
    }
 | 
						|
 | 
						|
    //
 | 
						|
    // Print interface config policy.
 | 
						|
    //
 | 
						|
    if (IfCb->Policy == Ip4Config2PolicyDhcp) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_POLICY_DHCP), gShellNetwork1HiiHandle);
 | 
						|
    } else {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_POLICY_MAN), gShellNetwork1HiiHandle);
 | 
						|
    }
 | 
						|
 | 
						|
    //
 | 
						|
    // Print mac address of the interface.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_MAC_ADDR_HEAD), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    IfConfigPrintMacAddr (
 | 
						|
      IfCb->IfInfo->HwAddress.Addr,
 | 
						|
      IfCb->IfInfo->HwAddressSize
 | 
						|
      );
 | 
						|
 | 
						|
    //
 | 
						|
    // Print IPv4 address list of the interface.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_IP_ADDR_HEAD), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    ShellPrintHiiEx(
 | 
						|
      -1, 
 | 
						|
      -1, 
 | 
						|
      NULL,
 | 
						|
      STRING_TOKEN (STR_IFCONFIG_INFO_IP_ADDR_BODY), 
 | 
						|
      gShellNetwork1HiiHandle,
 | 
						|
      (UINTN)IfCb->IfInfo->StationAddress.Addr[0],
 | 
						|
      (UINTN)IfCb->IfInfo->StationAddress.Addr[1],
 | 
						|
      (UINTN)IfCb->IfInfo->StationAddress.Addr[2],
 | 
						|
      (UINTN)IfCb->IfInfo->StationAddress.Addr[3]
 | 
						|
      );
 | 
						|
 | 
						|
    //
 | 
						|
    // Print subnet mask list of the interface.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_SUBNET_MASK_HEAD), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    ShellPrintHiiEx(
 | 
						|
      -1, 
 | 
						|
      -1, 
 | 
						|
      NULL,
 | 
						|
      STRING_TOKEN (STR_IFCONFIG_INFO_IP_ADDR_BODY), 
 | 
						|
      gShellNetwork1HiiHandle,
 | 
						|
      (UINTN)IfCb->IfInfo->SubnetMask.Addr[0],
 | 
						|
      (UINTN)IfCb->IfInfo->SubnetMask.Addr[1],
 | 
						|
      (UINTN)IfCb->IfInfo->SubnetMask.Addr[2],
 | 
						|
      (UINTN)IfCb->IfInfo->SubnetMask.Addr[3]
 | 
						|
      );
 | 
						|
 | 
						|
    //
 | 
						|
    // Print default gateway of the interface.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_GATEWAY_HEAD), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    ZeroMem (&Gateway, sizeof (EFI_IPv4_ADDRESS));
 | 
						|
    
 | 
						|
    for (Index = 0; Index < IfCb->IfInfo->RouteTableSize; Index++) {
 | 
						|
      if ((CompareMem (&IfCb->IfInfo->RouteTable[Index].SubnetAddress, &mZeroIp4Addr, sizeof (EFI_IPv4_ADDRESS)) == 0) &&
 | 
						|
          (CompareMem (&IfCb->IfInfo->RouteTable[Index].SubnetMask   , &mZeroIp4Addr, sizeof (EFI_IPv4_ADDRESS)) == 0) ){
 | 
						|
        CopyMem (&Gateway, &IfCb->IfInfo->RouteTable[Index].GatewayAddress, sizeof (EFI_IPv4_ADDRESS));
 | 
						|
      }
 | 
						|
    }    
 | 
						|
 | 
						|
    ShellPrintHiiEx(
 | 
						|
      -1, 
 | 
						|
      -1, 
 | 
						|
      NULL,
 | 
						|
      STRING_TOKEN (STR_IFCONFIG_INFO_IP_ADDR_BODY), 
 | 
						|
      gShellNetwork1HiiHandle,
 | 
						|
      (UINTN)Gateway.Addr[0],
 | 
						|
      (UINTN)Gateway.Addr[1],
 | 
						|
      (UINTN)Gateway.Addr[2],
 | 
						|
      (UINTN)Gateway.Addr[3]
 | 
						|
      );
 | 
						|
      
 | 
						|
    //
 | 
						|
    // Print route table entry.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_ROUTES_SIZE), gShellNetwork1HiiHandle, IfCb->IfInfo->RouteTableSize);
 | 
						|
 | 
						|
    for (Index = 0; Index < IfCb->IfInfo->RouteTableSize; Index++) {
 | 
						|
      ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_ROUTES_ENTRY_INDEX), gShellNetwork1HiiHandle, Index);
 | 
						|
 | 
						|
      ShellPrintHiiEx(
 | 
						|
        -1, 
 | 
						|
        -1, 
 | 
						|
        NULL,
 | 
						|
        STRING_TOKEN (STR_IFCONFIG_SHOW_IP_ADDR), 
 | 
						|
        gShellNetwork1HiiHandle, 
 | 
						|
        L"Subnet ",
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetAddress.Addr[0],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetAddress.Addr[1],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetAddress.Addr[2],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetAddress.Addr[3]
 | 
						|
        );
 | 
						|
 | 
						|
      ShellPrintHiiEx(
 | 
						|
        -1, 
 | 
						|
        -1, 
 | 
						|
        NULL,
 | 
						|
        STRING_TOKEN (STR_IFCONFIG_SHOW_IP_ADDR), 
 | 
						|
        gShellNetwork1HiiHandle, 
 | 
						|
        L"Netmask",
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetMask.Addr[0],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetMask.Addr[1],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetMask.Addr[2],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].SubnetMask.Addr[3]
 | 
						|
        );
 | 
						|
 | 
						|
      ShellPrintHiiEx(
 | 
						|
        -1, 
 | 
						|
        -1, 
 | 
						|
        NULL,
 | 
						|
        STRING_TOKEN (STR_IFCONFIG_SHOW_IP_ADDR), 
 | 
						|
        gShellNetwork1HiiHandle, 
 | 
						|
        L"Gateway",
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].GatewayAddress.Addr[0],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].GatewayAddress.Addr[1],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].GatewayAddress.Addr[2],
 | 
						|
        (UINTN)IfCb->IfInfo->RouteTable[Index].GatewayAddress.Addr[3]
 | 
						|
        );
 | 
						|
    }
 | 
						|
 | 
						|
    //
 | 
						|
    // Print dns server addresses list of the interface if has.
 | 
						|
    //
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_DNS_ADDR_HEAD), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
    for (Index = 0; Index < IfCb->DnsCnt; Index++) {
 | 
						|
      ShellPrintHiiEx(
 | 
						|
        -1, 
 | 
						|
        -1, 
 | 
						|
        NULL,
 | 
						|
        STRING_TOKEN (STR_IFCONFIG_INFO_DNS_ADDR_BODY), 
 | 
						|
        gShellNetwork1HiiHandle,
 | 
						|
        (UINTN) IfCb->DnsAddr[Index].Addr[0],
 | 
						|
        (UINTN) IfCb->DnsAddr[Index].Addr[1],
 | 
						|
        (UINTN) IfCb->DnsAddr[Index].Addr[2],
 | 
						|
        (UINTN) IfCb->DnsAddr[Index].Addr[3]
 | 
						|
        );
 | 
						|
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_NEWLINE), gShellNetwork1HiiHandle);
 | 
						|
    }
 | 
						|
  }
 | 
						|
  
 | 
						|
  ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INFO_BREAK), gShellNetwork1HiiHandle);
 | 
						|
 | 
						|
  return SHELL_SUCCESS;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The clean process of the ifconfig command to clear interface info.
 | 
						|
 | 
						|
  @param[in]   IfList    The pointer of IfList(interface list).
 | 
						|
  @param[in]   IfName    The pointer of interface name.
 | 
						|
 | 
						|
  @retval SHELL_SUCCESS  The ifconfig command clean processed successfully.
 | 
						|
  @retval others         The ifconfig command clean process failed.
 | 
						|
 | 
						|
**/
 | 
						|
SHELL_STATUS
 | 
						|
IfConfigClearInterfaceInfo (
 | 
						|
  IN LIST_ENTRY    *IfList,
 | 
						|
  IN CHAR16        *IfName
 | 
						|
  )
 | 
						|
{
 | 
						|
  EFI_STATUS                Status;  
 | 
						|
  SHELL_STATUS              ShellStatus;
 | 
						|
  LIST_ENTRY                *Entry;
 | 
						|
  LIST_ENTRY                *Next;
 | 
						|
  IFCONFIG_INTERFACE_CB     *IfCb;
 | 
						|
  EFI_IP4_CONFIG2_POLICY    Policy;
 | 
						|
  
 | 
						|
  Status = EFI_SUCCESS;
 | 
						|
  ShellStatus = SHELL_SUCCESS;
 | 
						|
 | 
						|
  if (IsListEmpty (IfList)) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INVALID_INTERFACE), gShellNetwork1HiiHandle);
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Go through the interface list.
 | 
						|
  // If the interface name is specified, DHCP DORA process will be 
 | 
						|
  // triggered by the policy transition (static -> dhcp).
 | 
						|
  //
 | 
						|
  NET_LIST_FOR_EACH_SAFE (Entry, Next, IfList) {
 | 
						|
    IfCb = NET_LIST_USER_STRUCT (Entry, IFCONFIG_INTERFACE_CB, Link);
 | 
						|
 | 
						|
    if ((IfName != NULL) && (StrCmp (IfName, IfCb->IfInfo->Name) == 0)) {
 | 
						|
      Policy = Ip4Config2PolicyStatic;
 | 
						|
      
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypePolicy,
 | 
						|
                              sizeof (EFI_IP4_CONFIG2_POLICY),
 | 
						|
                              &Policy
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        break;
 | 
						|
      }  
 | 
						|
    }
 | 
						|
 | 
						|
    Policy = Ip4Config2PolicyDhcp;
 | 
						|
    
 | 
						|
    Status = IfCb->IfCfg->SetData (
 | 
						|
                            IfCb->IfCfg,
 | 
						|
                            Ip4Config2DataTypePolicy,
 | 
						|
                            sizeof (EFI_IP4_CONFIG2_POLICY),
 | 
						|
                            &Policy
 | 
						|
                            );
 | 
						|
    if (EFI_ERROR (Status)) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
      ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
      break;
 | 
						|
    }
 | 
						|
  }
 | 
						|
 | 
						|
  return ShellStatus;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The set process of the ifconfig command.
 | 
						|
 | 
						|
  @param[in]   IfList    The pointer of IfList(interface list).
 | 
						|
  @param[in]   VarArg    The pointer of ARG_LIST(Args with "-s" option).
 | 
						|
 | 
						|
  @retval SHELL_SUCCESS  The ifconfig command set processed successfully.
 | 
						|
  @retval others         The ifconfig command set process failed.
 | 
						|
 | 
						|
**/
 | 
						|
SHELL_STATUS
 | 
						|
IfConfigSetInterfaceInfo (
 | 
						|
  IN LIST_ENTRY    *IfList,
 | 
						|
  IN ARG_LIST      *VarArg
 | 
						|
  )
 | 
						|
{
 | 
						|
  EFI_STATUS                       Status;
 | 
						|
  SHELL_STATUS                     ShellStatus;
 | 
						|
  IFCONFIG_INTERFACE_CB            *IfCb;
 | 
						|
  VAR_CHECK_CODE                   CheckCode;
 | 
						|
  EFI_EVENT                        TimeOutEvt;
 | 
						|
  EFI_EVENT                        MappedEvt;
 | 
						|
  BOOLEAN                          IsAddressOk;
 | 
						|
 | 
						|
  EFI_IP4_CONFIG2_POLICY           Policy;
 | 
						|
  EFI_IP4_CONFIG2_MANUAL_ADDRESS   ManualAddress;
 | 
						|
  UINTN                            DataSize;
 | 
						|
  EFI_IPv4_ADDRESS                 Gateway;
 | 
						|
  IP4_ADDR                         SubnetMask;
 | 
						|
  IP4_ADDR                         TempGateway;
 | 
						|
  EFI_IPv4_ADDRESS                 *Dns;
 | 
						|
  ARG_LIST                         *Tmp;
 | 
						|
  UINTN                            Index;
 | 
						|
 | 
						|
  CONST CHAR16* TempString;
 | 
						|
 | 
						|
  Dns = NULL;
 | 
						|
 | 
						|
  if (IsListEmpty (IfList)) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INVALID_INTERFACE), gShellNetwork1HiiHandle);
 | 
						|
    return SHELL_INVALID_PARAMETER;
 | 
						|
  }
 | 
						|
  
 | 
						|
  //
 | 
						|
  // Make sure to set only one interface each time.
 | 
						|
  //
 | 
						|
  IfCb   = NET_LIST_USER_STRUCT (IfList->ForwardLink, IFCONFIG_INTERFACE_CB, Link);
 | 
						|
  Status = EFI_SUCCESS;
 | 
						|
  ShellStatus = SHELL_SUCCESS;
 | 
						|
 | 
						|
  //
 | 
						|
  // Initialize check list mechanism.
 | 
						|
  //
 | 
						|
  CheckCode = IfConfigRetriveCheckListByName(
 | 
						|
                NULL,
 | 
						|
                NULL,
 | 
						|
                TRUE
 | 
						|
                );
 | 
						|
 | 
						|
  //
 | 
						|
  // Create events & timers for asynchronous settings.
 | 
						|
  //
 | 
						|
  Status = gBS->CreateEvent (
 | 
						|
                  EVT_TIMER,
 | 
						|
                  TPL_CALLBACK,
 | 
						|
                  NULL,
 | 
						|
                  NULL,
 | 
						|
                  &TimeOutEvt
 | 
						|
                  );
 | 
						|
  if (EFI_ERROR (Status)) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
    ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  Status = gBS->CreateEvent (
 | 
						|
                  EVT_NOTIFY_SIGNAL,
 | 
						|
                  TPL_NOTIFY,
 | 
						|
                  IfConfigManualAddressNotify,
 | 
						|
                  &IsAddressOk,
 | 
						|
                  &MappedEvt
 | 
						|
                  );
 | 
						|
  if (EFI_ERROR (Status)) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
    ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Parse the setting variables.
 | 
						|
  //
 | 
						|
  while (VarArg != NULL) {
 | 
						|
    //
 | 
						|
    // Check invalid parameters (duplication & unknown & conflict).
 | 
						|
    //
 | 
						|
    CheckCode = IfConfigRetriveCheckListByName(
 | 
						|
                  mSetCheckList,
 | 
						|
                  VarArg->Arg,
 | 
						|
                  FALSE
 | 
						|
                  );
 | 
						|
 | 
						|
    if (VarCheckOk != CheckCode) {
 | 
						|
      switch (CheckCode) {
 | 
						|
        case VarCheckDuplicate:
 | 
						|
          ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_DUPLICATE_COMMAND), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
          break;
 | 
						|
 | 
						|
        case VarCheckConflict:
 | 
						|
          ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_CONFLICT_COMMAND), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
          break;
 | 
						|
 | 
						|
        case VarCheckUnknown:
 | 
						|
          //
 | 
						|
          // To handle unsupported option.
 | 
						|
          //
 | 
						|
          TempString = PermanentString;
 | 
						|
          if (StringNoCaseCompare(&VarArg->Arg, &TempString) == 0) {
 | 
						|
            ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_UNSUPPORTED_OPTION), gShellNetwork1HiiHandle, PermanentString);
 | 
						|
            goto ON_EXIT;
 | 
						|
          }
 | 
						|
 | 
						|
          //
 | 
						|
          // To handle unknown option.
 | 
						|
          //
 | 
						|
          ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_UNKNOWN_COMMAND), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
          break;
 | 
						|
 | 
						|
        default:
 | 
						|
          break;
 | 
						|
      }
 | 
						|
 | 
						|
      VarArg = VarArg->Next;
 | 
						|
      continue;   
 | 
						|
    }
 | 
						|
 | 
						|
    //
 | 
						|
    // Process valid variables.
 | 
						|
    //
 | 
						|
    if (StrCmp(VarArg->Arg, L"dhcp") == 0) {
 | 
						|
      //
 | 
						|
      // Set dhcp config policy
 | 
						|
      //
 | 
						|
      Policy = Ip4Config2PolicyDhcp;
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypePolicy,
 | 
						|
                              sizeof (EFI_IP4_CONFIG2_POLICY),
 | 
						|
                              &Policy
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR(Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      
 | 
						|
      VarArg= VarArg->Next;    
 | 
						|
 | 
						|
    } else if (StrCmp (VarArg->Arg, L"static") == 0) {
 | 
						|
      VarArg= VarArg->Next;
 | 
						|
      if (VarArg == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_COMMAND), gShellNetwork1HiiHandle);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      ZeroMem (&ManualAddress, sizeof (ManualAddress));
 | 
						|
    
 | 
						|
      //
 | 
						|
      // Get manual IP address.
 | 
						|
      //
 | 
						|
      Status = NetLibStrToIp4 (VarArg->Arg, &ManualAddress.Address);
 | 
						|
      if (EFI_ERROR(Status)) {
 | 
						|
        ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_INVALID_IPADDRESS), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      //
 | 
						|
      // Get subnetmask.
 | 
						|
      //    
 | 
						|
      VarArg = VarArg->Next;
 | 
						|
      if (VarArg == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_COMMAND), gShellNetwork1HiiHandle);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      
 | 
						|
      Status = NetLibStrToIp4 (VarArg->Arg, &ManualAddress.SubnetMask);
 | 
						|
      if (EFI_ERROR(Status)) {
 | 
						|
        ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_INVALID_IPADDRESS), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      //
 | 
						|
      // Get gateway.
 | 
						|
      //
 | 
						|
      VarArg = VarArg->Next;
 | 
						|
      if (VarArg == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_COMMAND), gShellNetwork1HiiHandle);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      
 | 
						|
      Status = NetLibStrToIp4 (VarArg->Arg, &Gateway);
 | 
						|
      if (EFI_ERROR(Status)) {
 | 
						|
        ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_INVALID_IPADDRESS), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      //
 | 
						|
      // Need to check the gateway validity before set Manual Address.
 | 
						|
      // In case we can set manual address but fail to configure Gateway.
 | 
						|
      //
 | 
						|
      CopyMem (&SubnetMask, &ManualAddress.SubnetMask, sizeof (IP4_ADDR));
 | 
						|
      CopyMem (&TempGateway, &Gateway, sizeof (IP4_ADDR));
 | 
						|
      SubnetMask  = NTOHL (SubnetMask);
 | 
						|
      TempGateway = NTOHL (TempGateway);
 | 
						|
      if ((SubnetMask != 0) &&
 | 
						|
          !NetIp4IsUnicast (TempGateway, SubnetMask)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_INVALID_GATEWAY), gShellNetwork1HiiHandle, VarArg->Arg);
 | 
						|
        ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      //
 | 
						|
      // Set manual config policy.
 | 
						|
      //
 | 
						|
      Policy = Ip4Config2PolicyStatic;
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypePolicy,
 | 
						|
                              sizeof (EFI_IP4_CONFIG2_POLICY),
 | 
						|
                              &Policy
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR(Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      
 | 
						|
      //
 | 
						|
      // Set Manual Address.
 | 
						|
      //
 | 
						|
      IsAddressOk = FALSE;
 | 
						|
 | 
						|
      Status = IfCb->IfCfg->RegisterDataNotify (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypeManualAddress,
 | 
						|
                              MappedEvt
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_SET_ADDR_FAILED), gShellNetwork1HiiHandle, Status);
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      DataSize = sizeof (EFI_IP4_CONFIG2_MANUAL_ADDRESS);
 | 
						|
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypeManualAddress,
 | 
						|
                              DataSize,
 | 
						|
                              &ManualAddress
 | 
						|
                              );
 | 
						|
 | 
						|
      if (Status == EFI_NOT_READY) {
 | 
						|
        gBS->SetTimer (TimeOutEvt, TimerRelative, 50000000);
 | 
						|
 | 
						|
        while (EFI_ERROR (gBS->CheckEvent (TimeOutEvt))) {
 | 
						|
          if (IsAddressOk) {
 | 
						|
            Status = EFI_SUCCESS;
 | 
						|
            break;
 | 
						|
          }
 | 
						|
        }
 | 
						|
      }
 | 
						|
 | 
						|
      IfCb->IfCfg->UnregisterDataNotify (
 | 
						|
                     IfCb->IfCfg,
 | 
						|
                     Ip4Config2DataTypeManualAddress,
 | 
						|
                     MappedEvt
 | 
						|
                     );
 | 
						|
      
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_SET_ADDR_FAILED), gShellNetwork1HiiHandle, Status);
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
 | 
						|
      //
 | 
						|
      // Set gateway.
 | 
						|
      //
 | 
						|
      DataSize = sizeof (EFI_IPv4_ADDRESS);
 | 
						|
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypeGateway,
 | 
						|
                              DataSize,
 | 
						|
                              &Gateway
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_SET_ADDR_FAILED), gShellNetwork1HiiHandle, Status);
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      
 | 
						|
      VarArg = VarArg->Next;
 | 
						|
      
 | 
						|
    } else if (StrCmp (VarArg->Arg, L"dns") == 0) {
 | 
						|
      //
 | 
						|
      // Get DNS addresses.
 | 
						|
      //
 | 
						|
      VarArg = VarArg->Next;
 | 
						|
      Tmp    = VarArg;
 | 
						|
      Index  = 0;
 | 
						|
      while (Tmp != NULL) {
 | 
						|
        Index ++;
 | 
						|
        Tmp = Tmp->Next;
 | 
						|
      }
 | 
						|
 | 
						|
      Dns   = AllocatePool (Index * sizeof (EFI_IPv4_ADDRESS));
 | 
						|
      if (Dns == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_OUT_OF_RESOURCES;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      Tmp   = VarArg;
 | 
						|
      Index = 0;
 | 
						|
      while (Tmp != NULL) {
 | 
						|
        Status = NetLibStrToIp4 (Tmp->Arg, Dns + Index);
 | 
						|
        if (EFI_ERROR(Status)) {
 | 
						|
          ShellPrintHiiEx(-1, -1, NULL,STRING_TOKEN (STR_IFCONFIG_INVALID_IPADDRESS), gShellNetwork1HiiHandle, Tmp->Arg);
 | 
						|
          ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
          goto ON_EXIT;
 | 
						|
        }
 | 
						|
        Index ++;
 | 
						|
        Tmp = Tmp->Next;
 | 
						|
      }
 | 
						|
      
 | 
						|
      VarArg = Tmp;
 | 
						|
 | 
						|
      //
 | 
						|
      // Set DNS addresses.
 | 
						|
      //
 | 
						|
      DataSize = Index * sizeof (EFI_IPv4_ADDRESS);
 | 
						|
 | 
						|
      Status = IfCb->IfCfg->SetData (
 | 
						|
                              IfCb->IfCfg,
 | 
						|
                              Ip4Config2DataTypeDnsServer,
 | 
						|
                              DataSize,
 | 
						|
                              Dns
 | 
						|
                              );
 | 
						|
      if (EFI_ERROR (Status)) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_ERR_AD), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_ACCESS_DENIED;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
    }
 | 
						|
  }
 | 
						|
 | 
						|
ON_EXIT:
 | 
						|
  if (Dns != NULL) {
 | 
						|
    FreePool (Dns);
 | 
						|
  }
 | 
						|
  
 | 
						|
  return ShellStatus;
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The ifconfig command main process.
 | 
						|
 | 
						|
  @param[in]   Private    The pointer of IFCONFIG_PRIVATE_DATA.
 | 
						|
 | 
						|
  @retval SHELL_SUCCESS  ifconfig command processed successfully.
 | 
						|
  @retval others         The ifconfig command process failed.
 | 
						|
 | 
						|
**/
 | 
						|
SHELL_STATUS
 | 
						|
IfConfig (
 | 
						|
  IN IFCONFIG_PRIVATE_DATA    *Private
 | 
						|
  )
 | 
						|
{
 | 
						|
  EFI_STATUS    Status;
 | 
						|
  SHELL_STATUS  ShellStatus;
 | 
						|
 | 
						|
  ShellStatus = SHELL_SUCCESS;
 | 
						|
 | 
						|
  //
 | 
						|
  // Get configure information of all interfaces.
 | 
						|
  //
 | 
						|
  Status = IfConfigGetInterfaceInfo (
 | 
						|
             Private->IfName,
 | 
						|
             &Private->IfList
 | 
						|
             );
 | 
						|
  if (EFI_ERROR (Status)) {
 | 
						|
    ShellStatus = SHELL_NOT_FOUND; 
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  switch (Private->OpCode) {
 | 
						|
  case IfConfigOpList:
 | 
						|
    ShellStatus = IfConfigShowInterfaceInfo (&Private->IfList);
 | 
						|
    break;
 | 
						|
 | 
						|
  case IfConfigOpClear:
 | 
						|
    ShellStatus = IfConfigClearInterfaceInfo (&Private->IfList, Private->IfName);
 | 
						|
    break;
 | 
						|
 | 
						|
  case IfConfigOpSet:
 | 
						|
    ShellStatus = IfConfigSetInterfaceInfo (&Private->IfList, Private->VarArg);
 | 
						|
    break;
 | 
						|
 | 
						|
  default:
 | 
						|
    ShellStatus = SHELL_UNSUPPORTED;
 | 
						|
  }
 | 
						|
 | 
						|
ON_EXIT:
 | 
						|
  return ShellStatus;
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  The ifconfig command cleanup process, free the allocated memory.
 | 
						|
 | 
						|
  @param[in]   Private    The pointer of  IFCONFIG_PRIVATE_DATA.
 | 
						|
 | 
						|
**/
 | 
						|
VOID
 | 
						|
IfConfigCleanup (
 | 
						|
  IN IFCONFIG_PRIVATE_DATA  *Private
 | 
						|
  )
 | 
						|
{
 | 
						|
  LIST_ENTRY                *Entry;
 | 
						|
  LIST_ENTRY                *NextEntry;
 | 
						|
  IFCONFIG_INTERFACE_CB     *IfCb;
 | 
						|
 | 
						|
  ASSERT (Private != NULL);
 | 
						|
 | 
						|
  //
 | 
						|
  // Clean the list which save the set config Args.
 | 
						|
  //
 | 
						|
  if (Private->VarArg != NULL) {
 | 
						|
    FreeArgList (Private->VarArg);
 | 
						|
  }
 | 
						|
 | 
						|
  if (Private->IfName != NULL) {
 | 
						|
    FreePool (Private->IfName);
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // Clean the IFCONFIG_INTERFACE_CB list.
 | 
						|
  //
 | 
						|
  NET_LIST_FOR_EACH_SAFE (Entry, NextEntry, &Private->IfList) {
 | 
						|
    IfCb = NET_LIST_USER_STRUCT (Entry, IFCONFIG_INTERFACE_CB, Link);
 | 
						|
 | 
						|
    RemoveEntryList (&IfCb->Link);
 | 
						|
 | 
						|
    if (IfCb->IfInfo != NULL) {
 | 
						|
 | 
						|
      FreePool (IfCb->IfInfo);
 | 
						|
    }
 | 
						|
 | 
						|
    FreePool (IfCb);
 | 
						|
  }
 | 
						|
 | 
						|
  FreePool (Private);
 | 
						|
}
 | 
						|
 | 
						|
/**
 | 
						|
  Function for 'ifconfig' command.
 | 
						|
 | 
						|
  @param[in] ImageHandle  Handle to the Image (NULL if Internal).
 | 
						|
  @param[in] SystemTable  Pointer to the System Table (NULL if Internal).
 | 
						|
 | 
						|
  @retval EFI_SUCCESS    ifconfig command processed successfully.
 | 
						|
  @retval others         The ifconfig command process failed.
 | 
						|
  
 | 
						|
**/
 | 
						|
SHELL_STATUS
 | 
						|
EFIAPI
 | 
						|
ShellCommandRunIfconfig (
 | 
						|
  IN EFI_HANDLE        ImageHandle,
 | 
						|
  IN EFI_SYSTEM_TABLE  *SystemTable
 | 
						|
  )
 | 
						|
{
 | 
						|
  EFI_STATUS                Status;
 | 
						|
  IFCONFIG_PRIVATE_DATA     *Private;
 | 
						|
  LIST_ENTRY                *ParamPackage;
 | 
						|
  SHELL_STATUS              ShellStatus;
 | 
						|
  CONST CHAR16              *ValueStr;
 | 
						|
  ARG_LIST                  *ArgList;
 | 
						|
  CHAR16                    *ProblemParam;
 | 
						|
  CHAR16                    *Str;
 | 
						|
  
 | 
						|
  Status = EFI_INVALID_PARAMETER;
 | 
						|
  Private = NULL;
 | 
						|
  ShellStatus = SHELL_SUCCESS;
 | 
						|
 | 
						|
  Status = ShellCommandLineParseEx (mIfConfigCheckList, &ParamPackage, &ProblemParam, TRUE, FALSE);
 | 
						|
  if (EFI_ERROR (Status)) {
 | 
						|
    if (Status == EFI_VOLUME_CORRUPTED && ProblemParam != NULL) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_INV), gShellNetwork1HiiHandle, L"ifconfig", ProblemParam);
 | 
						|
      FreePool(ProblemParam);
 | 
						|
      ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
    } else {
 | 
						|
      ASSERT(FALSE);
 | 
						|
    }
 | 
						|
    
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // To handle unsupported option.
 | 
						|
  //
 | 
						|
  if (ShellCommandLineGetFlag (ParamPackage, L"-c")) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_UNSUPPORTED_OPTION), gShellNetwork1HiiHandle,L"-c");
 | 
						|
    ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // To handle no option.
 | 
						|
  //
 | 
						|
  if (!ShellCommandLineGetFlag (ParamPackage, L"-r") && !ShellCommandLineGetFlag (ParamPackage, L"-s") &&
 | 
						|
      !ShellCommandLineGetFlag (ParamPackage, L"-l")) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_OPTION), gShellNetwork1HiiHandle);
 | 
						|
    ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // To handle conflict options.
 | 
						|
  //
 | 
						|
  if (((ShellCommandLineGetFlag (ParamPackage, L"-r")) && (ShellCommandLineGetFlag (ParamPackage, L"-s"))) ||
 | 
						|
      ((ShellCommandLineGetFlag (ParamPackage, L"-r")) && (ShellCommandLineGetFlag (ParamPackage, L"-l"))) ||
 | 
						|
      ((ShellCommandLineGetFlag (ParamPackage, L"-s")) && (ShellCommandLineGetFlag (ParamPackage, L"-l")))) {
 | 
						|
    ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PARAM_CON), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
    ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  Private = AllocateZeroPool (sizeof (IFCONFIG_PRIVATE_DATA));
 | 
						|
  if (Private == NULL) {
 | 
						|
    ShellStatus = SHELL_OUT_OF_RESOURCES;
 | 
						|
    goto ON_EXIT;
 | 
						|
  }
 | 
						|
 | 
						|
  InitializeListHead (&Private->IfList);
 | 
						|
 | 
						|
  //
 | 
						|
  // To get interface name for the list option.
 | 
						|
  //
 | 
						|
  if (ShellCommandLineGetFlag (ParamPackage, L"-l")) {
 | 
						|
    Private->OpCode = IfConfigOpList;
 | 
						|
    ValueStr = ShellCommandLineGetValue (ParamPackage, L"-l");
 | 
						|
    if (ValueStr != NULL) {
 | 
						|
      Str = AllocateCopyPool (StrSize (ValueStr), ValueStr);
 | 
						|
      if (Str == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_OUT_OF_RESOURCES;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      Private->IfName = Str;
 | 
						|
    }
 | 
						|
  }
 | 
						|
 | 
						|
  //
 | 
						|
  // To get interface name for the clear option.
 | 
						|
  //
 | 
						|
  if (ShellCommandLineGetFlag (ParamPackage, L"-r")) {
 | 
						|
    Private->OpCode = IfConfigOpClear;
 | 
						|
    ValueStr = ShellCommandLineGetValue (ParamPackage, L"-r");
 | 
						|
    if (ValueStr != NULL) {
 | 
						|
      Str = AllocateCopyPool (StrSize (ValueStr), ValueStr);
 | 
						|
      if (Str == NULL) {
 | 
						|
        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
        ShellStatus = SHELL_OUT_OF_RESOURCES;
 | 
						|
        goto ON_EXIT;
 | 
						|
      }
 | 
						|
      Private->IfName = Str;
 | 
						|
    }
 | 
						|
  }
 | 
						|
  
 | 
						|
  //
 | 
						|
  // To get interface name and corresponding Args for the set option.
 | 
						|
  //
 | 
						|
  if (ShellCommandLineGetFlag (ParamPackage, L"-s")) {
 | 
						|
    ValueStr = ShellCommandLineGetValue (ParamPackage, L"-s");
 | 
						|
    if (ValueStr == NULL) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_INTERFACE), gShellNetwork1HiiHandle);
 | 
						|
      ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
      goto ON_EXIT;
 | 
						|
    }
 | 
						|
    
 | 
						|
    //
 | 
						|
    // To split the configuration into multi-section.
 | 
						|
    //
 | 
						|
    ArgList = SplitStrToList (ValueStr, L' ');
 | 
						|
    if (ArgList == NULL) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_OUT_MEM), gShellNetwork1HiiHandle, L"ifconfig");
 | 
						|
      ShellStatus = SHELL_OUT_OF_RESOURCES;
 | 
						|
      goto ON_EXIT;
 | 
						|
    }
 | 
						|
 | 
						|
    Private->OpCode = IfConfigOpSet;
 | 
						|
    Private->IfName = ArgList->Arg;
 | 
						|
 | 
						|
    Private->VarArg = ArgList->Next;
 | 
						|
 | 
						|
    if (Private->IfName == NULL || Private->VarArg == NULL) {
 | 
						|
      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_IFCONFIG_LACK_COMMAND), gShellNetwork1HiiHandle);
 | 
						|
      ShellStatus = SHELL_INVALID_PARAMETER;
 | 
						|
      goto ON_EXIT;
 | 
						|
    }
 | 
						|
  }
 | 
						|
  
 | 
						|
  //
 | 
						|
  // Main process of ifconfig.
 | 
						|
  //
 | 
						|
  ShellStatus = IfConfig (Private);
 | 
						|
 | 
						|
ON_EXIT:
 | 
						|
 | 
						|
  ShellCommandLineFreeVarList (ParamPackage);
 | 
						|
  
 | 
						|
  if (Private != NULL) {
 | 
						|
    IfConfigCleanup (Private);
 | 
						|
  }
 | 
						|
 | 
						|
  return ShellStatus;
 | 
						|
}
 |