123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581 |
- /** @file
- Provides the Simple Network functions.
- Copyright (c) 2011 - 2016, Intel Corporation. All rights reserved.
- Copyright (c) 2020, ARM Limited. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent
- **/
- #include "Ax88772.h"
- /**
- This function updates the filtering on the receiver.
- This support routine calls ::Ax88772MacAddressSet to update
- the MAC address. This routine then rebuilds the multicast
- hash by calling ::Ax88772MulticastClear and ::Ax88772MulticastSet.
- Finally this routine enables the receiver by calling
- ::Ax88772RxControl.
- @param [in] SimpleNetwork Simple network mode pointer
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- ReceiveFilterUpdate (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice;
- EFI_STATUS Status;
- UINT32 Index;
- //
- // Set the MAC address
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- Mode = SimpleNetwork->Mode;
- //
- // Clear the multicast hash table
- //
- Ax88772MulticastClear (NicDevice);
- //
- // Load the multicast hash table
- //
- if ((Mode->ReceiveFilterSetting & EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST) != 0) {
- for (Index = 0; Index < Mode->MCastFilterCount; Index++) {
- //
- // Enable the next multicast address
- //
- Ax88772MulticastSet (NicDevice,
- &Mode->MCastFilter[Index].Addr[0]);
- }
- }
- Status = Ax88772RxControl (NicDevice, Mode->ReceiveFilterSetting);
- //
- // Return the operation status
- //
- return Status;
- }
- /**
- This function updates the SNP driver status.
- This function gets the current interrupt and recycled transmit
- buffer status from the network interface. The interrupt status
- and the media status are returned as a bit mask in InterruptStatus.
- If InterruptStatus is NULL, the interrupt status will not be read.
- Upon successful return of the media status, the MediaPresent field
- of EFI_SIMPLE_NETWORK_MODE will be updated to reflect any change
- of media status. If TxBuf is not NULL, a recycled transmit buffer
- address will be retrived. If a recycled transmit buffer address
- is returned in TxBuf, then the buffer has been successfully
- transmitted, and the status for that buffer is cleared.
- This function calls ::Ax88772Rx to update the media status and
- queue any receive packets.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] InterruptStatus A pointer to the bit mask of the current active interrupts.
- If this is NULL, the interrupt status will not be read from
- the device. If this is not NULL, the interrupt status will
- be read from teh device. When the interrupt status is read,
- it will also be cleared. Clearing the transmit interrupt
- does not empty the recycled transmit buffer array.
- @param [out] TxBuf Recycled transmit buffer address. The network interface will
- not transmit if its internal recycled transmit buffer array is
- full. Reading the transmit buffer does not clear the transmit
- interrupt. If this is NULL, then the transmit buffer status
- will not be read. If there are not transmit buffers to recycle
- and TxBuf is not NULL, *TxBuf will be set to NULL.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- **/
- EFI_STATUS
- EFIAPI
- SN_GetStatus (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- OUT UINT32 *InterruptStatus,
- OUT VOID **TxBuf
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice = NULL;
- EFI_STATUS Status = EFI_SUCCESS;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // Return the transmit buffer
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- if ((TxBuf != NULL) && (NicDevice->TxBuffer != NULL)) {
- *TxBuf = NicDevice->TxBuffer;
- NicDevice->TxBuffer = NULL;
- }
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- if ((TxBuf == NULL) && (InterruptStatus == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- #if REPORTLINK
- #else
- if (!NicDevice->LinkUp || !NicDevice->Complete) {
- #endif
- Status = Ax88772NegotiateLinkComplete (NicDevice,
- &NicDevice->PollCount,
- &NicDevice->Complete,
- &NicDevice->LinkUp,
- &NicDevice->LinkSpeed100Mbps,
- &NicDevice->FullDuplex);
- if (EFI_ERROR(Status))
- goto EXIT;
- #if REPORTLINK
- if (NicDevice->LinkUp && NicDevice->Complete) {
- Mode->MediaPresent = TRUE;
- Status = ReceiveFilterUpdate (SimpleNetwork);
- } else {
- Mode->MediaPresent = FALSE;
- }
- #else
- if (NicDevice->LinkUp && NicDevice->Complete) {
- Mode->MediaPresent = TRUE;
- Mode->MediaPresentSupported = FALSE;
- Status = ReceiveFilterUpdate (SimpleNetwork);
- }
- }
- #endif
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR;
- } else {
- Status = EFI_NOT_STARTED ;
- }
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- if (InterruptStatus != NULL) {
- *InterruptStatus = 0;
- }
- EXIT:
- gBS->RestoreTPL(TplPrevious) ;
- return Status;
- }
- /**
- This function performs read and write operations on the NVRAM device
- attached to a network interface.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] ReadWrite TRUE for read operations, FALSE for write operations.
- @param [in] Offset Byte offset in the NVRAM device at which to start the
- read or write operation. This must be a multiple of
- NvRamAccessSize and less than NvRamSize.
- @param [in] BufferSize The number of bytes to read or write from the NVRAM device.
- This must also be a multiple of NvramAccessSize.
- @param [in, out] Buffer A pointer to the data buffer.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_NvData (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN BOOLEAN ReadWrite,
- IN UINTN Offset,
- IN UINTN BufferSize,
- IN OUT VOID *Buffer
- )
- {
- EFI_STATUS Status = EFI_INVALID_PARAMETER;
- EFI_TPL TplPrevious;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice;
- UINTN Index;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- if ((SimpleNetwork == NULL) || (SimpleNetwork->Mode == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized != Mode->State) {
- Status = EFI_NOT_STARTED;
- goto EXIT;
- }
- if (Offset != 0) {
- if (((Offset % Mode->NvRamAccessSize) != 0) ||
- (Offset >= Mode->NvRamSize)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- }
- //
- // Offset must be a multiple of NvRamAccessSize and less than NvRamSize.
- //
- if ((BufferSize % Mode->NvRamAccessSize) != 0) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if (BufferSize + Offset > Mode->NvRamSize) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if (Buffer == NULL) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- //
- // ReadWrite: TRUE FOR READ FALSE FOR WRITE
- //
- if (ReadWrite) {
- for (Index = 0; Index < BufferSize / 2; Index++) {
- Status = Ax88772SromRead (NicDevice,
- (UINT32)(Offset/2 + Index),
- (((UINT16*)Buffer) + Index));
- }
- } else {
- Status = Ax88772EnableSromWrite(NicDevice);
- if (EFI_ERROR(Status))
- goto EXIT;
- for (Index = 0; Index < BufferSize / 2; Index++) {
- Status = Ax88772SromWrite (NicDevice,
- (UINT32)(Offset/2 + Index),
- (((UINT16*)Buffer) + Index));
- }
- Status = Ax88772DisableSromWrite(NicDevice);
- if (BufferSize == 272)
- Status = Ax88772ReloadSrom(NicDevice);
- }
- //
- // Return the operation status
- //
- EXIT:
- gBS->RestoreTPL (TplPrevious);
- return Status;
- }
- /**
- Resets the network adapter and allocates the transmit and receive buffers
- required by the network interface; optionally, also requests allocation of
- additional transmit and receive buffers. This routine must be called before
- any other routine in the Simple Network protocol is called.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] ExtraRxBufferSize Size in bytes to add to the receive buffer allocation
- @param [in] ExtraTxBufferSize Size in bytes to add to the transmit buffer allocation
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_OUT_OF_RESOURCES There was not enough memory for the transmit and receive buffers
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Initialize (
- IN EFI_SIMPLE_NETWORK_PROTOCOL * SimpleNetwork,
- IN UINTN ExtraRxBufferSize,
- IN UINTN ExtraTxBufferSize
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_STATUS Status;
- UINT32 TmpState;
- EFI_TPL TplPrevious;
- NIC_DEVICE *NicDevice;
- TplPrevious = gBS->RaiseTPL (TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // Determine if the interface is already started
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkStarted == Mode->State) {
- if ((0 == ExtraRxBufferSize) && (0 == ExtraTxBufferSize)) {
- //
- // Start the adapter
- //
- TmpState = Mode->State;
- Mode->State = EfiSimpleNetworkInitialized;
- Status = SN_Reset (SimpleNetwork, FALSE);
- if (EFI_ERROR (Status)) {
- //
- // Update the network state
- //
- Mode->State = TmpState; // EfiSimpleNetworkInitialized;
- } else {
- Mode->MediaPresentSupported = TRUE;
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- Mode->MediaPresent = Ax88772GetLinkStatus (NicDevice);
- }
- } else {
- Status = EFI_UNSUPPORTED;
- }
- } else {
- Status = EFI_NOT_STARTED;
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL (TplPrevious);
- return Status;
- }
- /**
- This function converts a multicast IP address to a multicast HW MAC address
- for all packet transactions.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] IPv6 Set to TRUE if the multicast IP address is IPv6 [RFC2460].
- Set to FALSE if the multicast IP address is IPv4 [RFC 791].
- @param [in] IP The multicast IP address that is to be converted to a
- multicast HW MAC address.
- @param [in] MAC The multicast HW MAC address that is to be generated from IP.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_MCastIPtoMAC (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN BOOLEAN IPv6,
- IN EFI_IP_ADDRESS *IP,
- IN EFI_MAC_ADDRESS *MAC
- )
- {
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // The interface must be running
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- if (IP == NULL || MAC == NULL) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if (IPv6) {
- Status = EFI_UNSUPPORTED;
- goto EXIT;
- } else {
- //
- // check if the ip given is a mcast IP
- //
- if ((IP->v4.Addr[0] & 0xF0) != 0xE0) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- } else {
- MAC->Addr[0] = 0x01;
- MAC->Addr[1] = 0x00;
- MAC->Addr[2] = 0x5e;
- MAC->Addr[3] = (UINT8) (IP->v4.Addr[1] & 0x7f);
- MAC->Addr[4] = (UINT8) IP->v4.Addr[2];
- MAC->Addr[5] = (UINT8) IP->v4.Addr[3];
- Status = EFI_SUCCESS;
- }
- }
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR;
- } else {
- Status = EFI_NOT_STARTED ;
- }
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- EXIT:
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- Attempt to receive a packet from the network adapter.
- This function retrieves one packet from the receive queue of the network
- interface. If there are no packets on the receive queue, then EFI_NOT_READY
- will be returned. If there is a packet on the receive queue, and the size
- of the packet is smaller than BufferSize, then the contents of the packet
- will be placed in Buffer, and BufferSize will be udpated with the actual
- size of the packet. In addition, if SrcAddr, DestAddr, and Protocol are
- not NULL, then these values will be extracted from the media header and
- returned. If BufferSize is smaller than the received packet, then the
- size of the receive packet will be placed in BufferSize and
- EFI_BUFFER_TOO_SMALL will be returned.
- This routine calls ::Ax88179Rx to update the media status and
- empty the network adapter of receive packets.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [out] HeaderSize The size, in bytes, of the media header to be filled in by
- the Transmit() function. If HeaderSize is non-zero, then
- it must be equal to SimpleNetwork->Mode->MediaHeaderSize
- and DestAddr and Protocol parameters must not be NULL.
- @param [out] BufferSize The size, in bytes, of the entire packet (media header and
- data) to be transmitted through the network interface.
- @param [out] Buffer A pointer to the packet (media header followed by data) to
- to be transmitted. This parameter can not be NULL. If
- HeaderSize is zero, then the media header is Buffer must
- already be filled in by the caller. If HeaderSize is nonzero,
- then the media header will be filled in by the Transmit()
- function.
- @param [out] SrcAddr The source HW MAC address. If HeaderSize is zero, then
- this parameter is ignored. If HeaderSize is nonzero and
- SrcAddr is NULL, then SimpleNetwork->Mode->CurrentAddress
- is used for the source HW MAC address.
- @param [out] DestAddr The destination HW MAC address. If HeaderSize is zero, then
- this parameter is ignored.
- @param [out] Protocol The type of header to build. If HeaderSize is zero, then
- this parameter is ignored.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_NOT_READY No packets have been received on the network interface.
- @retval EFI_BUFFER_TOO_SMALL The packet is larger than BufferSize bytes.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- **/
- EFI_STATUS
- EFIAPI
- SN_Receive (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- OUT UINTN *HeaderSize,
- OUT UINTN *BufferSize,
- OUT VOID *Buffer,
- OUT EFI_MAC_ADDRESS *SrcAddr,
- OUT EFI_MAC_ADDRESS *DestAddr,
- OUT UINT16 *Protocol
- )
- {
- ETHERNET_HEADER *Header;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice = NULL;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- UINT16 Type;
- UINT16 CurrentPktLen;
- TplPrevious = gBS->RaiseTPL (TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // The interface must be running
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- if ((BufferSize == NULL) || (Buffer == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- gBS->RestoreTPL (TplPrevious);
- return Status;
- }
- //
- // Update the link status
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- if (NicDevice->LinkUp && NicDevice->Complete) {
- if ((HeaderSize != NULL) && (*HeaderSize == 7720)) {
- NicDevice->Grub_f = TRUE;
- }
- if ((NicDevice->Grub_f) && (*HeaderSize != 7720)) {
- gBS->RestoreTPL (TplPrevious);
- return EFI_NOT_READY;
- }
- //
- // Attempt to receive a packet
- //
- if (0 == NicDevice->PktCnt) {
- Status = Ax88772BulkIn(NicDevice);
- if (EFI_ERROR(Status)) {
- goto no_pkt;
- }
- }
- CurrentPktLen = *((UINT16*) (NicDevice->CurPktHdrOff));
- CurrentPktLen &= 0x7ff;
- if ((60 <= CurrentPktLen) &&
- (CurrentPktLen - 14 <= MAX_ETHERNET_PKT_SIZE)) {
- if (*BufferSize < (UINTN)CurrentPktLen) {
- gBS->RestoreTPL (TplPrevious);
- return EFI_BUFFER_TOO_SMALL;
- }
- *BufferSize = CurrentPktLen;
- CopyMem (Buffer, NicDevice->CurPktOff, CurrentPktLen);
- Header = (ETHERNET_HEADER *) NicDevice->CurPktOff;
- if ((HeaderSize != NULL) && (*HeaderSize != 7720)) {
- *HeaderSize = sizeof (*Header);
- }
- if (DestAddr != NULL) {
- CopyMem (DestAddr, &Header->DestAddr, PXE_HWADDR_LEN_ETHER);
- }
- if (SrcAddr != NULL) {
- CopyMem (SrcAddr, &Header->SrcAddr, PXE_HWADDR_LEN_ETHER);
- }
- if (Protocol != NULL) {
- Type = Header->Type;
- Type = (UINT16)((Type >> 8) | (Type << 8));
- *Protocol = Type;
- }
- NicDevice->PktCnt--;
- NicDevice->CurPktHdrOff += (CurrentPktLen + 4 + 1) & 0xfffe;
- NicDevice->CurPktOff = NicDevice->CurPktHdrOff + 4;
- Status = EFI_SUCCESS;
- } else {
- NicDevice->PktCnt = 0;
- Status = EFI_DEVICE_ERROR;
- }
- } else {
- //
- // Link no up
- //
- Status = EFI_NOT_READY;
- }
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR;
- } else {
- Status = EFI_NOT_STARTED;
- }
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- no_pkt:
- gBS->RestoreTPL (TplPrevious);
- return Status;
- }
- /**
- This function is used to enable and disable the hardware and software receive
- filters for the underlying network device.
- The receive filter change is broken down into three steps:
- 1. The filter mask bits that are set (ON) in the Enable parameter
- are added to the current receive filter settings.
- 2. The filter mask bits that are set (ON) in the Disable parameter
- are subtracted from the updated receive filter settins.
- 3. If the resulting filter settigns is not supported by the hardware
- a more liberal setting is selected.
- If the same bits are set in the Enable and Disable parameters, then the bits
- in the Disable parameter takes precedence.
- If the ResetMCastFilter parameter is TRUE, then the multicast address list
- filter is disabled (irregardless of what other multicast bits are set in
- the enable and Disable parameters). The SNP->Mode->MCastFilterCount field
- is set to zero. The SNP->Mode->MCastFilter contents are undefined.
- After enableing or disabling receive filter settings, software should
- verify the new settings by checking the SNP->Mode->ReceeiveFilterSettings,
- SNP->Mode->MCastFilterCount and SNP->Mode->MCastFilter fields.
- Note: Some network drivers and/or devices will automatically promote
- receive filter settings if the requested setting can not be honored.
- For example, if a request for four multicast addresses is made and
- the underlying hardware only supports two multicast addresses the
- driver might set the promiscuous or promiscuous multicast receive filters
- instead. The receiving software is responsible for discarding any extra
- packets that get through the hardware receive filters.
- If ResetMCastFilter is TRUE, then the multicast receive filter list
- on the network interface will be reset to the default multicast receive
- filter list. If ResetMCastFilter is FALSE, and this network interface
- allows the multicast receive filter list to be modified, then the
- MCastFilterCnt and MCastFilter are used to update the current multicast
- receive filter list. The modified receive filter list settings can be
- found in the MCastFilter field of EFI_SIMPLE_NETWORK_MODE.
- This routine calls ::ReceiveFilterUpdate to update the receive
- state in the network adapter.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] Enable A bit mask of receive filters to enable on the network interface.
- @param [in] Disable A bit mask of receive filters to disable on the network interface.
- For backward compatibility with EFI 1.1 platforms, the
- EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST bit must be set
- when the ResetMCastFilter parameter is TRUE.
- @param [in] ResetMCastFilter Set to TRUE to reset the contents of the multicast receive
- filters on the network interface to their default values.
- @param [in] MCastFilterCnt Number of multicast HW MAC address in the new MCastFilter list.
- This value must be less than or equal to the MaxMCastFilterCnt
- field of EFI_SIMPLE_NETWORK_MODE. This field is optional if
- ResetMCastFilter is TRUE.
- @param [in] MCastFilter A pointer to a list of new multicast receive filter HW MAC
- addresses. This list will replace any existing multicast
- HW MAC address list. This field is optional if ResetMCastFilter
- is TRUE.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_ReceiveFilters (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN UINT32 Enable,
- IN UINT32 Disable,
- IN BOOLEAN ResetMCastFilter,
- IN UINTN MCastFilterCnt,
- IN EFI_MAC_ADDRESS *MCastFilter
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_STATUS Status = EFI_SUCCESS;
- EFI_TPL TplPrevious;
- UINTN Index;
- UINT8 Temp;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- Mode = SimpleNetwork->Mode;
- if (SimpleNetwork == NULL) {
- gBS->RestoreTPL(TplPrevious);
- return EFI_INVALID_PARAMETER;
- }
- switch (Mode->State) {
- case EfiSimpleNetworkInitialized:
- break;
- case EfiSimpleNetworkStopped:
- Status = EFI_NOT_STARTED;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- default:
- Status = EFI_DEVICE_ERROR;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- //
- // check if we are asked to enable or disable something that the SNP
- // does not even support!
- //
- if (((Enable &~Mode->ReceiveFilterMask) != 0) ||
- ((Disable &~Mode->ReceiveFilterMask) != 0)) {
- Status = EFI_INVALID_PARAMETER;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- if (ResetMCastFilter) {
- if ((0 == (Mode->ReceiveFilterSetting & EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST)) &&
- Enable == 0 &&
- Disable == 2) {
- gBS->RestoreTPL(TplPrevious);
- return EFI_SUCCESS;
- }
- Mode->MCastFilterCount = 0;
- SetMem (&Mode->MCastFilter[0],
- sizeof(EFI_MAC_ADDRESS) * MAX_MCAST_FILTER_CNT,
- 0);
- } else {
- if (MCastFilterCnt != 0) {
- EFI_MAC_ADDRESS * MulticastAddress;
- MulticastAddress = MCastFilter;
- if ((MCastFilterCnt > Mode->MaxMCastFilterCount) ||
- (MCastFilter == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- for (Index = 0 ; Index < MCastFilterCnt ; Index++) {
- Temp = MulticastAddress->Addr[0];
- if ((Temp & 0x01) != 0x01) {
- gBS->RestoreTPL(TplPrevious);
- return EFI_INVALID_PARAMETER;
- }
- MulticastAddress++;
- }
- Mode->MCastFilterCount = (UINT32)MCastFilterCnt;
- CopyMem (&Mode->MCastFilter[0],
- MCastFilter,
- MCastFilterCnt * sizeof (EFI_MAC_ADDRESS));
- }
- }
- if (Enable == 0 && Disable == 0 && !ResetMCastFilter && MCastFilterCnt == 0) {
- Status = EFI_SUCCESS;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- if ((Enable & EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST) != 0 && MCastFilterCnt == 0) {
- Status = EFI_INVALID_PARAMETER;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- Mode->ReceiveFilterSetting |= Enable;
- Mode->ReceiveFilterSetting &= ~Disable;
- Status = ReceiveFilterUpdate (SimpleNetwork);
- if (EFI_DEVICE_ERROR == Status || EFI_INVALID_PARAMETER == Status)
- Status = EFI_SUCCESS;
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- Reset the network adapter.
- Resets a network adapter and reinitializes it with the parameters that
- were provided in the previous call to Initialize (). The transmit and
- receive queues are cleared. Receive filters, the station address, the
- statistics, and the multicast-IP-to-HW MAC addresses are not reset by
- this call.
- This routine calls ::Ax88772Reset to perform the adapter specific
- reset operation. This routine also starts the link negotiation
- by calling ::Ax88772NegotiateLinkStart.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] ExtendedVerification Indicates that the driver may perform a more
- exhaustive verification operation of the device
- during reset.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Reset (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN BOOLEAN ExtendedVerification
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- //
- // Update the device state
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- //
- // Reset the device
- //
- if (!NicDevice->FirstRst) {
- Status = EFI_SUCCESS;
- } else {
- Status = Ax88772Reset (NicDevice);
- if (!EFI_ERROR (Status)) {
- Status = ReceiveFilterUpdate (SimpleNetwork);
- if (!EFI_ERROR (Status) && !NicDevice->LinkUp && NicDevice->FirstRst) {
- Status = Ax88772NegotiateLinkStart (NicDevice);
- NicDevice->FirstRst = FALSE;
- }
- }
- }
- } else {
- Status = EFI_NOT_STARTED;
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- Initialize the simple network protocol.
- This routine calls ::Ax88772MacAddressGet to obtain the
- MAC address.
- @param [in] NicDevice NIC_DEVICE_INSTANCE pointer
- @retval EFI_SUCCESS Setup was successful
- **/
- EFI_STATUS
- SN_Setup (
- IN NIC_DEVICE *NicDevice
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork;
- EFI_STATUS Status;
- //
- // Initialize the simple network protocol
- //
- SimpleNetwork = &NicDevice->SimpleNetwork;
- SimpleNetwork->Revision = EFI_SIMPLE_NETWORK_PROTOCOL_REVISION;
- SimpleNetwork->Start = SN_Start;
- SimpleNetwork->Stop = SN_Stop;
- SimpleNetwork->Initialize = SN_Initialize;
- SimpleNetwork->Reset = SN_Reset;
- SimpleNetwork->Shutdown = SN_Shutdown;
- SimpleNetwork->ReceiveFilters = SN_ReceiveFilters;
- SimpleNetwork->StationAddress = SN_StationAddress;
- SimpleNetwork->Statistics = SN_Statistics;
- SimpleNetwork->MCastIpToMac = SN_MCastIPtoMAC;
- SimpleNetwork->NvData = SN_NvData;
- SimpleNetwork->GetStatus = SN_GetStatus;
- SimpleNetwork->Transmit = SN_Transmit;
- SimpleNetwork->Receive = SN_Receive;
- SimpleNetwork->WaitForPacket = NULL;
- Mode = &NicDevice->SimpleNetworkData;
- SimpleNetwork->Mode = Mode;
- Mode->State = EfiSimpleNetworkStopped;
- Mode->HwAddressSize = PXE_HWADDR_LEN_ETHER;
- Mode->MediaHeaderSize = sizeof (ETHERNET_HEADER);
- Mode->MaxPacketSize = MAX_ETHERNET_PKT_SIZE;
- Mode->ReceiveFilterMask = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST
- | EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST
- | EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST
- | EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS
- | EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST;
- Mode->ReceiveFilterSetting = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST
- | EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST;
- Mode->MaxMCastFilterCount = ASIX_MCAST_FILTER_CNT;
- Mode->MCastFilterCount = 0;
- Mode->NvRamSize = 512;
- Mode->NvRamAccessSize = 2;
- SetMem (&Mode->BroadcastAddress,
- PXE_HWADDR_LEN_ETHER,
- 0xff);
- SetMem (&Mode->MCastFilter[0],
- sizeof(EFI_MAC_ADDRESS) * MAX_MCAST_FILTER_CNT,
- 0);
- Mode->IfType = NET_IFTYPE_ETHERNET;
- Mode->MacAddressChangeable = TRUE;
- Mode->MultipleTxSupported = FALSE;
- Mode->MediaPresentSupported = TRUE;
- Mode->MediaPresent = FALSE;
- //
- // Read the MAC address
- //
- NicDevice->PhyId = PHY_ID_INTERNAL;
- NicDevice->LinkSpeed100Mbps = TRUE;
- NicDevice->FullDuplex = TRUE;
- NicDevice->Complete = FALSE;
- NicDevice->LinkUp = FALSE;
- NicDevice->Grub_f = FALSE;
- NicDevice->FirstRst = TRUE;
- NicDevice->PktCnt = 0;
- Status = Ax88772MacAddressGet (
- NicDevice,
- &Mode->PermanentAddress.Addr[0]);
- if (EFI_ERROR (Status)) {
- return Status;
- }
- //
- // Use the hardware address as the current address
- //
- CopyMem (&Mode->CurrentAddress,
- &Mode->PermanentAddress,
- PXE_HWADDR_LEN_ETHER);
- CopyMem (&NicDevice->MAC,
- &Mode->PermanentAddress,
- PXE_HWADDR_LEN_ETHER);
- Status = gBS->AllocatePool (EfiBootServicesData,
- AX88772_MAX_BULKIN_SIZE,
- (VOID **) &NicDevice->BulkInbuf);
- if (EFI_ERROR (Status)) {
- return Status;
- }
- Status = gBS->AllocatePool (EfiBootServicesData,
- sizeof (RX_TX_PACKET),
- (VOID **) &NicDevice->TxTest);
- if (EFI_ERROR (Status)) {
- gBS->FreePool (NicDevice->BulkInbuf);
- return Status;
- }
- //
- // Return the setup status
- //
- return Status;
- }
- /**
- This routine starts the network interface.
- @param [in] SimpleNetwork Protocol instance pointer
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_ALREADY_STARTED The network interface was already started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Start (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork
- )
- {
- NIC_DEVICE *NicDevice;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- Status = EFI_INVALID_PARAMETER;
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkStopped == Mode->State) {
- //
- // Initialize the mode structure
- // NVRAM access is not supported
- //
- ZeroMem (Mode, sizeof (*Mode));
- Mode->State = EfiSimpleNetworkStarted;
- Mode->HwAddressSize = PXE_HWADDR_LEN_ETHER;
- Mode->MediaHeaderSize = sizeof (ETHERNET_HEADER);
- Mode->MaxPacketSize = MAX_ETHERNET_PKT_SIZE;
- Mode->ReceiveFilterMask = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST
- | EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST
- | EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST
- | EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS
- | EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST;
- Mode->ReceiveFilterSetting = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST;
- Mode->MaxMCastFilterCount = ASIX_MCAST_FILTER_CNT;
- Mode->MCastFilterCount = 0;
- SetMem (&Mode->MCastFilter[0],
- sizeof(EFI_MAC_ADDRESS) * MAX_MCAST_FILTER_CNT,
- 0);
- Mode->NvRamSize = 512;
- Mode->NvRamAccessSize = 2;
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- Status = Ax88772MacAddressGet (NicDevice, &Mode->PermanentAddress.Addr[0]);
- CopyMem (&Mode->CurrentAddress,
- &Mode->PermanentAddress,
- sizeof (Mode->CurrentAddress));
- SetMem(&Mode->BroadcastAddress, PXE_HWADDR_LEN_ETHER, 0xff);
- Mode->IfType = NET_IFTYPE_ETHERNET;
- Mode->MacAddressChangeable = TRUE;
- Mode->MultipleTxSupported = FALSE;
- Mode->MediaPresentSupported = TRUE;
- Mode->MediaPresent = FALSE;
- } else {
- Status = EFI_ALREADY_STARTED;
- }
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- Set the MAC address.
- This function modifies or resets the current station address of a
- network interface. If Reset is TRUE, then the current station address
- is set ot the network interface's permanent address. If Reset if FALSE
- then the current station address is changed to the address specified by
- New.
- This routine calls ::Ax88772MacAddressSet to update the MAC address
- in the network adapter.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] Reset Flag used to reset the station address to the
- network interface's permanent address.
- @param [in] New New station address to be used for the network
- interface.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_StationAddress (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN BOOLEAN Reset,
- IN EFI_MAC_ADDRESS *New
- )
- {
- NIC_DEVICE *NicDevice;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) &&
- (SimpleNetwork->Mode != NULL) &&
- ((!Reset) || (Reset && (New != NULL)))) {
- //
- // Verify that the adapter is already started
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- //
- // Determine the adapter MAC address
- //
- if (Reset) {
- //
- // Use the permanent address
- //
- CopyMem (&Mode->CurrentAddress,
- &Mode->PermanentAddress,
- sizeof (Mode->CurrentAddress));
- } else {
- //
- // Use the specified address
- //
- CopyMem (&Mode->CurrentAddress,
- New,
- sizeof (Mode->CurrentAddress));
- }
- //
- // Update the address on the adapter
- //
- Status = Ax88772MacAddressSet (NicDevice, &Mode->CurrentAddress.Addr[0]);
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR; ;
- } else {
- Status = EFI_NOT_STARTED ;
- }
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- This function resets or collects the statistics on a network interface.
- If the size of the statistics table specified by StatisticsSize is not
- big enough for all of the statistics that are collected by the network
- interface, then a partial buffer of statistics is returned in
- StatisticsTable.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] Reset Set to TRUE to reset the statistics for the network interface.
- @param [in, out] StatisticsSize On input the size, in bytes, of StatisticsTable. On output
- the size, in bytes, of the resulting table of statistics.
- @param [out] StatisticsTable A pointer to the EFI_NETWORK_STATISTICS structure that
- conains the statistics.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_BUFFER_TOO_SMALL The StatisticsTable is NULL or the buffer is too small.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Statistics (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN BOOLEAN Reset,
- IN OUT UINTN *StatisticsSize,
- OUT EFI_NETWORK_STATISTICS *StatisticsTable
- )
- {
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- if ((StatisticsSize != NULL) && (*StatisticsSize == 0)) {
- Status = EFI_BUFFER_TOO_SMALL;
- goto EXIT;
- }
- if(Reset) {
- Status = EFI_SUCCESS;
- } else {
- Status = EFI_SUCCESS;
- }
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR; ;
- } else {
- Status = EFI_NOT_STARTED ;
- }
- }
- //
- // This is not currently supported
- //
- EXIT:
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- This function stops a network interface. This call is only valid
- if the network interface is in the started state.
- @param [in] SimpleNetwork Protocol instance pointer
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Stop (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // Determine if the interface is started
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkStarted == Mode->State) {
- Mode->State = EfiSimpleNetworkStopped;
- Status = EFI_SUCCESS;
- } else {
- Status = EFI_NOT_STARTED;
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- This function releases the memory buffers assigned in the Initialize() call.
- Ending transmits and receives are lost, and interrupts are cleared and disabled.
- After this call, only Initialize() and Stop() calls may be used.
- @param [in] SimpleNetwork Protocol instance pointer
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- @retval EFI_UNSUPPORTED The increased buffer size feature is not supported.
- **/
- EFI_STATUS
- EFIAPI
- SN_Shutdown (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork
- )
- {
- EFI_SIMPLE_NETWORK_MODE *Mode;
- UINT32 RxFilter;
- EFI_STATUS Status;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // Determine if the interface is already started
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- //
- // Stop the adapter
- //
- RxFilter = Mode->ReceiveFilterSetting;
- Mode->ReceiveFilterSetting = 0;
- Status = SN_Reset (SimpleNetwork, FALSE);
- Mode->ReceiveFilterSetting = RxFilter;
- if (!EFI_ERROR (Status)) {
- //
- // Update the network state
- //
- Mode->State = EfiSimpleNetworkStarted;
- } else if (EFI_DEVICE_ERROR == Status) {
- Mode->State = EfiSimpleNetworkStopped;
- }
- } else {
- Status = EFI_NOT_STARTED;
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- //
- // Return the operation status
- //
- gBS->RestoreTPL(TplPrevious);
- return Status;
- }
- /**
- Send a packet over the network.
- This function places the packet specified by Header and Buffer on
- the transmit queue. This function performs a non-blocking transmit
- operation. When the transmit is complete, the buffer is returned
- via the GetStatus() call.
- This routine calls ::Ax88772Rx to empty the network adapter of
- receive packets. The routine then passes the transmit packet
- to the network adapter.
- @param [in] SimpleNetwork Protocol instance pointer
- @param [in] HeaderSize The size, in bytes, of the media header to be filled in by
- the Transmit() function. If HeaderSize is non-zero, then
- it must be equal to SimpleNetwork->Mode->MediaHeaderSize
- and DestAddr and Protocol parameters must not be NULL.
- @param [in] BufferSize The size, in bytes, of the entire packet (media header and
- data) to be transmitted through the network interface.
- @param [in] Buffer A pointer to the packet (media header followed by data) to
- to be transmitted. This parameter can not be NULL. If
- HeaderSize is zero, then the media header is Buffer must
- already be filled in by the caller. If HeaderSize is nonzero,
- then the media header will be filled in by the Transmit()
- function.
- @param [in] SrcAddr The source HW MAC address. If HeaderSize is zero, then
- this parameter is ignored. If HeaderSize is nonzero and
- SrcAddr is NULL, then SimpleNetwork->Mode->CurrentAddress
- is used for the source HW MAC address.
- @param [in] DestAddr The destination HW MAC address. If HeaderSize is zero, then
- this parameter is ignored.
- @param [in] Protocol The type of header to build. If HeaderSize is zero, then
- this parameter is ignored.
- @retval EFI_SUCCESS This operation was successful.
- @retval EFI_NOT_STARTED The network interface was not started.
- @retval EFI_NOT_READY The network interface is too busy to accept this transmit request.
- @retval EFI_BUFFER_TOO_SMALL The BufferSize parameter is too small.
- @retval EFI_INVALID_PARAMETER SimpleNetwork parameter was NULL or did not point to a valid
- EFI_SIMPLE_NETWORK_PROTOCOL structure.
- @retval EFI_DEVICE_ERROR The command could not be sent to the network interface.
- **/
- EFI_STATUS
- EFIAPI
- SN_Transmit (
- IN EFI_SIMPLE_NETWORK_PROTOCOL *SimpleNetwork,
- IN UINTN HeaderSize,
- IN UINTN BufferSize,
- IN VOID *Buffer,
- IN EFI_MAC_ADDRESS *SrcAddr,
- IN EFI_MAC_ADDRESS *DestAddr,
- IN UINT16 *Protocol
- )
- {
- ETHERNET_HEADER *Header;
- EFI_SIMPLE_NETWORK_MODE *Mode;
- NIC_DEVICE *NicDevice;
- EFI_USB_IO_PROTOCOL *UsbIo;
- EFI_STATUS Status;
- UINTN TransferLength;
- UINT32 TransferStatus;
- UINT16 Type;
- EFI_TPL TplPrevious;
- TplPrevious = gBS->RaiseTPL(TPL_CALLBACK);
- //
- // Verify the parameters
- //
- if ((SimpleNetwork != NULL) && (SimpleNetwork->Mode != NULL)) {
- //
- // The interface must be running
- //
- Mode = SimpleNetwork->Mode;
- if (EfiSimpleNetworkInitialized == Mode->State) {
- //
- // Update the link status
- //
- NicDevice = DEV_FROM_SIMPLE_NETWORK (SimpleNetwork);
- //
- // Release the synchronization with Ax88772Timer
- //
- if (NicDevice->LinkUp && NicDevice->Complete) {
- //
- // Copy the packet into the USB buffer
- //
- if ((HeaderSize != 0) && (Mode->MediaHeaderSize != HeaderSize)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if (BufferSize < Mode->MediaHeaderSize) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if (Buffer == NULL) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if ((HeaderSize != 0) && (DestAddr == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- if ((HeaderSize != 0) && (Protocol == NULL)) {
- Status = EFI_INVALID_PARAMETER;
- goto EXIT;
- }
- CopyMem (&NicDevice->TxTest->Data[0], Buffer, BufferSize);
- NicDevice->TxTest->Length = (UINT16) BufferSize;
- //
- // Transmit the packet
- //
- Header = (ETHERNET_HEADER *) &NicDevice->TxTest->Data[0];
- if (HeaderSize != 0) {
- if (DestAddr != NULL) {
- CopyMem (&Header->DestAddr, DestAddr, PXE_HWADDR_LEN_ETHER);
- }
- if (SrcAddr != NULL) {
- CopyMem (&Header->SrcAddr, SrcAddr, PXE_HWADDR_LEN_ETHER);
- } else {
- CopyMem (&Header->SrcAddr, &Mode->CurrentAddress.Addr[0], PXE_HWADDR_LEN_ETHER);
- }
- if (Protocol != NULL) {
- Type = *Protocol;
- } else {
- Type = NicDevice->TxTest->Length;
- }
- Type = (UINT16)((Type >> 8) | (Type << 8));
- Header->Type = Type;
- }
- if (NicDevice->TxTest->Length < MIN_ETHERNET_PKT_SIZE) {
- NicDevice->TxTest->Length = MIN_ETHERNET_PKT_SIZE;
- ZeroMem (&NicDevice->TxTest->Data[BufferSize],
- NicDevice->TxTest->Length - BufferSize);
- }
- NicDevice->TxTest->LengthBar = ~(NicDevice->TxTest->Length);
- TransferLength = sizeof (NicDevice->TxTest->Length)
- + sizeof (NicDevice->TxTest->LengthBar)
- + NicDevice->TxTest->Length;
- if (TransferLength % 512 == 0 || TransferLength % 1024 == 0)
- TransferLength +=4;
- #if RXTHOU
- if (NicDevice->RxBurst == 1)
- NicDevice->RxBurst--;
- #endif
- //
- // Work around USB bus driver bug where a timeout set by receive
- // succeeds but the timeout expires immediately after, causing the
- // transmit operation to timeout.
- //
- UsbIo = NicDevice->UsbIo;
- Status = UsbIo->UsbBulkTransfer (UsbIo,
- BULK_OUT_ENDPOINT,
- &NicDevice->TxTest->Length,
- &TransferLength,
- 0xfffffffe,
- &TransferStatus);
- if (EFI_SUCCESS == Status) {
- Status = TransferStatus;
- }
- if (EFI_SUCCESS == Status && EFI_SUCCESS == TransferStatus) {
- NicDevice->TxBuffer = Buffer;
- } else {
- if (EFI_DEVICE_ERROR == Status) {
- SN_Reset (SimpleNetwork, FALSE);
- }
- Status = EFI_NOT_READY;
- }
- } else {
- //
- // No packets available.
- //
- Status = EFI_NOT_READY;
- }
- } else {
- if (EfiSimpleNetworkStarted == Mode->State) {
- Status = EFI_DEVICE_ERROR;
- } else {
- Status = EFI_NOT_STARTED;
- }
- }
- } else {
- Status = EFI_INVALID_PARAMETER;
- }
- EXIT:
- gBS->RestoreTPL (TplPrevious);
- return Status;
- }
|