1772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** @file 20c323d071d8951fe0c8f41fad08939722d436b12jgong Implementation of EFI Address Resolution Protocol (ARP) Protocol interface functions. 3c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 4e5eed7d3641d71d7ea539e5379ea9c6a5cd97004hhtianCopyright (c) 2006 - 2009, Intel Corporation. All rights reserved.<BR> 5e5eed7d3641d71d7ea539e5379ea9c6a5cd97004hhtianThis program and the accompanying materials 6772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffare licensed and made available under the terms and conditions of the BSD License 7c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgongwhich accompanies this distribution. The full text of the license may be found at<BR> 8772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffhttp://opensource.org/licenses/bsd-license.php 9772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 10772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffTHE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 11772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffWITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 12772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 13772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 14772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 15772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff#include "ArpImpl.h" 16772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 17772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 18772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 19772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function is used to assign a station address to the ARP cache for this instance 200c323d071d8951fe0c8f41fad08939722d436b12jgong of the ARP driver. 210c323d071d8951fe0c8f41fad08939722d436b12jgong 220c323d071d8951fe0c8f41fad08939722d436b12jgong Each ARP instance has one station address. The EFI_ARP_PROTOCOL driver will 230c323d071d8951fe0c8f41fad08939722d436b12jgong respond to ARP requests that match this registered station address. A call to 240c323d071d8951fe0c8f41fad08939722d436b12jgong this function with the ConfigData field set to NULL will reset this ARP instance. 25c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 26c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong Once a protocol type and station address have been assigned to this ARP instance, 27c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong all the following ARP functions will use this information. Attempting to change 28c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong the protocol type or station address to a configured ARP instance will result in errors. 29772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 30772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 31772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param ConfigData Pointer to the EFI_ARP_CONFIG_DATA structure. 32772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 33772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The new station address was successfully 34772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff registered. 35772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER One or more of the following conditions is TRUE: 36772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This is NULL. SwAddressLength is zero when 37772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ConfigData is not NULL. StationAddress is NULL 38772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff when ConfigData is not NULL. 39772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_ACCESS_DENIED The SwAddressType, SwAddressLength, or 40772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff StationAddress is different from the one that is 41772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff already registered. 42772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_OUT_OF_RESOURCES Storage for the new StationAddress could not be 43772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff allocated. 44772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 45772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 46772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 47772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 48772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpConfigure ( 49772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 50772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_CONFIG_DATA *ConfigData OPTIONAL 51772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 52772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 53772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_STATUS Status; 54772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 5536ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 56772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 57772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (This == NULL) { 58772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 59772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 60772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 61772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((ConfigData != NULL) && 62772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ((ConfigData->SwAddressLength == 0) || 63772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff (ConfigData->StationAddress == NULL) || 64772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff (ConfigData->SwAddressType <= 1500))) { 65772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 66772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 67772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 68772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 69772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 70e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 71772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 72772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 73772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Configure this instance, the ConfigData has already passed the basic checks. 74772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 75772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = ArpConfigureInstance (Instance, ConfigData); 76772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 77e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 78772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 79772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return Status; 80772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 81772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 82772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 83772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 84772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function is used to insert entries into the ARP cache. 85772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 86c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong ARP cache entries are typically inserted and updated by network protocol drivers 87c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong as network traffic is processed. Most ARP cache entries will time out and be 88c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong deleted if the network traffic stops. ARP cache entries that were inserted 89c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong by the Add() function may be static (will not time out) or dynamic (will time out). 90c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong Default ARP cache timeout values are not covered in most network protocol 91c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong specifications (although RFC 1122 comes pretty close) and will only be 92c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong discussed in general in this specification. The timeout values that are 93c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong used in the EFI Sample Implementation should be used only as a guideline. 94c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong Final product implementations of the EFI network stack should be tuned for 95c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong their expected network environments. 96c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 97772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 98772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param DenyFlag Set to TRUE if this entry is a deny entry. Set to 99772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff FALSE if this entry is a normal entry. 100772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TargetSwAddress Pointer to a protocol address to add (or deny). 101772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff May be set to NULL if DenyFlag is TRUE. 102772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TargetHwAddress Pointer to a hardware address to add (or deny). 103772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff May be set to NULL if DenyFlag is TRUE. 104772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TimeoutValue Time in 100-ns units that this entry will remain 105772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff in the ARP cache. A value of zero means that the 106772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff entry is permanent. A nonzero value will override 107772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff the one given by Configure() if the entry to be 108772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff added is a dynamic entry. 109772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param Overwrite If TRUE, the matching cache entry will be 110772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff overwritten with the supplied parameters. If 111772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff FALSE, EFI_ACCESS_DENIED is returned if the 112772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff corresponding cache entry already exists. 113772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 114772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The entry has been added or updated. 115772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER One or more of the following conditions is TRUE: 116772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This is NULL. DenyFlag is FALSE and 117772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetHwAddress is NULL. DenyFlag is FALSE and 118772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetSwAddress is NULL. TargetHwAddress is NULL 119772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff and TargetSwAddress is NULL. Both TargetSwAddress 120772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff and TargetHwAddress are not NULL when DenyFlag is 121772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TRUE. 122772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_OUT_OF_RESOURCES The new ARP cache entry could not be allocated. 123772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_ACCESS_DENIED The ARP cache entry already exists and Overwrite 124772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff is not true. 125772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 126772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 127772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 128772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 129772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 130772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpAdd ( 131772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 132772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN BOOLEAN DenyFlag, 133772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *TargetSwAddress OPTIONAL, 134772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *TargetHwAddress OPTIONAL, 135772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN UINT32 TimeoutValue, 136772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN BOOLEAN Overwrite 137772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 138772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 139772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_STATUS Status; 140772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 141772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_SERVICE_DATA *ArpService; 142772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_CACHE_ENTRY *CacheEntry; 143772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_SIMPLE_NETWORK_MODE *SnpMode; 144772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NET_ARP_ADDRESS MatchAddress[2]; 14536ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 146772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 147772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (This == NULL) { 148772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 149772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 150772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 151772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (((!DenyFlag) && ((TargetHwAddress == NULL) || (TargetSwAddress == NULL))) || 152772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff (DenyFlag && (TargetHwAddress != NULL) && (TargetSwAddress != NULL)) || 153772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ((TargetHwAddress == NULL) && (TargetSwAddress == NULL))) { 154772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 155772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 156772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 157772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 158772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 159772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 160772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 161772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 162772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 163772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_SUCCESS; 164772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpService = Instance->ArpService; 165772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff SnpMode = &Instance->ArpService->SnpMode; 166772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 167772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 168772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Fill the hardware address part in the MatchAddress. 169772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 170772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Hardware].Type = SnpMode->IfType; 171772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Hardware].Length = (UINT8) SnpMode->HwAddressSize; 172772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Hardware].AddressPtr = TargetHwAddress; 173772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 174772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 175772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Fill the software address part in the MatchAddress. 176772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 177772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Protocol].Type = Instance->ConfigData.SwAddressType; 178772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Protocol].Length = Instance->ConfigData.SwAddressLength; 179772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff MatchAddress[Protocol].AddressPtr = TargetSwAddress; 180772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 181e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 182772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 183772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 184772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // See whether the entry to add exists. Check the DeinedCacheTable first. 185772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 186772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindDeniedCacheEntry ( 187772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpService, 188772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Protocol], 189772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Hardware] 190772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 191772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 192772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry == NULL) { 193772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 194772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Check the ResolvedCacheTable 195772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 196772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindNextCacheEntryInTable ( 197772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ArpService->ResolvedCacheTable, 198772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL, 199772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ByBoth, 200772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Protocol], 201772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Hardware] 202772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 203772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 204772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 205772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((CacheEntry != NULL) && !Overwrite) { 206772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 207772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // The entry to add exists, if not Overwirte, deny this add request. 208772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 209772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_ACCESS_DENIED; 210772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 211772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 212772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 213772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((CacheEntry == NULL) && (TargetSwAddress != NULL)) { 214772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 215772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Check whether there are pending requests matching the entry to be added. 216772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 217772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindNextCacheEntryInTable ( 218772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ArpService->PendingRequestTable, 219772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL, 220772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ByProtoAddress, 221772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Protocol], 222772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL 223772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 224772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 225772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 226772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry != NULL) { 227772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 228772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Remove it from the Table. 229772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 230e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff RemoveEntryList (&CacheEntry->List); 231772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } else { 232772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 233772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // It's a new entry, allocate memory for the entry. 234772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 235772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpAllocCacheEntry (Instance); 236772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 237772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry == NULL) { 238e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff DEBUG ((EFI_D_ERROR, "ArpAdd: Failed to allocate pool for CacheEntry.\n")); 239772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_OUT_OF_RESOURCES; 240772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 241772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 242772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 243772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 244772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 245772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Overwrite these parameters. 246772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 247772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->DefaultDecayTime = TimeoutValue; 248772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->DecayTime = TimeoutValue; 249772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 250772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 251772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Fill in the addresses. 252772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 253772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpFillAddressInCacheEntry ( 254772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry, 255772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Hardware], 256772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &MatchAddress[Protocol] 257772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 258772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 259772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 260772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Inform the user if there is any. 261772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 262772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpAddressResolved (CacheEntry, NULL, NULL); 263772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 264772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 265772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Add this CacheEntry to the corresponding CacheTable. 266772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 267772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (DenyFlag) { 268e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff InsertHeadList (&ArpService->DeniedCacheTable, &CacheEntry->List); 269772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } else { 270e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff InsertHeadList (&ArpService->ResolvedCacheTable, &CacheEntry->List); 271772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 272772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 273772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffUNLOCK_EXIT: 274772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 275e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 276772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 277772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return Status; 278772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 279772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 280772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 281772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 282772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function searches the ARP cache for matching entries and allocates a buffer into 283772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff which those entries are copied. 284c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 285c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong The first part of the allocated buffer is EFI_ARP_FIND_DATA, following which 286c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong are protocol address pairs and hardware address pairs. 287c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong When finding a specific protocol address (BySwAddress is TRUE and AddressBuffer 288c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong is not NULL), the ARP cache timeout for the found entry is reset if Refresh is 289c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong set to TRUE. If the found ARP cache entry is a permanent entry, it is not 290c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong affected by Refresh. 291c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 292772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 293772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param BySwAddress Set to TRUE to look for matching software protocol 294772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff addresses. Set to FALSE to look for matching 295772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff hardware protocol addresses. 296772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param AddressBuffer Pointer to address buffer. Set to NULL to match 297772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff all addresses. 298772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param EntryLength The size of an entry in the entries buffer. 299772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param EntryCount The number of ARP cache entries that are found by 300772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff the specified criteria. 301772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param Entries Pointer to the buffer that will receive the ARP 302772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff cache entries. 303772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param Refresh Set to TRUE to refresh the timeout value of the 304772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff matching ARP cache entry. 305772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 306772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The requested ARP cache entries were copied into 307772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff the buffer. 308772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER One or more of the following conditions is TRUE: 309772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This is NULL. Both EntryCount and EntryLength are 310772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL, when Refresh is FALSE. 311772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_FOUND No matching entries were found. 312772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 313772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 314772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 315772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 316772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 317772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpFind ( 318772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 319772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN BOOLEAN BySwAddress, 320772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *AddressBuffer OPTIONAL, 321772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff OUT UINT32 *EntryLength OPTIONAL, 322772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff OUT UINT32 *EntryCount OPTIONAL, 323772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff OUT EFI_ARP_FIND_DATA **Entries OPTIONAL, 324772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN BOOLEAN Refresh 325772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 326772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 327772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_STATUS Status; 328772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 32936ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 330772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 331772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((This == NULL) || 332772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff (!Refresh && (EntryCount == NULL) && (EntryLength == NULL)) || 333772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ((Entries != NULL) && ((EntryLength == NULL) || (EntryCount == NULL)))) { 334772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 335772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 336772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 337772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 338772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 339772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 340772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 341772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 342772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 343e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 344772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 345772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 346772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // All the check passed, find the cache entries now. 347772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 348772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = ArpFindCacheEntry ( 349772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance, 350772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff BySwAddress, 351772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff AddressBuffer, 352772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EntryLength, 353772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EntryCount, 354772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Entries, 355772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Refresh 356772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 357772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 358e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 359772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 360772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return Status; 361772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 362772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 363772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 364772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 365772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function removes specified ARP cache entries. 366772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 367772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 368772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param BySwAddress Set to TRUE to delete matching protocol addresses. 369772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Set to FALSE to delete matching hardware 370772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff addresses. 371772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param AddressBuffer Pointer to the address buffer that is used as a 372772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff key to look for the cache entry. Set to NULL to 373772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff delete all entries. 374772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 375772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The entry was removed from the ARP cache. 376772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER This is NULL. 377772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_FOUND The specified deletion key was not found. 378772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 379772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 380772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 381772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 382772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 383772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpDelete ( 384772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 385772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN BOOLEAN BySwAddress, 386772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *AddressBuffer OPTIONAL 387772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 388772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 389772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 390772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff UINTN Count; 39136ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 392772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 393772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (This == NULL) { 394772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 395772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 396772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 397772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 398772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 399772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 400772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 401772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 402772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 403e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 404772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 405772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 406772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Delete the specified cache entries. 407772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 408772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Count = ArpDeleteCacheEntry (Instance, BySwAddress, AddressBuffer, TRUE); 409772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 410e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 411772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 412772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return (Count == 0) ? EFI_NOT_FOUND : EFI_SUCCESS; 413772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 414772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 415772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 416772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 417772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function delete all dynamic entries from the ARP cache that match the specified 418772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff software protocol type. 419772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 420772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 421772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 422772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The cache has been flushed. 423772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER This is NULL. 424772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_FOUND There are no matching dynamic cache entries. 425772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 426772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 427772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 428772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 429772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 430772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpFlush ( 431772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This 432772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 433772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 434772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 435772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff UINTN Count; 43636ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 437772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 438772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (This == NULL) { 439772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 440772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 441772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 442772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 443772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 444772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 445772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 446772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 447772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 448e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 449772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 450772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 451772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Delete the dynamic entries from the cache table. 452772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 453772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Count = ArpDeleteCacheEntry (Instance, FALSE, NULL, FALSE); 454772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 455e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 456772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 457772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return (Count == 0) ? EFI_NOT_FOUND : EFI_SUCCESS; 458772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 459772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 460772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 461772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 462772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function tries to resolve the TargetSwAddress and optionally returns a 463772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetHwAddress if it already exists in the ARP cache. 464772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 465772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 466772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TargetSwAddress Pointer to the protocol address to resolve. 467772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param ResolvedEvent Pointer to the event that will be signaled when 468772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff the address is resolved or some error occurs. 469772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TargetHwAddress Pointer to the buffer for the resolved hardware 470772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff address in network byte order. 471772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 472772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The data is copied from the ARP cache into the 473772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetHwAddress buffer. 474772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER One or more of the following conditions is TRUE: 475772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This is NULL. TargetHwAddress is NULL. 476772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_ACCESS_DENIED The requested address is not present in the normal 477772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP cache but is present in the deny address list. 478772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Outgoing traffic to that address is forbidden. 479772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 480772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_READY The request has been started and is not finished. 481772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 482772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 483772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 484772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 485772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpRequest ( 486772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 487772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *TargetSwAddress OPTIONAL, 488772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_EVENT ResolvedEvent OPTIONAL, 489772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff OUT VOID *TargetHwAddress 490772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 491772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 492772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_STATUS Status; 493772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 494772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_SERVICE_DATA *ArpService; 495772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_SIMPLE_NETWORK_MODE *SnpMode; 496772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_CACHE_ENTRY *CacheEntry; 497772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NET_ARP_ADDRESS HardwareAddress; 498772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NET_ARP_ADDRESS ProtocolAddress; 499772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff USER_REQUEST_CONTEXT *RequestContext; 50036ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 501772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 502772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((This == NULL) || (TargetHwAddress == NULL)) { 503772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 504772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 505772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 506772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 507772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 508772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 509772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 510772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 511772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 512772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_SUCCESS; 513772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpService = Instance->ArpService; 514772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff SnpMode = &ArpService->SnpMode; 515772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 516772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((TargetSwAddress == NULL) || 5177bce0c5a0eb806a55d7231b05769d0efc71cdc59vanjeff ((Instance->ConfigData.SwAddressType == IPV4_ETHER_PROTO_TYPE) && 518772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IP4_IS_LOCAL_BROADCAST (*((UINT32 *)TargetSwAddress)))) { 519772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 520772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Return the hardware broadcast address. 521772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 522e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff CopyMem (TargetHwAddress, &SnpMode->BroadcastAddress, SnpMode->HwAddressSize); 523772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 524772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto SIGNAL_USER; 525772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 526772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 5277bce0c5a0eb806a55d7231b05769d0efc71cdc59vanjeff if ((Instance->ConfigData.SwAddressType == IPV4_ETHER_PROTO_TYPE) && 528772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IP4_IS_MULTICAST (NTOHL (*((UINT32 *)TargetSwAddress)))) { 529772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 530772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // If the software address is an IPv4 multicast address, invoke Mnp to 531772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // resolve the address. 532772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 533772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = ArpService->Mnp->McastIpToMac ( 534772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpService->Mnp, 535772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff FALSE, 536772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetSwAddress, 537772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetHwAddress 538772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 539772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto SIGNAL_USER; 540772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 541772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 542772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff HardwareAddress.Type = SnpMode->IfType; 543772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff HardwareAddress.Length = (UINT8)SnpMode->HwAddressSize; 544772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff HardwareAddress.AddressPtr = NULL; 545772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 546772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ProtocolAddress.Type = Instance->ConfigData.SwAddressType; 547772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ProtocolAddress.Length = Instance->ConfigData.SwAddressLength; 548772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ProtocolAddress.AddressPtr = TargetSwAddress; 549772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 550772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 551772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Initialize the TargetHwAddrss to a zero address. 552772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 553e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff ZeroMem (TargetHwAddress, SnpMode->HwAddressSize); 554772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 555e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 556772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 557772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 558772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Check whether the software address is in the denied table. 559772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 560772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindDeniedCacheEntry (ArpService, &ProtocolAddress, NULL); 561772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry != NULL) { 562772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_ACCESS_DENIED; 563772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 564772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 565772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 566772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 567772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Check whether the software address is already resolved. 568772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 569772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindNextCacheEntryInTable ( 570772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ArpService->ResolvedCacheTable, 571772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL, 572772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ByProtoAddress, 573772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ProtocolAddress, 574772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL 575772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 576772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry != NULL) { 577772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 578772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Resolved, copy the address into the user buffer. 579772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 580e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff CopyMem ( 581772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff TargetHwAddress, 582772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->Addresses[Hardware].AddressPtr, 583772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->Addresses[Hardware].Length 584772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 585772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 586772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 587772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 588772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 589772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (ResolvedEvent == NULL) { 590772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_NOT_READY; 591772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 592772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 593772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 594772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 595772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Create a request context for this arp request. 596772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 597e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff RequestContext = AllocatePool (sizeof(USER_REQUEST_CONTEXT)); 598772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (RequestContext == NULL) { 599e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff DEBUG ((EFI_D_ERROR, "ArpRequest: Allocate memory for RequestContext failed.\n")); 600772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 601772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_OUT_OF_RESOURCES; 602772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 603772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 604772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 605772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff RequestContext->Instance = Instance; 606772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff RequestContext->UserRequestEvent = ResolvedEvent; 607772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff RequestContext->UserHwAddrBuffer = TargetHwAddress; 608e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff InitializeListHead (&RequestContext->List); 609772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 610772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 611772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Check whether there is a same request. 612772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 613772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpFindNextCacheEntryInTable ( 614772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ArpService->PendingRequestTable, 615772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL, 616772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ByProtoAddress, 617772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff &ProtocolAddress, 618772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff NULL 619772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ); 620772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry != NULL) { 621772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 622772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->NextRetryTime = Instance->ConfigData.RetryTimeOut; 623772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry->RetryCount = Instance->ConfigData.RetryCount; 624772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } else { 625772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 626772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Allocate a cache entry for this request. 627772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 628772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff CacheEntry = ArpAllocCacheEntry (Instance); 629772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (CacheEntry == NULL) { 630e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff DEBUG ((EFI_D_ERROR, "ArpRequest: Allocate memory for CacheEntry failed.\n")); 631766c7483c335931b190a78d78d62e5a5e69dc8b9xdu FreePool (RequestContext); 632772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 633772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_OUT_OF_RESOURCES; 634772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff goto UNLOCK_EXIT; 635772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 636772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 637772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 638772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Fill the software address. 639772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 640772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpFillAddressInCacheEntry (CacheEntry, &HardwareAddress, &ProtocolAddress); 641772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 642772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 643772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Add this entry into the PendingRequestTable. 644772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 645e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff InsertTailList (&ArpService->PendingRequestTable, &CacheEntry->List); 646772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 647772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 648772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 649772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Link this request context into the cache entry. 650772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 651e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff InsertHeadList (&CacheEntry->UserRequestList, &RequestContext->List); 652772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 653772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 654772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Send out the ARP Request frame. 655772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 656772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ArpSendFrame (Instance, CacheEntry, ARP_OPCODE_REQUEST); 657772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Status = EFI_NOT_READY; 658772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 659772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffUNLOCK_EXIT: 660772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 661e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 662772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 663772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffSIGNAL_USER: 664772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 665772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((ResolvedEvent != NULL) && (Status == EFI_SUCCESS)) { 666772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff gBS->SignalEvent (ResolvedEvent); 66736ee91ca3661d3d020a7841aacbf858d885c4728vanjeff 66836ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // 66936ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // Dispatch the DPC queued by the NotifyFunction of ResolvedEvent. 67036ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // 671d8d26fb207e02aa5ef57e2bcb213f9dda16166ccmdkinney DispatchDpc (); 672772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 673772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 674772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return Status; 675772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 676772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 677772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 678772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff/** 679772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This function aborts the previous ARP request (identified by This, TargetSwAddress 680772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff and ResolvedEvent) that is issued by EFI_ARP_PROTOCOL.Request(). 681c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 682c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong If the request is in the internal ARP request queue, the request is aborted 683c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong immediately and its ResolvedEvent is signaled. Only an asynchronous address 684c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong request needs to be canceled. If TargeSwAddress and ResolveEvent are both 685c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong NULL, all the pending asynchronous requests that have been issued by This 686c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong instance will be cancelled and their corresponding events will be signaled. 687c6d0ee4b41589bcf5806b457bb3de596d455d4a1jgong 688772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param This Pointer to the EFI_ARP_PROTOCOL instance. 689772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param TargetSwAddress Pointer to the protocol address in previous 690772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff request session. 691772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @param ResolvedEvent Pointer to the event that is used as the 692772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff notification event in previous request session. 693772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 694772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_SUCCESS The pending request session(s) is/are aborted and 695772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff corresponding event(s) is/are signaled. 696772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_INVALID_PARAMETER One or more of the following conditions is TRUE: 697772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff This is NULL. TargetSwAddress is not NULL and 698772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ResolvedEvent is NULL. TargetSwAddress is NULL and 699772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ResolvedEvent is not NULL. 700772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_STARTED The ARP driver instance has not been configured. 701772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff @retval EFI_NOT_FOUND The request is not issued by 702772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff EFI_ARP_PROTOCOL.Request(). 703772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 704772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff**/ 705772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFI_STATUS 706772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffEFIAPI 707772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeffArpCancel ( 708772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_ARP_PROTOCOL *This, 709772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN VOID *TargetSwAddress OPTIONAL, 710772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff IN EFI_EVENT ResolvedEvent OPTIONAL 711772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ) 712772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff{ 713772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ARP_INSTANCE_DATA *Instance; 714772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff UINTN Count; 71536ee91ca3661d3d020a7841aacbf858d885c4728vanjeff EFI_TPL OldTpl; 716772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 717772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if ((This == NULL) || 718772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ((TargetSwAddress != NULL) && (ResolvedEvent == NULL)) || 719772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff ((TargetSwAddress == NULL) && (ResolvedEvent != NULL))) { 720772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_INVALID_PARAMETER; 721772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 722772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 723772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Instance = ARP_INSTANCE_DATA_FROM_THIS (This); 724772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 725772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff if (!Instance->Configured) { 726772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return EFI_NOT_STARTED; 727772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff } 728772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 729e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff OldTpl = gBS->RaiseTPL (TPL_CALLBACK); 730772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 731772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 732772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // Cancel the specified request. 733772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff // 734772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff Count = ArpCancelRequest (Instance, TargetSwAddress, ResolvedEvent); 735772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 73636ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // 73736ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // Dispatch the DPCs queued by the NotifyFunction of the events signaled 73836ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // by ArpCancleRequest. 73936ee91ca3661d3d020a7841aacbf858d885c4728vanjeff // 740d8d26fb207e02aa5ef57e2bcb213f9dda16166ccmdkinney DispatchDpc (); 74136ee91ca3661d3d020a7841aacbf858d885c4728vanjeff 742e48e37fce2611df7a52aff271835ff72ee396d9bvanjeff gBS->RestoreTPL (OldTpl); 743772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff 744772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff return (Count == 0) ? EFI_NOT_FOUND : EFI_SUCCESS; 745772db4bb33ae66fa20e39f786b5f80d107d450a5vanjeff} 746