iPXE
Data Structures | Functions | Variables
efi_snp.c File Reference
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <assert.h>
#include <byteswap.h>
#include <ipxe/netdevice.h>
#include <ipxe/vlan.h>
#include <ipxe/iobuf.h>
#include <ipxe/in.h>
#include <ipxe/version.h>
#include <ipxe/console.h>
#include <ipxe/efi/efi.h>
#include <ipxe/efi/efi_driver.h>
#include <ipxe/efi/efi_strings.h>
#include <ipxe/efi/efi_path.h>
#include <ipxe/efi/efi_utils.h>
#include <ipxe/efi/efi_watchdog.h>
#include <ipxe/efi/efi_null.h>
#include <ipxe/efi/efi_snp.h>
#include <usr/autoboot.h>
#include <config/general.h>

Go to the source code of this file.

Data Structures

union  PXE_CPB_ANY
 Union type for command parameter blocks. More...
 
union  PXE_DB_ANY
 Union type for data blocks. More...
 

Functions

 FILE_LICENCE (GPL2_OR_LATER)
 
 FILE_SECBOOT (PERMITTED)
 
static LIST_HEAD (efi_snp_devices)
 List of SNP devices. More...
 
static void efi_snp_set_state (struct efi_snp_device *snpdev)
 Set EFI SNP mode state. More...
 
static void efi_snp_set_mode (struct efi_snp_device *snpdev)
 Set EFI SNP mode based on iPXE net device parameters. More...
 
static void efi_snp_flush (struct efi_snp_device *snpdev)
 Flush transmit ring and receive queue. More...
 
static void efi_snp_poll (struct efi_snp_device *snpdev)
 Poll net device and count received packets. More...
 
static EFI_STATUS EFIAPI efi_snp_start (EFI_SIMPLE_NETWORK_PROTOCOL *snp)
 Change SNP state from "stopped" to "started". More...
 
static EFI_STATUS EFIAPI efi_snp_stop (EFI_SIMPLE_NETWORK_PROTOCOL *snp)
 Change SNP state from "started" to "stopped". More...
 
static EFI_STATUS EFIAPI efi_snp_initialize (EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN extra_rx_bufsize, UINTN extra_tx_bufsize)
 Open the network device. More...
 
static EFI_STATUS EFIAPI efi_snp_reset (EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN ext_verify)
 Reset the network device. More...
 
static EFI_STATUS EFIAPI efi_snp_shutdown (EFI_SIMPLE_NETWORK_PROTOCOL *snp)
 Shut down the network device. More...
 
static EFI_STATUS EFIAPI efi_snp_receive_filters (EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINT32 enable, UINT32 disable, BOOLEAN mcast_reset, UINTN mcast_count, EFI_MAC_ADDRESS *mcast)
 Manage receive filters. More...
 
static EFI_STATUS EFIAPI efi_snp_station_address (EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN reset, EFI_MAC_ADDRESS *new)
 Set station address. More...
 
static EFI_STATUS EFIAPI efi_snp_statistics (EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN reset, UINTN *stats_len, EFI_NETWORK_STATISTICS *stats)
 Get (or reset) statistics. More...
 
static EFI_STATUS EFIAPI efi_snp_mcast_ip_to_mac (EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN ipv6, EFI_IP_ADDRESS *ip, EFI_MAC_ADDRESS *mac)
 Convert multicast IP address to MAC address. More...
 
static EFI_STATUS EFIAPI efi_snp_nvdata (EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN read, UINTN offset, UINTN len, VOID *data)
 Read or write non-volatile storage. More...
 
static EFI_STATUS EFIAPI efi_snp_get_status (EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINT32 *interrupts, VOID **txbuf)
 Read interrupt status and TX recycled buffer status. More...
 
static EFI_STATUS EFIAPI efi_snp_transmit (EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN ll_header_len, UINTN len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
 Start packet transmission. More...
 
static EFI_STATUS EFIAPI efi_snp_receive (EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN *ll_header_len, UINTN *len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
 Receive packet. More...
 
static VOID EFIAPI efi_snp_wait_for_packet (EFI_EVENT event __unused, VOID *context)
 Poll event. More...
 
static uint8_t efi_undi_checksum (void *data, size_t len)
 Calculate UNDI byte checksum. More...
 
static unsigned int efi_undi_ifnum (struct efi_snp_device *snpdev)
 Get UNDI SNP device interface number. More...
 
static struct efi_snp_deviceefi_undi_snpdev (unsigned int ifnum)
 Identify UNDI SNP device. More...
 
static PXE_STATCODE efi_undi_statcode (EFI_STATUS efirc)
 Convert EFI status code to UNDI status code. More...
 
static EFI_STATUS efi_undi_get_state (struct efi_snp_device *snpdev, PXE_CDB *cdb)
 Get state. More...
 
static EFI_STATUS efi_undi_start (struct efi_snp_device *snpdev)
 Start. More...
 
static EFI_STATUS efi_undi_stop (struct efi_snp_device *snpdev)
 Stop. More...
 
static EFI_STATUS efi_undi_get_init_info (struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_DB_GET_INIT_INFO *db)
 Get initialisation information. More...
 
static EFI_STATUS efi_undi_initialize (struct efi_snp_device *snpdev, PXE_CDB *cdb)
 Initialise. More...
 
static EFI_STATUS efi_undi_reset (struct efi_snp_device *snpdev)
 Reset. More...
 
static EFI_STATUS efi_undi_shutdown (struct efi_snp_device *snpdev)
 Shutdown. More...
 
static EFI_STATUS efi_undi_receive_filters (struct efi_snp_device *snpdev, PXE_CDB *cdb)
 Get/set receive filters. More...
 
static EFI_STATUS efi_undi_station_address (struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_CPB_STATION_ADDRESS *cpb, PXE_DB_STATION_ADDRESS *db)
 Get/set station address. More...
 
static EFI_STATUS efi_undi_get_status (struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_DB_GET_STATUS *db)
 Get interrupt status. More...
 
static EFI_STATUS efi_undi_fill_header (struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_CPB_ANY *cpb)
 Fill header. More...
 
static EFI_STATUS efi_undi_transmit (struct efi_snp_device *snpdev, PXE_CPB_TRANSMIT *cpb)
 Transmit. More...
 
static EFI_STATUS efi_undi_receive (struct efi_snp_device *snpdev, PXE_CPB_RECEIVE *cpb, PXE_DB_RECEIVE *db)
 Receive. More...
 
static EFIAPI VOID efi_undi_issue (UINT64 cdb_phys)
 UNDI entry point. More...
 
static EFI_STATUS EFIAPI efi_vlan_set (EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 tag, UINT8 priority)
 Create or modify VLAN device. More...
 
static EFI_STATUS EFIAPI efi_vlan_find (EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 *filter, UINT16 *count, EFI_VLAN_FIND_DATA **entries)
 Find VLAN device(s) More...
 
static EFI_STATUS EFIAPI efi_vlan_remove (EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 tag)
 Remove VLAN device. More...
 
static EFI_STATUS EFIAPI efi_snp_get_driver_name (EFI_COMPONENT_NAME2_PROTOCOL *name2, CHAR8 *language __unused, CHAR16 **driver_name)
 Look up driver name. More...
 
static EFI_STATUS EFIAPI efi_snp_get_controller_name (EFI_COMPONENT_NAME2_PROTOCOL *name2, EFI_HANDLE device __unused, EFI_HANDLE child __unused, CHAR8 *language __unused, CHAR16 **controller_name)
 Look up controller name. More...
 
static EFI_STATUS EFIAPI efi_snp_load_file (EFI_LOAD_FILE_PROTOCOL *load_file, EFI_DEVICE_PATH_PROTOCOL *path __unused, BOOLEAN booting, UINTN *len __unused, VOID *data __unused)
 Load file. More...
 
static struct efi_snp_deviceefi_snp_demux (struct net_device *netdev)
 Locate SNP device corresponding to network device. More...
 
static int efi_snp_probe (struct net_device *netdev, void *priv __unused)
 Create SNP device. More...
 
static void efi_snp_notify (struct net_device *netdev, void *priv __unused)
 Handle SNP device or link state change. More...
 
static void efi_snp_remove (struct net_device *netdev, void *priv __unused)
 Destroy SNP device. More...
 
struct efi_snp_devicefind_snpdev (EFI_HANDLE handle)
 Find SNP device by EFI device handle. More...
 
struct efi_snp_devicelast_opened_snpdev (void)
 Get most recently opened SNP device. More...
 
void efi_snp_add_claim (int delta)
 Add to SNP claimed/released count. More...
 

Variables

static int efi_snp_claimed
 Network devices are currently claimed for use by iPXE. More...
 
static struct efi_saved_tpl efi_snp_saved_tpl
 TPL prior to network devices being claimed. More...
 
static EFI_SIMPLE_NETWORK_PROTOCOL efi_snp_device_snp
 SNP interface. More...
 
static PXE_SW_UNDI efi_snp_undi
 UNDI interface. More...
 
static EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL efi_snp_device_nii
 Network Identification Interface (NII) More...
 
static EFI_VLAN_CONFIG_PROTOCOL efi_vlan
 VLAN configuration protocol. More...
 
static EFI_LOAD_FILE_PROTOCOL efi_snp_load_file_protocol
 Load file protocol. More...
 
struct net_driver efi_snp_driver __net_driver
 SNP driver. More...
 

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( GPL2_OR_LATER  )

◆ FILE_SECBOOT()

FILE_SECBOOT ( PERMITTED  )

◆ LIST_HEAD()

static LIST_HEAD ( efi_snp_devices  )
static

List of SNP devices.

◆ efi_snp_set_state()

static void efi_snp_set_state ( struct efi_snp_device snpdev)
static

Set EFI SNP mode state.

Parameters
snpSNP interface

Definition at line 92 of file efi_snp.c.

92  {
93  struct net_device *netdev = snpdev->netdev;
94  EFI_SIMPLE_NETWORK_MODE *mode = &snpdev->mode;
95 
96  /* Calculate state */
97  if ( ! snpdev->started ) {
98  /* Start() method not called; report as Stopped */
100  } else if ( ! netdev_is_open ( netdev ) ) {
101  /* Network device not opened; report as Started */
102  mode->State = EfiSimpleNetworkStarted;
103  } else if ( efi_snp_claimed ) {
104  /* Network device opened but claimed for use by iPXE; report
105  * as Started to inhibit receive polling.
106  */
107  mode->State = EfiSimpleNetworkStarted;
108  } else {
109  /* Network device opened and available for use via SNP; report
110  * as Initialized.
111  */
113  }
114 }
int started
Started flag.
Definition: efi_snp.h:43
uint16_t mode
Acceleration mode.
Definition: ena.h:26
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
static int netdev_is_open(struct net_device *netdev)
Check whether or not network device is open.
Definition: netdevice.h:662
static struct net_device * netdev
Definition: gdbudp.c:52
A network device.
Definition: netdevice.h:353
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41

References efi_snp_claimed, EfiSimpleNetworkInitialized, EfiSimpleNetworkStarted, EfiSimpleNetworkStopped, mode, efi_snp_device::mode, efi_snp_device::netdev, netdev, netdev_is_open(), and efi_snp_device::started.

Referenced by efi_snp_add_claim(), efi_snp_initialize(), efi_snp_notify(), efi_snp_reset(), efi_snp_shutdown(), efi_snp_start(), and efi_snp_stop().

◆ efi_snp_set_mode()

static void efi_snp_set_mode ( struct efi_snp_device snpdev)
static

Set EFI SNP mode based on iPXE net device parameters.

Parameters
snpSNP interface

Definition at line 121 of file efi_snp.c.

121  {
122  struct net_device *netdev = snpdev->netdev;
123  EFI_SIMPLE_NETWORK_MODE *mode = &snpdev->mode;
125  unsigned int ll_addr_len = ll_protocol->ll_addr_len;
126 
127  mode->HwAddressSize = ll_addr_len;
128  mode->MediaHeaderSize = ll_protocol->ll_header_len;
129  mode->MaxPacketSize = netdev->mtu;
130  mode->ReceiveFilterMask = ( EFI_SIMPLE_NETWORK_RECEIVE_UNICAST |
133  assert ( ll_addr_len <= sizeof ( mode->CurrentAddress ) );
134  memcpy ( &mode->CurrentAddress, netdev->ll_addr, ll_addr_len );
135  memcpy ( &mode->BroadcastAddress, netdev->ll_broadcast, ll_addr_len );
136  ll_protocol->init_addr ( netdev->hw_addr, &mode->PermanentAddress );
137  mode->IfType = ntohs ( ll_protocol->ll_proto );
138  mode->MacAddressChangeable = TRUE;
139  mode->MediaPresentSupported = TRUE;
140  mode->MediaPresent = ( netdev_link_ok ( netdev ) ? TRUE : FALSE );
141 }
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
uint16_t mode
Acceleration mode.
Definition: ena.h:26
size_t mtu
Maximum transmission unit length.
Definition: netdevice.h:416
#define EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST
const uint8_t * ll_broadcast
Link-layer broadcast address.
Definition: netdevice.h:390
#define ntohs(value)
Definition: byteswap.h:137
void(* init_addr)(const void *hw_addr, void *ll_addr)
Initialise link-layer address.
Definition: netdevice.h:151
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void * memcpy(void *dest, const void *src, size_t len) __nonnull
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
static int netdev_link_ok(struct net_device *netdev)
Check link state of network device.
Definition: netdevice.h:640
static struct net_device * netdev
Definition: gdbudp.c:52
#define EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST
A network device.
Definition: netdevice.h:353
uint16_t ll_proto
Link-layer protocol.
Definition: netdevice.h:195
#define TRUE
Definition: tlan.h:46
#define EFI_SIMPLE_NETWORK_RECEIVE_UNICAST
#define FALSE
Definition: tlan.h:45
uint8_t ll_addr[MAX_LL_ADDR_LEN]
Link-layer address.
Definition: netdevice.h:388
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
uint8_t hw_addr[MAX_HW_ADDR_LEN]
Hardware address.
Definition: netdevice.h:382
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373

References assert(), EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST, EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST, EFI_SIMPLE_NETWORK_RECEIVE_UNICAST, FALSE, net_device::hw_addr, ll_protocol::init_addr, net_device::ll_addr, ll_protocol::ll_addr_len, net_device::ll_broadcast, ll_protocol::ll_header_len, ll_protocol::ll_proto, net_device::ll_protocol, memcpy(), mode, efi_snp_device::mode, net_device::mtu, efi_snp_device::netdev, netdev, netdev_link_ok(), ntohs, and TRUE.

Referenced by efi_snp_probe().

◆ efi_snp_flush()

static void efi_snp_flush ( struct efi_snp_device snpdev)
static

Flush transmit ring and receive queue.

Parameters
snpdevSNP device

Definition at line 148 of file efi_snp.c.

148  {
149  struct io_buffer *iobuf;
150  struct io_buffer *tmp;
151 
152  /* Reset transmit completion ring */
153  snpdev->tx_prod = 0;
154  snpdev->tx_cons = 0;
155 
156  /* Discard any queued receive buffers */
157  list_for_each_entry_safe ( iobuf, tmp, &snpdev->rx, list ) {
158  list_del ( &iobuf->list );
159  free_iob ( iobuf );
160  }
161 }
void free_iob(struct io_buffer *iobuf)
Free I/O buffer.
Definition: iobuf.c:153
unsigned long tmp
Definition: linux_pci.h:65
#define list_del(list)
Delete an entry from a list.
Definition: list.h:120
unsigned int tx_cons
Transmit completion ring consumer counter.
Definition: efi_snp.h:51
#define list_for_each_entry_safe(pos, tmp, head, member)
Iterate over entries in a list, safe against deletion of the current entry.
Definition: list.h:459
struct list_head rx
Receive queue.
Definition: efi_snp.h:53
unsigned int tx_prod
Transmit completion ring producer counter.
Definition: efi_snp.h:49
struct list_head list
List of which this buffer is a member.
Definition: iobuf.h:45
A persistent I/O buffer.
Definition: iobuf.h:38

References free_iob(), io_buffer::list, list_del, list_for_each_entry_safe, efi_snp_device::rx, tmp, efi_snp_device::tx_cons, and efi_snp_device::tx_prod.

Referenced by efi_snp_reset(), and efi_snp_shutdown().

◆ efi_snp_poll()

static void efi_snp_poll ( struct efi_snp_device snpdev)
static

Poll net device and count received packets.

Parameters
snpdevSNP device

Definition at line 168 of file efi_snp.c.

168  {
170  struct io_buffer *iobuf;
171 
172  /* Poll network device */
173  netdev_poll ( snpdev->netdev );
174 
175  /* Retrieve any received packets */
176  while ( ( iobuf = netdev_rx_dequeue ( snpdev->netdev ) ) ) {
177  list_add_tail ( &iobuf->list, &snpdev->rx );
179  bs->SignalEvent ( snpdev->snp.WaitForPacket );
180  }
181 }
EFI_BOOT_SERVICES * BootServices
A pointer to the EFI Boot Services Table.
Definition: UefiSpec.h:2099
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define list_add_tail(new, head)
Add a new entry to the tail of a list.
Definition: list.h:94
EFI_SIGNAL_EVENT SignalEvent
Definition: UefiSpec.h:1958
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
void netdev_poll(struct net_device *netdev)
Poll for completed and received packets on network device.
Definition: netdevice.c:613
EFI Boot Services Table.
Definition: UefiSpec.h:1931
struct list_head rx
Receive queue.
Definition: efi_snp.h:53
struct list_head list
List of which this buffer is a member.
Definition: iobuf.h:45
EFI_SYSTEM_TABLE * efi_systab
EFI_EVENT WaitForPacket
Event used with WaitForEvent() to wait for a packet to be received.
#define EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT
unsigned int interrupts
Pending interrupt status.
Definition: efi_snp.h:45
struct io_buffer * netdev_rx_dequeue(struct net_device *netdev)
Remove packet from device's receive queue.
Definition: netdevice.c:638
A persistent I/O buffer.
Definition: iobuf.h:38

References EFI_SYSTEM_TABLE::BootServices, EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT, efi_systab, efi_snp_device::interrupts, io_buffer::list, list_add_tail, efi_snp_device::netdev, netdev_poll(), netdev_rx_dequeue(), efi_snp_device::rx, EFI_BOOT_SERVICES::SignalEvent, efi_snp_device::snp, and _EFI_SIMPLE_NETWORK_PROTOCOL::WaitForPacket.

Referenced by efi_snp_get_status(), efi_snp_receive(), and efi_snp_wait_for_packet().

◆ efi_snp_start()

static EFI_STATUS EFIAPI efi_snp_start ( EFI_SIMPLE_NETWORK_PROTOCOL snp)
static

Change SNP state from "stopped" to "started".

Parameters
snpSNP interface
Return values
efircEFI status code

Definition at line 190 of file efi_snp.c.

190  {
191  struct efi_snp_device *snpdev =
192  container_of ( snp, struct efi_snp_device, snp );
193 
194  DBGC ( snpdev, "SNPDEV %p START\n", snpdev );
195 
196  /* Allow start even if net device is currently claimed by iPXE */
197  if ( efi_snp_claimed ) {
198  DBGC ( snpdev, "SNPDEV %p allowing start while claimed\n",
199  snpdev );
200  }
201 
202  snpdev->started = 1;
203  efi_snp_set_state ( snpdev );
204  return 0;
205 }
int started
Started flag.
Definition: efi_snp.h:43
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29

References container_of, DBGC, efi_snp_claimed, efi_snp_set_state(), efi_snp_device::snp, and efi_snp_device::started.

Referenced by efi_undi_start().

◆ efi_snp_stop()

static EFI_STATUS EFIAPI efi_snp_stop ( EFI_SIMPLE_NETWORK_PROTOCOL snp)
static

Change SNP state from "started" to "stopped".

Parameters
snpSNP interface
Return values
efircEFI status code

Definition at line 214 of file efi_snp.c.

214  {
215  struct efi_snp_device *snpdev =
216  container_of ( snp, struct efi_snp_device, snp );
217 
218  DBGC ( snpdev, "SNPDEV %p STOP\n", snpdev );
219 
220  /* Fail if net device is currently claimed for use by iPXE */
221  if ( efi_snp_claimed )
222  return EFI_NOT_READY;
223 
224  snpdev->started = 0;
225  efi_snp_set_state ( snpdev );
226 
227  return 0;
228 }
int started
Started flag.
Definition: efi_snp.h:43
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121

References container_of, DBGC, EFI_NOT_READY, efi_snp_claimed, efi_snp_set_state(), efi_snp_device::snp, and efi_snp_device::started.

Referenced by efi_undi_stop().

◆ efi_snp_initialize()

static EFI_STATUS EFIAPI efi_snp_initialize ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
UINTN  extra_rx_bufsize,
UINTN  extra_tx_bufsize 
)
static

Open the network device.

Parameters
snpSNP interface
extra_rx_bufsizeExtra RX buffer size, in bytes
extra_tx_bufsizeExtra TX buffer size, in bytes
Return values
efircEFI status code

Definition at line 239 of file efi_snp.c.

240  {
241  struct efi_snp_device *snpdev =
242  container_of ( snp, struct efi_snp_device, snp );
243  struct efi_saved_tpl tpl;
244  int rc;
245 
246  DBGC ( snpdev, "SNPDEV %p INITIALIZE (%ld extra RX, %ld extra TX)\n",
247  snpdev, ( ( unsigned long ) extra_rx_bufsize ),
248  ( ( unsigned long ) extra_tx_bufsize ) );
249 
250  /* Do nothing if net device is currently claimed for use by
251  * iPXE. Do not return an error, because this will cause
252  * MnpDxe et al to fail to install the relevant child handles
253  * and to leave behind a partially initialised device handle
254  * that can cause a later system crash.
255  */
256  if ( efi_snp_claimed ) {
257  DBGC ( snpdev, "SNPDEV %p ignoring initialization while "
258  "claimed\n", snpdev );
259  return 0;
260  }
261 
262  /* Raise TPL */
263  efi_raise_tpl ( &tpl );
264 
265  /* Open network device */
266  if ( ( rc = netdev_open ( snpdev->netdev ) ) != 0 ) {
267  DBGC ( snpdev, "SNPDEV %p could not open %s: %s\n",
268  snpdev, snpdev->netdev->name, strerror ( rc ) );
269  goto err_open;
270  }
271  efi_snp_set_state ( snpdev );
272 
273  err_open:
274  efi_restore_tpl ( &tpl );
275  return EFIRC ( rc );
276 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
An SNP device.
Definition: efi_snp.h:29
char name[NETDEV_NAME_LEN]
Name of this network device.
Definition: netdevice.h:363
An EFI saved task priority level.
Definition: efi.h:80
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
int netdev_open(struct net_device *netdev)
Open network device.
Definition: netdevice.c:862
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167

References container_of, DBGC, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_set_state(), EFIRC, net_device::name, efi_snp_device::netdev, netdev_open(), rc, efi_snp_device::snp, and strerror().

Referenced by efi_undi_initialize().

◆ efi_snp_reset()

static EFI_STATUS EFIAPI efi_snp_reset ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
BOOLEAN  ext_verify 
)
static

Reset the network device.

Parameters
snpSNP interface
ext_verifyExtended verification required
Return values
efircEFI status code

Definition at line 286 of file efi_snp.c.

286  {
287  struct efi_snp_device *snpdev =
288  container_of ( snp, struct efi_snp_device, snp );
289  struct efi_saved_tpl tpl;
290  int rc;
291 
292  DBGC ( snpdev, "SNPDEV %p RESET (%s extended verification)\n",
293  snpdev, ( ext_verify ? "with" : "without" ) );
294 
295  /* Fail if net device is currently claimed for use by iPXE */
296  if ( efi_snp_claimed ) {
297  rc = -EAGAIN;
298  goto err_claimed;
299  }
300 
301  /* Raise TPL */
302  efi_raise_tpl ( &tpl );
303 
304  /* Close network device */
305  netdev_close ( snpdev->netdev );
306  efi_snp_set_state ( snpdev );
307  efi_snp_flush ( snpdev );
308 
309  /* Reopen network device */
310  if ( ( rc = netdev_open ( snpdev->netdev ) ) != 0 ) {
311  DBGC ( snpdev, "SNPDEV %p could not reopen %s: %s\n",
312  snpdev, snpdev->netdev->name, strerror ( rc ) );
313  goto err_open;
314  }
315  efi_snp_set_state ( snpdev );
316 
317  err_open:
318  efi_restore_tpl ( &tpl );
319  err_claimed:
320  return EFIRC ( rc );
321 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
static void efi_snp_flush(struct efi_snp_device *snpdev)
Flush transmit ring and receive queue.
Definition: efi_snp.c:148
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
An SNP device.
Definition: efi_snp.h:29
#define EAGAIN
Resource temporarily unavailable.
Definition: errno.h:319
void netdev_close(struct net_device *netdev)
Close network device.
Definition: netdevice.c:896
char name[NETDEV_NAME_LEN]
Name of this network device.
Definition: netdevice.h:363
An EFI saved task priority level.
Definition: efi.h:80
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
int netdev_open(struct net_device *netdev)
Open network device.
Definition: netdevice.c:862
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167

References container_of, DBGC, EAGAIN, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_flush(), efi_snp_set_state(), EFIRC, net_device::name, efi_snp_device::netdev, netdev_close(), netdev_open(), rc, efi_snp_device::snp, and strerror().

Referenced by efi_undi_reset().

◆ efi_snp_shutdown()

static EFI_STATUS EFIAPI efi_snp_shutdown ( EFI_SIMPLE_NETWORK_PROTOCOL snp)
static

Shut down the network device.

Parameters
snpSNP interface
Return values
efircEFI status code

Definition at line 330 of file efi_snp.c.

330  {
331  struct efi_snp_device *snpdev =
332  container_of ( snp, struct efi_snp_device, snp );
333  struct efi_saved_tpl tpl;
334 
335  DBGC ( snpdev, "SNPDEV %p SHUTDOWN\n", snpdev );
336 
337  /* Fail if net device is currently claimed for use by iPXE */
338  if ( efi_snp_claimed )
339  return EFI_NOT_READY;
340 
341  /* Raise TPL */
342  efi_raise_tpl ( &tpl );
343 
344  /* Close network device */
345  netdev_close ( snpdev->netdev );
346  efi_snp_set_state ( snpdev );
347  efi_snp_flush ( snpdev );
348 
349  /* Restore TPL */
350  efi_restore_tpl ( &tpl );
351 
352  return 0;
353 }
static void efi_snp_flush(struct efi_snp_device *snpdev)
Flush transmit ring and receive queue.
Definition: efi_snp.c:148
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
void netdev_close(struct net_device *netdev)
Close network device.
Definition: netdevice.c:896
An EFI saved task priority level.
Definition: efi.h:80
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399

References container_of, DBGC, EFI_NOT_READY, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_flush(), efi_snp_set_state(), efi_snp_device::netdev, netdev_close(), and efi_snp_device::snp.

Referenced by efi_undi_shutdown().

◆ efi_snp_receive_filters()

static EFI_STATUS EFIAPI efi_snp_receive_filters ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
UINT32  enable,
UINT32  disable,
BOOLEAN  mcast_reset,
UINTN  mcast_count,
EFI_MAC_ADDRESS mcast 
)
static

Manage receive filters.

Parameters
snpSNP interface
enableReceive filters to enable
disableReceive filters to disable
mcast_resetReset multicast filters
mcast_countNumber of multicast filters
mcastMulticast filters
Return values
efircEFI status code

Definition at line 367 of file efi_snp.c.

369  {
370  struct efi_snp_device *snpdev =
371  container_of ( snp, struct efi_snp_device, snp );
372  unsigned int i;
373 
374  DBGC ( snpdev, "SNPDEV %p RECEIVE_FILTERS %08x&~%08x%s %ld mcast\n",
375  snpdev, enable, disable, ( mcast_reset ? " reset" : "" ),
376  ( ( unsigned long ) mcast_count ) );
377  for ( i = 0 ; i < mcast_count ; i++ ) {
378  DBGC2_HDA ( snpdev, i, &mcast[i],
379  snpdev->netdev->ll_protocol->ll_addr_len );
380  }
381 
382  /* Lie through our teeth, otherwise MNP refuses to accept us.
383  *
384  * Return success even if the SNP device is currently claimed
385  * for use by iPXE, since otherwise Windows Deployment
386  * Services refuses to attempt to receive further packets via
387  * our EFI PXE Base Code protocol.
388  */
389  return 0;
390 }
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
#define DBGC(...)
Definition: compiler.h:505
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
#define DBGC2_HDA(...)
Definition: compiler.h:523
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373

References container_of, DBGC, DBGC2_HDA, ll_protocol::ll_addr_len, net_device::ll_protocol, efi_snp_device::netdev, and efi_snp_device::snp.

◆ efi_snp_station_address()

static EFI_STATUS EFIAPI efi_snp_station_address ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
BOOLEAN  reset,
EFI_MAC_ADDRESS new 
)
static

Set station address.

Parameters
snpSNP interface
resetReset to permanent address
newNew station address
Return values
efircEFI status code

Definition at line 401 of file efi_snp.c.

402  {
403  struct efi_snp_device *snpdev =
404  container_of ( snp, struct efi_snp_device, snp );
405  struct ll_protocol *ll_protocol = snpdev->netdev->ll_protocol;
406 
407  DBGC ( snpdev, "SNPDEV %p STATION_ADDRESS %s\n", snpdev,
408  ( reset ? "reset" : ll_protocol->ntoa ( new ) ) );
409 
410  /* Fail if net device is currently claimed for use by iPXE */
411  if ( efi_snp_claimed )
412  return EFI_NOT_READY;
413 
414  /* Set the MAC address */
415  if ( reset )
416  new = &snpdev->mode.PermanentAddress;
417  memcpy ( snpdev->netdev->ll_addr, new, ll_protocol->ll_addr_len );
418 
419  /* MAC address changes take effect only on netdev_open() */
420  if ( netdev_is_open ( snpdev->netdev ) ) {
421  DBGC ( snpdev, "SNPDEV %p MAC address changed while net "
422  "device open\n", snpdev );
423  }
424 
425  return 0;
426 }
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
#define DBGC(...)
Definition: compiler.h:505
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void * memcpy(void *dest, const void *src, size_t len) __nonnull
static int netdev_is_open(struct net_device *netdev)
Check whether or not network device is open.
Definition: netdevice.h:662
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
const char *(* ntoa)(const void *ll_addr)
Transcribe link-layer address.
Definition: netdevice.h:164
uint8_t ll_addr[MAX_LL_ADDR_LEN]
Link-layer address.
Definition: netdevice.h:388
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
EFI_MAC_ADDRESS PermanentAddress
The permanent HW MAC address for the network interface.

References container_of, DBGC, EFI_NOT_READY, efi_snp_claimed, net_device::ll_addr, ll_protocol::ll_addr_len, net_device::ll_protocol, memcpy(), efi_snp_device::mode, efi_snp_device::netdev, netdev_is_open(), ll_protocol::ntoa, EFI_SIMPLE_NETWORK_MODE::PermanentAddress, and efi_snp_device::snp.

Referenced by efi_undi_station_address().

◆ efi_snp_statistics()

static EFI_STATUS EFIAPI efi_snp_statistics ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
BOOLEAN  reset,
UINTN stats_len,
EFI_NETWORK_STATISTICS stats 
)
static

Get (or reset) statistics.

Parameters
snpSNP interface
resetReset statistics
stats_lenSize of statistics table
statsStatistics table
Return values
efircEFI status code

Definition at line 438 of file efi_snp.c.

439  {
440  struct efi_snp_device *snpdev =
441  container_of ( snp, struct efi_snp_device, snp );
442  EFI_NETWORK_STATISTICS stats_buf;
443 
444  DBGC ( snpdev, "SNPDEV %p STATISTICS%s", snpdev,
445  ( reset ? " reset" : "" ) );
446 
447  /* Fail if net device is currently claimed for use by iPXE */
448  if ( efi_snp_claimed )
449  return EFI_NOT_READY;
450 
451  /* Gather statistics */
452  memset ( &stats_buf, 0, sizeof ( stats_buf ) );
453  stats_buf.TxGoodFrames = snpdev->netdev->tx_stats.good;
454  stats_buf.TxDroppedFrames = snpdev->netdev->tx_stats.bad;
455  stats_buf.TxTotalFrames = ( snpdev->netdev->tx_stats.good +
456  snpdev->netdev->tx_stats.bad );
457  stats_buf.RxGoodFrames = snpdev->netdev->rx_stats.good;
458  stats_buf.RxDroppedFrames = snpdev->netdev->rx_stats.bad;
459  stats_buf.RxTotalFrames = ( snpdev->netdev->rx_stats.good +
460  snpdev->netdev->rx_stats.bad );
461  if ( *stats_len > sizeof ( stats_buf ) )
462  *stats_len = sizeof ( stats_buf );
463  if ( stats )
464  memcpy ( stats, &stats_buf, *stats_len );
465 
466  /* Reset statistics if requested to do so */
467  if ( reset ) {
468  memset ( &snpdev->netdev->tx_stats, 0,
469  sizeof ( snpdev->netdev->tx_stats ) );
470  memset ( &snpdev->netdev->rx_stats, 0,
471  sizeof ( snpdev->netdev->rx_stats ) );
472  }
473 
474  return 0;
475 }
#define DBGC(...)
Definition: compiler.h:505
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device_stats tx_stats
TX statistics.
Definition: netdevice.h:424
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
UINT64 RxGoodFrames
Number of valid frames received and copied into receive buffers.
Definition: SimpleNetwork.h:51
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
UINT64 TxTotalFrames
Transmit statistics.
Definition: SimpleNetwork.h:99
UINT64 RxDroppedFrames
Valid frames that were dropped because receive buffers were full.
Definition: SimpleNetwork.h:68
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
UINT64 RxTotalFrames
Total number of frames received.
Definition: SimpleNetwork.h:46
struct net_device_stats rx_stats
RX statistics.
Definition: netdevice.h:426
unsigned int bad
Count of error completions.
Definition: netdevice.h:296
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
unsigned int good
Count of successful completions.
Definition: netdevice.h:294
Simple Network Protocol data structures.
Definition: SimpleNetwork.h:41
void * memset(void *dest, int character, size_t len) __nonnull

References net_device_stats::bad, container_of, DBGC, EFI_NOT_READY, efi_snp_claimed, net_device_stats::good, memcpy(), memset(), efi_snp_device::netdev, net_device::rx_stats, EFI_NETWORK_STATISTICS::RxDroppedFrames, EFI_NETWORK_STATISTICS::RxGoodFrames, EFI_NETWORK_STATISTICS::RxTotalFrames, efi_snp_device::snp, net_device::tx_stats, EFI_NETWORK_STATISTICS::TxDroppedFrames, EFI_NETWORK_STATISTICS::TxGoodFrames, and EFI_NETWORK_STATISTICS::TxTotalFrames.

◆ efi_snp_mcast_ip_to_mac()

static EFI_STATUS EFIAPI efi_snp_mcast_ip_to_mac ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
BOOLEAN  ipv6,
EFI_IP_ADDRESS ip,
EFI_MAC_ADDRESS mac 
)
static

Convert multicast IP address to MAC address.

Parameters
snpSNP interface
ipv6Address is IPv6
ipIP address
macMAC address
Return values
efircEFI status code

Definition at line 487 of file efi_snp.c.

488  {
489  struct efi_snp_device *snpdev =
490  container_of ( snp, struct efi_snp_device, snp );
491  struct ll_protocol *ll_protocol = snpdev->netdev->ll_protocol;
492  const char *ip_str;
493  int rc;
494 
495  ip_str = ( ipv6 ? "(IPv6)" /* FIXME when we have inet6_ntoa() */ :
496  inet_ntoa ( *( ( struct in_addr * ) ip ) ) );
497  DBGC ( snpdev, "SNPDEV %p MCAST_IP_TO_MAC %s\n", snpdev, ip_str );
498 
499  /* Fail if net device is currently claimed for use by iPXE */
500  if ( efi_snp_claimed )
501  return EFI_NOT_READY;
502 
503  /* Try to hash the address */
504  if ( ( rc = ll_protocol->mc_hash ( ( ipv6 ? AF_INET6 : AF_INET ),
505  ip, mac ) ) != 0 ) {
506  DBGC ( snpdev, "SNPDEV %p could not hash %s: %s\n",
507  snpdev, ip_str, strerror ( rc ) );
508  return EFIRC ( rc );
509  }
510 
511  return 0;
512 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define AF_INET6
IPv6 Internet addresses.
Definition: socket.h:65
#define DBGC(...)
Definition: compiler.h:505
uint8_t mac[ETH_ALEN]
MAC address.
Definition: ena.h:24
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
IP address structure.
Definition: in.h:42
An SNP device.
Definition: efi_snp.h:29
IP4_t ip
Destination IP address.
Definition: pxe_api.h:58
char * inet_ntoa(struct in_addr in)
Convert IPv4 address to dotted-quad notation.
Definition: ipv4.c:814
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
int(* mc_hash)(unsigned int af, const void *net_addr, void *ll_addr)
Hash multicast address.
Definition: netdevice.h:173
#define AF_INET
IPv4 Internet addresses.
Definition: socket.h:64
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373

References AF_INET, AF_INET6, container_of, DBGC, EFI_NOT_READY, efi_snp_claimed, EFIRC, inet_ntoa(), ip, net_device::ll_protocol, mac, ll_protocol::mc_hash, efi_snp_device::netdev, rc, efi_snp_device::snp, and strerror().

◆ efi_snp_nvdata()

static EFI_STATUS EFIAPI efi_snp_nvdata ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
BOOLEAN  read,
UINTN  offset,
UINTN  len,
VOID data 
)
static

Read or write non-volatile storage.

Parameters
snpSNP interface
readOperation is a read
offsetStarting offset within NVRAM
lenLength of data buffer
dataData buffer
Return values
efircEFI status code

Definition at line 525 of file efi_snp.c.

526  {
527  struct efi_snp_device *snpdev =
528  container_of ( snp, struct efi_snp_device, snp );
529 
530  DBGC ( snpdev, "SNPDEV %p NVDATA %s %lx+%lx\n", snpdev,
531  ( read ? "read" : "write" ), ( ( unsigned long ) offset ),
532  ( ( unsigned long ) len ) );
533  if ( ! read )
534  DBGC2_HDA ( snpdev, offset, data, len );
535 
536  /* Fail if net device is currently claimed for use by iPXE */
537  if ( efi_snp_claimed )
538  return EFI_NOT_READY;
539 
540  return EFI_UNSUPPORTED;
541 }
struct option_descriptor read[1]
Definition: nvo_cmd.c:116
#define EFI_UNSUPPORTED
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:118
#define DBGC(...)
Definition: compiler.h:505
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
ring len
Length.
Definition: dwmac.h:231
#define DBGC2_HDA(...)
Definition: compiler.h:523
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
uint8_t data[48]
Additional event data.
Definition: ena.h:22
uint16_t offset
Offset to command line.
Definition: bzimage.h:8

References container_of, data, DBGC, DBGC2_HDA, EFI_NOT_READY, efi_snp_claimed, EFI_UNSUPPORTED, len, offset, read, and efi_snp_device::snp.

◆ efi_snp_get_status()

static EFI_STATUS EFIAPI efi_snp_get_status ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
UINT32 interrupts,
VOID **  txbuf 
)
static

Read interrupt status and TX recycled buffer status.

Parameters
snpSNP interface
interruptsInterrupt status, or NULL
txbufRecycled transmit buffer address, or NULL
Return values
efircEFI status code

Definition at line 552 of file efi_snp.c.

553  {
554  struct efi_snp_device *snpdev =
555  container_of ( snp, struct efi_snp_device, snp );
556  struct efi_saved_tpl tpl;
557 
558  DBGC2 ( snpdev, "SNPDEV %p GET_STATUS", snpdev );
559 
560  /* Fail if net device is currently claimed for use by iPXE */
561  if ( efi_snp_claimed ) {
562  DBGC2 ( snpdev, "\n" );
563  return EFI_NOT_READY;
564  }
565 
566  /* Raise TPL */
567  efi_raise_tpl ( &tpl );
568 
569  /* Poll the network device */
570  efi_snp_poll ( snpdev );
571 
572  /* Interrupt status. In practice, this seems to be used only
573  * to detect TX completions.
574  */
575  if ( interrupts ) {
576  *interrupts = snpdev->interrupts;
577  DBGC2 ( snpdev, " INTS:%02x", *interrupts );
578  snpdev->interrupts = 0;
579  }
580 
581  /* TX completions */
582  if ( txbuf ) {
583  if ( snpdev->tx_prod != snpdev->tx_cons ) {
584  *txbuf = snpdev->tx[snpdev->tx_cons++ % EFI_SNP_NUM_TX];
585  } else {
586  *txbuf = NULL;
587  }
588  DBGC2 ( snpdev, " TX:%p", *txbuf );
589  }
590 
591  /* Restore TPL */
592  efi_restore_tpl ( &tpl );
593 
594  DBGC2 ( snpdev, "\n" );
595  return 0;
596 }
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define EFI_SNP_NUM_TX
SNP transmit completion ring size.
Definition: efi_snp.h:26
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
unsigned int tx_cons
Transmit completion ring consumer counter.
Definition: efi_snp.h:51
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
VOID * tx[EFI_SNP_NUM_TX]
Transmit completion ring.
Definition: efi_snp.h:47
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
An SNP device.
Definition: efi_snp.h:29
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
unsigned int tx_prod
Transmit completion ring producer counter.
Definition: efi_snp.h:49
An EFI saved task priority level.
Definition: efi.h:80
#define DBGC2(...)
Definition: compiler.h:522
static void efi_snp_poll(struct efi_snp_device *snpdev)
Poll net device and count received packets.
Definition: efi_snp.c:168
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
unsigned int interrupts
Pending interrupt status.
Definition: efi_snp.h:45

References container_of, DBGC2, EFI_NOT_READY, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, EFI_SNP_NUM_TX, efi_snp_poll(), efi_snp_device::interrupts, NULL, efi_snp_device::snp, efi_snp_device::tx, efi_snp_device::tx_cons, and efi_snp_device::tx_prod.

Referenced by efi_undi_get_status().

◆ efi_snp_transmit()

static EFI_STATUS EFIAPI efi_snp_transmit ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
UINTN  ll_header_len,
UINTN  len,
VOID data,
EFI_MAC_ADDRESS ll_src,
EFI_MAC_ADDRESS ll_dest,
UINT16 net_proto 
)
static

Start packet transmission.

Parameters
snpSNP interface
ll_header_lenLink-layer header length, if to be filled in
lenLength of data buffer
dataData buffer
ll_srcLink-layer source address, if specified
ll_destLink-layer destination address, if specified
net_protoNetwork-layer protocol (in host order)
Return values
efircEFI status code

Definition at line 611 of file efi_snp.c.

614  {
615  struct efi_snp_device *snpdev =
616  container_of ( snp, struct efi_snp_device, snp );
617  struct ll_protocol *ll_protocol = snpdev->netdev->ll_protocol;
618  struct efi_saved_tpl tpl;
619  struct io_buffer *iobuf;
620  size_t payload_len;
621  unsigned int tx_fill;
622  int rc;
623 
624  DBGC2 ( snpdev, "SNPDEV %p TRANSMIT %p+%lx", snpdev, data,
625  ( ( unsigned long ) len ) );
626  if ( ll_header_len ) {
627  if ( ll_src ) {
628  DBGC2 ( snpdev, " src %s",
629  ll_protocol->ntoa ( ll_src ) );
630  }
631  if ( ll_dest ) {
632  DBGC2 ( snpdev, " dest %s",
633  ll_protocol->ntoa ( ll_dest ) );
634  }
635  if ( net_proto ) {
636  DBGC2 ( snpdev, " proto %04x", *net_proto );
637  }
638  }
639  DBGC2 ( snpdev, "\n" );
640 
641  /* Fail if net device is currently claimed for use by iPXE */
642  if ( efi_snp_claimed ) {
643  rc = -EAGAIN;
644  goto err_claimed;
645  }
646 
647  /* Raise TPL */
648  efi_raise_tpl ( &tpl );
649 
650  /* Sanity checks */
651  if ( ll_header_len ) {
652  if ( ll_header_len != ll_protocol->ll_header_len ) {
653  DBGC ( snpdev, "SNPDEV %p TX invalid header length "
654  "%ld\n", snpdev,
655  ( ( unsigned long ) ll_header_len ) );
656  rc = -EINVAL;
657  goto err_sanity;
658  }
659  if ( len < ll_header_len ) {
660  DBGC ( snpdev, "SNPDEV %p invalid packet length %ld\n",
661  snpdev, ( ( unsigned long ) len ) );
662  rc = -EINVAL;
663  goto err_sanity;
664  }
665  if ( ! ll_dest ) {
666  DBGC ( snpdev, "SNPDEV %p TX missing destination "
667  "address\n", snpdev );
668  rc = -EINVAL;
669  goto err_sanity;
670  }
671  if ( ! net_proto ) {
672  DBGC ( snpdev, "SNPDEV %p TX missing network "
673  "protocol\n", snpdev );
674  rc = -EINVAL;
675  goto err_sanity;
676  }
677  if ( ! ll_src )
678  ll_src = &snpdev->mode.CurrentAddress;
679  }
680 
681  /* Allocate buffer */
682  payload_len = ( len - ll_protocol->ll_header_len );
683  iobuf = alloc_iob ( MAX_LL_HEADER_LEN + ( ( payload_len > IOB_ZLEN ) ?
684  payload_len : IOB_ZLEN ) );
685  if ( ! iobuf ) {
686  DBGC ( snpdev, "SNPDEV %p TX could not allocate %ld-byte "
687  "buffer\n", snpdev, ( ( unsigned long ) len ) );
688  rc = -ENOMEM;
689  goto err_alloc_iob;
690  }
691  iob_reserve ( iobuf, ( MAX_LL_HEADER_LEN -
693  memcpy ( iob_put ( iobuf, len ), data, len );
694 
695  /* Create link-layer header, if specified */
696  if ( ll_header_len ) {
697  iob_pull ( iobuf, ll_protocol->ll_header_len );
698  if ( ( rc = ll_protocol->push ( snpdev->netdev,
699  iobuf, ll_dest, ll_src,
700  htons ( *net_proto ) )) != 0 ){
701  DBGC ( snpdev, "SNPDEV %p TX could not construct "
702  "header: %s\n", snpdev, strerror ( rc ) );
703  goto err_ll_push;
704  }
705  }
706 
707  /* Transmit packet */
708  if ( ( rc = netdev_tx ( snpdev->netdev, iob_disown ( iobuf ) ) ) != 0){
709  DBGC ( snpdev, "SNPDEV %p TX could not transmit: %s\n",
710  snpdev, strerror ( rc ) );
711  goto err_tx;
712  }
713 
714  /* Record in transmit completion ring. If we run out of
715  * space, report the failure even though we have already
716  * transmitted the packet.
717  *
718  * This allows us to report completions only for packets for
719  * which we had reported successfully initiating transmission,
720  * while continuing to support clients that never poll for
721  * transmit completions.
722  */
723  tx_fill = ( snpdev->tx_prod - snpdev->tx_cons );
724  if ( tx_fill >= EFI_SNP_NUM_TX ) {
725  DBGC ( snpdev, "SNPDEV %p TX completion ring full\n", snpdev );
726  rc = -ENOBUFS;
727  goto err_ring_full;
728  }
729  snpdev->tx[ snpdev->tx_prod++ % EFI_SNP_NUM_TX ] = data;
731 
732  /* Restore TPL */
733  efi_restore_tpl ( &tpl );
734 
735  return 0;
736 
737  err_ring_full:
738  err_tx:
739  err_ll_push:
740  free_iob ( iobuf );
741  err_alloc_iob:
742  err_sanity:
743  efi_restore_tpl ( &tpl );
744  err_claimed:
745  return EFIRC ( rc );
746 }
#define iob_pull(iobuf, len)
Definition: iobuf.h:107
#define EINVAL
Invalid argument.
Definition: errno.h:429
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define iob_put(iobuf, len)
Definition: iobuf.h:125
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
void free_iob(struct io_buffer *iobuf)
Free I/O buffer.
Definition: iobuf.c:153
#define DBGC(...)
Definition: compiler.h:505
#define EFI_SNP_NUM_TX
SNP transmit completion ring size.
Definition: efi_snp.h:26
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct io_buffer * alloc_iob(size_t len)
Allocate I/O buffer.
Definition: iobuf.c:131
A link-layer protocol.
Definition: netdevice.h:115
EFI_MAC_ADDRESS CurrentAddress
The current HW MAC address for the network interface.
int(* push)(struct net_device *netdev, struct io_buffer *iobuf, const void *ll_dest, const void *ll_source, uint16_t net_proto)
Add link-layer header.
Definition: netdevice.h:128
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define ENOMEM
Not enough space.
Definition: errno.h:535
#define iob_disown(iobuf)
Disown an I/O buffer.
Definition: iobuf.h:217
void * memcpy(void *dest, const void *src, size_t len) __nonnull
unsigned int tx_cons
Transmit completion ring consumer counter.
Definition: efi_snp.h:51
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
ring len
Length.
Definition: dwmac.h:231
#define MAX_LL_HEADER_LEN
Maximum length of a link-layer header.
Definition: netdevice.h:46
VOID * tx[EFI_SNP_NUM_TX]
Transmit completion ring.
Definition: efi_snp.h:47
#define EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
An SNP device.
Definition: efi_snp.h:29
int netdev_tx(struct net_device *netdev, struct io_buffer *iobuf)
Transmit raw packet via network device.
Definition: netdevice.c:335
#define EAGAIN
Resource temporarily unavailable.
Definition: errno.h:319
unsigned int tx_prod
Transmit completion ring producer counter.
Definition: efi_snp.h:49
#define iob_reserve(iobuf, len)
Definition: iobuf.h:72
An EFI saved task priority level.
Definition: efi.h:80
#define ENOBUFS
No buffer space available.
Definition: errno.h:499
#define DBGC2(...)
Definition: compiler.h:522
#define IOB_ZLEN
Minimum I/O buffer length and alignment.
Definition: iobuf.h:29
uint8_t data[48]
Additional event data.
Definition: ena.h:22
const char *(* ntoa)(const void *ll_addr)
Transcribe link-layer address.
Definition: netdevice.h:164
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define htons(value)
Definition: byteswap.h:136
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
unsigned int interrupts
Pending interrupt status.
Definition: efi_snp.h:45
A persistent I/O buffer.
Definition: iobuf.h:38

References alloc_iob(), container_of, EFI_SIMPLE_NETWORK_MODE::CurrentAddress, data, DBGC, DBGC2, EAGAIN, efi_raise_tpl(), efi_restore_tpl(), EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT, efi_snp_claimed, EFI_SNP_NUM_TX, EFIRC, EINVAL, ENOBUFS, ENOMEM, free_iob(), htons, efi_snp_device::interrupts, iob_disown, iob_pull, iob_put, iob_reserve, IOB_ZLEN, len, ll_protocol::ll_header_len, net_device::ll_protocol, MAX_LL_HEADER_LEN, memcpy(), efi_snp_device::mode, efi_snp_device::netdev, netdev_tx(), ll_protocol::ntoa, ll_protocol::push, rc, efi_snp_device::snp, strerror(), efi_snp_device::tx, efi_snp_device::tx_cons, and efi_snp_device::tx_prod.

Referenced by efi_undi_transmit().

◆ efi_snp_receive()

static EFI_STATUS EFIAPI efi_snp_receive ( EFI_SIMPLE_NETWORK_PROTOCOL snp,
UINTN ll_header_len,
UINTN len,
VOID data,
EFI_MAC_ADDRESS ll_src,
EFI_MAC_ADDRESS ll_dest,
UINT16 net_proto 
)
static

Receive packet.

Parameters
snpSNP interface
ll_header_lenLink-layer header length, if to be filled in
lenLength of data buffer
dataData buffer
ll_srcLink-layer source address, if specified
ll_destLink-layer destination address, if specified
net_protoNetwork-layer protocol (in host order)
Return values
efircEFI status code

Definition at line 761 of file efi_snp.c.

764  {
765  struct efi_snp_device *snpdev =
766  container_of ( snp, struct efi_snp_device, snp );
767  struct ll_protocol *ll_protocol = snpdev->netdev->ll_protocol;
768  struct efi_saved_tpl tpl;
769  struct io_buffer *iobuf;
770  const void *iob_ll_dest;
771  const void *iob_ll_src;
772  uint16_t iob_net_proto;
773  unsigned int iob_flags;
774  size_t copy_len;
775  int rc;
776 
777  DBGC2 ( snpdev, "SNPDEV %p RECEIVE %p(+%lx)", snpdev, data,
778  ( ( unsigned long ) *len ) );
779 
780  /* Fail if net device is currently claimed for use by iPXE */
781  if ( efi_snp_claimed ) {
782  rc = -EAGAIN;
783  goto err_claimed;
784  }
785 
786  /* Raise TPL */
787  efi_raise_tpl ( &tpl );
788 
789  /* Poll the network device */
790  efi_snp_poll ( snpdev );
791 
792  /* Check for an available packet */
793  iobuf = list_first_entry ( &snpdev->rx, struct io_buffer, list );
794  if ( ! iobuf ) {
795  DBGC2 ( snpdev, "\n" );
796  rc = -EAGAIN;
797  goto out_no_packet;
798  }
799  DBGC2 ( snpdev, "+%zx\n", iob_len ( iobuf ) );
800 
801  /* Dequeue packet */
802  list_del ( &iobuf->list );
803 
804  /* Return packet to caller, truncating to buffer length */
805  copy_len = iob_len ( iobuf );
806  if ( copy_len > *len )
807  copy_len = *len;
808  memcpy ( data, iobuf->data, copy_len );
809  *len = iob_len ( iobuf );
810 
811  /* Attempt to decode link-layer header */
812  if ( ( rc = ll_protocol->pull ( snpdev->netdev, iobuf, &iob_ll_dest,
813  &iob_ll_src, &iob_net_proto,
814  &iob_flags ) ) != 0 ) {
815  DBGC ( snpdev, "SNPDEV %p could not parse header: %s\n",
816  snpdev, strerror ( rc ) );
817  goto out_bad_ll_header;
818  }
819 
820  /* Return link-layer header parameters to caller, if required */
821  if ( ll_header_len )
822  *ll_header_len = ll_protocol->ll_header_len;
823  if ( ll_src )
824  memcpy ( ll_src, iob_ll_src, ll_protocol->ll_addr_len );
825  if ( ll_dest )
826  memcpy ( ll_dest, iob_ll_dest, ll_protocol->ll_addr_len );
827  if ( net_proto )
828  *net_proto = ntohs ( iob_net_proto );
829 
830  /* Check buffer length */
831  rc = ( ( copy_len == *len ) ? 0 : -ERANGE );
832 
833  out_bad_ll_header:
834  free_iob ( iobuf );
835  out_no_packet:
836  efi_restore_tpl ( &tpl );
837  err_claimed:
838  return EFIRC ( rc );
839 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
unsigned short uint16_t
Definition: stdint.h:11
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
void free_iob(struct io_buffer *iobuf)
Free I/O buffer.
Definition: iobuf.c:153
#define DBGC(...)
Definition: compiler.h:505
#define ntohs(value)
Definition: byteswap.h:137
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define list_first_entry(list, type, member)
Get the container of the first entry in a list.
Definition: list.h:334
#define list_del(list)
Delete an entry from a list.
Definition: list.h:120
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
ring len
Length.
Definition: dwmac.h:231
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
#define ERANGE
Result too large.
Definition: errno.h:640
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
static size_t iob_len(struct io_buffer *iobuf)
Calculate length of data in an I/O buffer.
Definition: iobuf.h:160
An SNP device.
Definition: efi_snp.h:29
#define EAGAIN
Resource temporarily unavailable.
Definition: errno.h:319
struct list_head rx
Receive queue.
Definition: efi_snp.h:53
int(* pull)(struct net_device *netdev, struct io_buffer *iobuf, const void **ll_dest, const void **ll_source, uint16_t *net_proto, unsigned int *flags)
Remove link-layer header.
Definition: netdevice.h:142
An EFI saved task priority level.
Definition: efi.h:80
struct list_head list
List of which this buffer is a member.
Definition: iobuf.h:45
#define DBGC2(...)
Definition: compiler.h:522
void * data
Start of data.
Definition: iobuf.h:53
static void efi_snp_poll(struct efi_snp_device *snpdev)
Poll net device and count received packets.
Definition: efi_snp.c:168
uint8_t data[48]
Additional event data.
Definition: ena.h:22
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
A persistent I/O buffer.
Definition: iobuf.h:38

References container_of, data, io_buffer::data, DBGC, DBGC2, EAGAIN, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_poll(), EFIRC, ERANGE, free_iob(), iob_len(), len, io_buffer::list, list_del, list_first_entry, ll_protocol::ll_addr_len, ll_protocol::ll_header_len, net_device::ll_protocol, memcpy(), efi_snp_device::netdev, ntohs, ll_protocol::pull, rc, efi_snp_device::rx, efi_snp_device::snp, and strerror().

Referenced by efi_undi_receive().

◆ efi_snp_wait_for_packet()

static VOID EFIAPI efi_snp_wait_for_packet ( EFI_EVENT event  __unused,
VOID context 
)
static

Poll event.

Parameters
eventEvent
contextEvent context

Definition at line 847 of file efi_snp.c.

848  {
849  struct efi_snp_device *snpdev = context;
850  struct efi_saved_tpl tpl;
851 
852  DBGCP ( snpdev, "SNPDEV %p WAIT_FOR_PACKET\n", snpdev );
853 
854  /* Do nothing unless the net device is open */
855  if ( ! netdev_is_open ( snpdev->netdev ) )
856  return;
857 
858  /* Do nothing if net device is currently claimed for use by iPXE */
859  if ( efi_snp_claimed )
860  return;
861 
862  /* Raise TPL */
863  efi_raise_tpl ( &tpl );
864 
865  /* Poll the network device */
866  efi_snp_poll ( snpdev );
867 
868  /* Restore TPL */
869  efi_restore_tpl ( &tpl );
870 }
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
static int netdev_is_open(struct net_device *netdev)
Check whether or not network device is open.
Definition: netdevice.h:662
An SNP device.
Definition: efi_snp.h:29
An EFI saved task priority level.
Definition: efi.h:80
static void efi_snp_poll(struct efi_snp_device *snpdev)
Poll net device and count received packets.
Definition: efi_snp.c:168
#define DBGCP(...)
Definition: compiler.h:539
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399

References DBGCP, efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_poll(), efi_snp_device::netdev, and netdev_is_open().

Referenced by efi_snp_probe().

◆ efi_undi_checksum()

static uint8_t efi_undi_checksum ( void *  data,
size_t  len 
)
static

Calculate UNDI byte checksum.

Parameters
dataData
lenLength of data
Return values
sumChecksum

Definition at line 921 of file efi_snp.c.

921  {
922  uint8_t *bytes = data;
923  uint8_t sum = 0;
924 
925  while ( len-- )
926  sum += *bytes++;
927  return sum;
928 }
ring len
Length.
Definition: dwmac.h:231
unsigned char uint8_t
Definition: stdint.h:10
uint8_t data[48]
Additional event data.
Definition: ena.h:22
uint8_t bytes[64]
Definition: ib_mad.h:17

References bytes, data, and len.

Referenced by efi_snp_probe().

◆ efi_undi_ifnum()

static unsigned int efi_undi_ifnum ( struct efi_snp_device snpdev)
static

Get UNDI SNP device interface number.

Parameters
snpdevSNP device
Return values
ifnumUNDI interface number

Definition at line 936 of file efi_snp.c.

936  {
937 
938  /* iPXE network device scope IDs are one-based (leaving zero
939  * meaning "unspecified"). UNDI interface numbers are
940  * zero-based.
941  */
942  return ( snpdev->netdev->scope_id - 1 );
943 }
unsigned int scope_id
Scope ID.
Definition: netdevice.h:361
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33

References efi_snp_device::netdev, and net_device::scope_id.

Referenced by efi_snp_probe(), and efi_undi_snpdev().

◆ efi_undi_snpdev()

static struct efi_snp_device* efi_undi_snpdev ( unsigned int  ifnum)
static

Identify UNDI SNP device.

Parameters
ifnumInterface number
Return values
snpdevSNP device, or NULL if not found

Definition at line 951 of file efi_snp.c.

951  {
952  struct efi_snp_device *snpdev;
953 
954  list_for_each_entry ( snpdev, &efi_snp_devices, list ) {
955  if ( efi_undi_ifnum ( snpdev ) == ifnum )
956  return snpdev;
957  }
958  return NULL;
959 }
static unsigned int efi_undi_ifnum(struct efi_snp_device *snpdev)
Get UNDI SNP device interface number.
Definition: efi_snp.c:936
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:432
An SNP device.
Definition: efi_snp.h:29
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31

References efi_undi_ifnum(), efi_snp_device::list, list_for_each_entry, and NULL.

Referenced by efi_undi_issue().

◆ efi_undi_statcode()

static PXE_STATCODE efi_undi_statcode ( EFI_STATUS  efirc)
static

Convert EFI status code to UNDI status code.

Parameters
efircEFI status code
Return values
statcodeUNDI status code

Definition at line 967 of file efi_snp.c.

967  {
968 
969  switch ( efirc ) {
974  case EFI_NOT_READY: return PXE_STATCODE_NO_DATA;
975  default:
977  }
978 }
#define EFI_UNSUPPORTED
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:118
#define EFI_PROTOCOL_ERROR
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:139
#define EFI_OUT_OF_RESOURCES
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:124
#define PXE_STATCODE_DEVICE_FAILURE
Definition: UefiPxe.h:616
#define PXE_STATCODE_UNSUPPORTED
Definition: UefiPxe.h:618
#define EFI_NOT_READY
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:121
#define EFI_INVALID_PARAMETER
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:117
#define PXE_STATCODE_NO_DATA
Definition: UefiPxe.h:625
#define PXE_STATCODE_BUFFER_FULL
Definition: UefiPxe.h:619
#define PXE_STATCODE_INVALID_CDB
Definition: UefiPxe.h:607
#define PXE_STATCODE_INVALID_PARAMETER
Definition: UefiPxe.h:620

References EFI_INVALID_PARAMETER, EFI_NOT_READY, EFI_OUT_OF_RESOURCES, EFI_PROTOCOL_ERROR, EFI_UNSUPPORTED, PXE_STATCODE_BUFFER_FULL, PXE_STATCODE_DEVICE_FAILURE, PXE_STATCODE_INVALID_CDB, PXE_STATCODE_INVALID_PARAMETER, PXE_STATCODE_NO_DATA, and PXE_STATCODE_UNSUPPORTED.

Referenced by efi_undi_issue().

◆ efi_undi_get_state()

static EFI_STATUS efi_undi_get_state ( struct efi_snp_device snpdev,
PXE_CDB cdb 
)
static

Get state.

Parameters
snpdevSNP device
cdbCommand description block
Return values
efircEFI status code

Definition at line 987 of file efi_snp.c.

988  {
989  EFI_SIMPLE_NETWORK_MODE *mode = &snpdev->mode;
990 
991  DBGC ( snpdev, "UNDI %p GET STATE\n", snpdev );
992 
993  /* Return current state */
994  if ( mode->State == EfiSimpleNetworkInitialized ) {
996  } else if ( mode->State == EfiSimpleNetworkStarted ) {
998  } else {
1000  }
1001 
1002  return 0;
1003 }
uint16_t mode
Acceleration mode.
Definition: ena.h:26
#define PXE_STATFLAGS_GET_STATE_STARTED
Definition: UefiPxe.h:426
#define DBGC(...)
Definition: compiler.h:505
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884
#define PXE_STATFLAGS_GET_STATE_STOPPED
Definition: UefiPxe.h:427
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
#define PXE_STATFLAGS_GET_STATE_INITIALIZED
Definition: UefiPxe.h:425

References DBGC, EfiSimpleNetworkInitialized, EfiSimpleNetworkStarted, mode, efi_snp_device::mode, PXE_STATFLAGS_GET_STATE_INITIALIZED, PXE_STATFLAGS_GET_STATE_STARTED, PXE_STATFLAGS_GET_STATE_STOPPED, and s_pxe_cdb::StatFlags.

Referenced by efi_undi_issue().

◆ efi_undi_start()

static EFI_STATUS efi_undi_start ( struct efi_snp_device snpdev)
static

Start.

Parameters
snpdevSNP device
Return values
efircEFI status code

Definition at line 1011 of file efi_snp.c.

1011  {
1012  EFI_STATUS efirc;
1013 
1014  DBGC ( snpdev, "UNDI %p START\n", snpdev );
1015 
1016  /* Start SNP device */
1017  if ( ( efirc = efi_snp_start ( &snpdev->snp ) ) != 0 )
1018  return efirc;
1019 
1020  return 0;
1021 }
static EFI_STATUS EFIAPI efi_snp_start(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Change SNP state from "stopped" to "started".
Definition: efi_snp.c:190
#define DBGC(...)
Definition: compiler.h:505
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32

References DBGC, efi_snp_start(), and efi_snp_device::snp.

Referenced by efi_undi_issue().

◆ efi_undi_stop()

static EFI_STATUS efi_undi_stop ( struct efi_snp_device snpdev)
static

Stop.

Parameters
snpdevSNP device
Return values
efircEFI status code

Definition at line 1029 of file efi_snp.c.

1029  {
1030  EFI_STATUS efirc;
1031 
1032  DBGC ( snpdev, "UNDI %p STOP\n", snpdev );
1033 
1034  /* Stop SNP device */
1035  if ( ( efirc = efi_snp_stop ( &snpdev->snp ) ) != 0 )
1036  return efirc;
1037 
1038  return 0;
1039 }
#define DBGC(...)
Definition: compiler.h:505
static EFI_STATUS EFIAPI efi_snp_stop(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Change SNP state from "started" to "stopped".
Definition: efi_snp.c:214
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32

References DBGC, efi_snp_stop(), and efi_snp_device::snp.

Referenced by efi_undi_issue().

◆ efi_undi_get_init_info()

static EFI_STATUS efi_undi_get_init_info ( struct efi_snp_device snpdev,
PXE_CDB cdb,
PXE_DB_GET_INIT_INFO db 
)
static

Get initialisation information.

Parameters
snpdevSNP device
cdbCommand description block
dbData block
Return values
efircEFI status code

Definition at line 1049 of file efi_snp.c.

1051  {
1052  struct net_device *netdev = snpdev->netdev;
1054 
1055  DBGC ( snpdev, "UNDI %p GET INIT INFO\n", snpdev );
1056 
1057  /* Populate structure */
1058  memset ( db, 0, sizeof ( *db ) );
1059  db->FrameDataLen = ( netdev->max_pkt_len - ll_protocol->ll_header_len );
1060  db->MediaHeaderLen = ll_protocol->ll_header_len;
1061  db->HWaddrLen = ll_protocol->ll_addr_len;
1062  db->IFtype = ntohs ( ll_protocol->ll_proto );
1065 
1066  return 0;
1067 }
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
#define DBGC(...)
Definition: compiler.h:505
#define ntohs(value)
Definition: byteswap.h:137
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
static struct net_device * netdev
Definition: gdbudp.c:52
#define PXE_STATFLAGS_CABLE_DETECT_SUPPORTED
Definition: UefiPxe.h:440
A network device.
Definition: netdevice.h:353
#define PXE_STATFLAGS_GET_STATUS_NO_MEDIA_SUPPORTED
Definition: UefiPxe.h:444
uint16_t ll_proto
Link-layer protocol.
Definition: netdevice.h:195
static struct dmfe_private * db
Definition: dmfe.c:177
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884
size_t max_pkt_len
Maximum packet length.
Definition: netdevice.h:410
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
void * memset(void *dest, int character, size_t len) __nonnull

References db, DBGC, ll_protocol::ll_addr_len, ll_protocol::ll_header_len, ll_protocol::ll_proto, net_device::ll_protocol, net_device::max_pkt_len, memset(), efi_snp_device::netdev, netdev, ntohs, PXE_STATFLAGS_CABLE_DETECT_SUPPORTED, PXE_STATFLAGS_GET_STATUS_NO_MEDIA_SUPPORTED, and s_pxe_cdb::StatFlags.

Referenced by efi_undi_issue().

◆ efi_undi_initialize()

static EFI_STATUS efi_undi_initialize ( struct efi_snp_device snpdev,
PXE_CDB cdb 
)
static

Initialise.

Parameters
snpdevSNP device
cdbCommand description block
efircEFI status code

Definition at line 1076 of file efi_snp.c.

1077  {
1078  struct net_device *netdev = snpdev->netdev;
1079  EFI_STATUS efirc;
1080 
1081  DBGC ( snpdev, "UNDI %p INITIALIZE\n", snpdev );
1082 
1083  /* Reset SNP device */
1084  if ( ( efirc = efi_snp_initialize ( &snpdev->snp, 0, 0 ) ) != 0 )
1085  return efirc;
1086 
1087  /* Report link state */
1088  if ( ! netdev_link_ok ( netdev ) )
1090 
1091  return 0;
1092 }
static EFI_STATUS EFIAPI efi_snp_initialize(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN extra_rx_bufsize, UINTN extra_tx_bufsize)
Open the network device.
Definition: efi_snp.c:239
#define DBGC(...)
Definition: compiler.h:505
#define PXE_STATFLAGS_INITIALIZED_NO_MEDIA
UNDI Initialize.
Definition: UefiPxe.h:449
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
static int netdev_link_ok(struct net_device *netdev)
Check link state of network device.
Definition: netdevice.h:640
static struct net_device * netdev
Definition: gdbudp.c:52
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
A network device.
Definition: netdevice.h:353
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884

References DBGC, efi_snp_initialize(), efi_snp_device::netdev, netdev, netdev_link_ok(), PXE_STATFLAGS_INITIALIZED_NO_MEDIA, efi_snp_device::snp, and s_pxe_cdb::StatFlags.

Referenced by efi_undi_issue().

◆ efi_undi_reset()

static EFI_STATUS efi_undi_reset ( struct efi_snp_device snpdev)
static

Reset.

Parameters
snpdevSNP device
efircEFI status code

Definition at line 1100 of file efi_snp.c.

1100  {
1101  EFI_STATUS efirc;
1102 
1103  DBGC ( snpdev, "UNDI %p RESET\n", snpdev );
1104 
1105  /* Reset SNP device */
1106  if ( ( efirc = efi_snp_reset ( &snpdev->snp, 0 ) ) != 0 )
1107  return efirc;
1108 
1109  return 0;
1110 }
#define DBGC(...)
Definition: compiler.h:505
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
static EFI_STATUS EFIAPI efi_snp_reset(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN ext_verify)
Reset the network device.
Definition: efi_snp.c:286

References DBGC, efi_snp_reset(), and efi_snp_device::snp.

Referenced by efi_undi_issue().

◆ efi_undi_shutdown()

static EFI_STATUS efi_undi_shutdown ( struct efi_snp_device snpdev)
static

Shutdown.

Parameters
snpdevSNP device
efircEFI status code

Definition at line 1118 of file efi_snp.c.

1118  {
1119  EFI_STATUS efirc;
1120 
1121  DBGC ( snpdev, "UNDI %p SHUTDOWN\n", snpdev );
1122 
1123  /* Reset SNP device */
1124  if ( ( efirc = efi_snp_shutdown ( &snpdev->snp ) ) != 0 )
1125  return efirc;
1126 
1127  return 0;
1128 }
#define DBGC(...)
Definition: compiler.h:505
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
static EFI_STATUS EFIAPI efi_snp_shutdown(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Shut down the network device.
Definition: efi_snp.c:330
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32

References DBGC, efi_snp_shutdown(), and efi_snp_device::snp.

Referenced by efi_undi_issue().

◆ efi_undi_receive_filters()

static EFI_STATUS efi_undi_receive_filters ( struct efi_snp_device snpdev,
PXE_CDB cdb 
)
static

Get/set receive filters.

Parameters
snpdevSNP device
cdbCommand description block
efircEFI status code

Definition at line 1137 of file efi_snp.c.

1138  {
1139 
1140  DBGC ( snpdev, "UNDI %p RECEIVE FILTERS\n", snpdev );
1141 
1142  /* Mark everything as supported */
1147 
1148  return 0;
1149 }
#define DBGC(...)
Definition: compiler.h:505
#define PXE_STATFLAGS_RECEIVE_FILTER_UNICAST
UNDI Receive Filters.
Definition: UefiPxe.h:486
#define PXE_STATFLAGS_RECEIVE_FILTER_ALL_MULTICAST
If set, all multicast packets will be received.
Definition: UefiPxe.h:507
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884
#define PXE_STATFLAGS_RECEIVE_FILTER_BROADCAST
If set, broadcast packets will be received.
Definition: UefiPxe.h:491
#define PXE_STATFLAGS_RECEIVE_FILTER_PROMISCUOUS
If set, all packets will be received.
Definition: UefiPxe.h:502

References DBGC, PXE_STATFLAGS_RECEIVE_FILTER_ALL_MULTICAST, PXE_STATFLAGS_RECEIVE_FILTER_BROADCAST, PXE_STATFLAGS_RECEIVE_FILTER_PROMISCUOUS, PXE_STATFLAGS_RECEIVE_FILTER_UNICAST, and s_pxe_cdb::StatFlags.

Referenced by efi_undi_issue().

◆ efi_undi_station_address()

static EFI_STATUS efi_undi_station_address ( struct efi_snp_device snpdev,
PXE_CDB cdb,
PXE_CPB_STATION_ADDRESS cpb,
PXE_DB_STATION_ADDRESS db 
)
static

Get/set station address.

Parameters
snpdevSNP device
cdbCommand description block
cpbCommand parameter block
efircEFI status code

Definition at line 1159 of file efi_snp.c.

1162  {
1163  struct net_device *netdev = snpdev->netdev;
1165  void *mac;
1166  int reset;
1167  EFI_STATUS efirc;
1168 
1169  DBGC ( snpdev, "UNDI %p STATION ADDRESS\n", snpdev );
1170 
1171  /* Update address if applicable */
1172  reset = ( cdb->OpFlags & PXE_OPFLAGS_STATION_ADDRESS_RESET );
1173  mac = ( cpb ? &cpb->StationAddr : NULL );
1174  if ( ( reset || mac ) &&
1175  ( ( efirc = efi_snp_station_address ( &snpdev->snp, reset,
1176  mac ) ) != 0 ) )
1177  return efirc;
1178 
1179  /* Fill in current addresses, if applicable */
1180  if ( db ) {
1181  memset ( db, 0, sizeof ( *db ) );
1182  memcpy ( &db->StationAddr, netdev->ll_addr,
1184  memcpy ( &db->BroadcastAddr, netdev->ll_broadcast,
1186  memcpy ( &db->PermanentAddr, netdev->hw_addr,
1188  }
1189 
1190  return 0;
1191 }
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
PXE_OPFLAGS OpFlags
Definition: UefiPxe.h:878
#define DBGC(...)
Definition: compiler.h:505
const uint8_t * ll_broadcast
Link-layer broadcast address.
Definition: netdevice.h:390
static EFI_STATUS EFIAPI efi_snp_station_address(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN reset, EFI_MAC_ADDRESS *new)
Set station address.
Definition: efi_snp.c:401
uint8_t mac[ETH_ALEN]
MAC address.
Definition: ena.h:24
PXE_MAC_ADDR StationAddr
If supplied and supported, the current station MAC address will be changed.
Definition: UefiPxe.h:1339
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void * memcpy(void *dest, const void *src, size_t len) __nonnull
uint8_t hw_addr_len
Hardware address length.
Definition: netdevice.h:197
static struct net_device * netdev
Definition: gdbudp.c:52
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
A network device.
Definition: netdevice.h:353
#define PXE_OPFLAGS_STATION_ADDRESS_RESET
Definition: UefiPxe.h:318
static struct dmfe_private * db
Definition: dmfe.c:177
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
uint8_t ll_addr[MAX_LL_ADDR_LEN]
Link-layer address.
Definition: netdevice.h:388
uint8_t hw_addr[MAX_HW_ADDR_LEN]
Hardware address.
Definition: netdevice.h:382
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
void * memset(void *dest, int character, size_t len) __nonnull

References db, DBGC, efi_snp_station_address(), net_device::hw_addr, ll_protocol::hw_addr_len, net_device::ll_addr, ll_protocol::ll_addr_len, net_device::ll_broadcast, net_device::ll_protocol, mac, memcpy(), memset(), efi_snp_device::netdev, netdev, NULL, s_pxe_cdb::OpFlags, PXE_OPFLAGS_STATION_ADDRESS_RESET, efi_snp_device::snp, and s_pxe_cpb_station_address::StationAddr.

Referenced by efi_undi_issue().

◆ efi_undi_get_status()

static EFI_STATUS efi_undi_get_status ( struct efi_snp_device snpdev,
PXE_CDB cdb,
PXE_DB_GET_STATUS db 
)
static

Get interrupt status.

Parameters
snpdevSNP device
cdbCommand description block
dbData block
efircEFI status code

Definition at line 1201 of file efi_snp.c.

1202  {
1203  UINT32 interrupts;
1204  VOID *txbuf;
1205  struct io_buffer *rxbuf;
1206  EFI_STATUS efirc;
1207 
1208  DBGC2 ( snpdev, "UNDI %p GET STATUS\n", snpdev );
1209 
1210  /* Get status */
1211  if ( ( efirc = efi_snp_get_status ( &snpdev->snp, &interrupts,
1212  &txbuf ) ) != 0 )
1213  return efirc;
1214 
1215  /* Report status */
1216  memset ( db, 0, sizeof ( *db ) );
1217  if ( interrupts & EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT )
1219  if ( interrupts & EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT )
1221  if ( txbuf ) {
1222  db->TxBuffer[0] = ( ( intptr_t ) txbuf );
1223  } else {
1225  /* The specification states clearly that UNDI drivers
1226  * should set TXBUF_QUEUE_EMPTY if all completed
1227  * buffer addresses are written into the returned data
1228  * block. However, SnpDxe chooses to interpret
1229  * TXBUF_QUEUE_EMPTY as a synonym for
1230  * NO_TXBUFS_WRITTEN, thereby rendering it entirely
1231  * pointless. Work around this UEFI stupidity, as per
1232  * usual.
1233  */
1234  if ( snpdev->tx_prod == snpdev->tx_cons )
1235  cdb->StatFlags |=
1237  }
1238  rxbuf = list_first_entry ( &snpdev->rx, struct io_buffer, list );
1239  if ( rxbuf )
1240  db->RxFrameLen = iob_len ( rxbuf );
1241  if ( ! netdev_link_ok ( snpdev->netdev ) )
1243 
1244  return 0;
1245 }
#define PXE_STATFLAGS_GET_STATUS_NO_TXBUFS_WRITTEN
This flag is set if no transmitted buffer addresses were written into the DB.
Definition: UefiPxe.h:572
unsigned int UINT32
Definition: ProcessorBind.h:99
unsigned long intptr_t
Definition: stdint.h:21
#define PXE_STATFLAGS_GET_STATUS_TXBUF_QUEUE_EMPTY
This flag is set if the transmitted buffer queue is empty.
Definition: UefiPxe.h:566
#define PXE_STATFLAGS_GET_STATUS_RECEIVE
If set, at least one receive interrupt occurred.
Definition: UefiPxe.h:545
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define list_first_entry(list, type, member)
Get the container of the first entry in a list.
Definition: list.h:334
unsigned int tx_cons
Transmit completion ring consumer counter.
Definition: efi_snp.h:51
static int netdev_link_ok(struct net_device *netdev)
Check link state of network device.
Definition: netdevice.h:640
#define EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
static size_t iob_len(struct io_buffer *iobuf)
Calculate length of data in an I/O buffer.
Definition: iobuf.h:160
#define PXE_STATFLAGS_GET_STATUS_NO_MEDIA
This flag is set if there is no media detected.
Definition: UefiPxe.h:577
#define VOID
Undeclared type.
Definition: Base.h:272
struct list_head rx
Receive queue.
Definition: efi_snp.h:53
unsigned int tx_prod
Transmit completion ring producer counter.
Definition: efi_snp.h:49
static struct dmfe_private * db
Definition: dmfe.c:177
struct list_head list
List of which this buffer is a member.
Definition: iobuf.h:45
#define DBGC2(...)
Definition: compiler.h:522
static EFI_STATUS EFIAPI efi_snp_get_status(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINT32 *interrupts, VOID **txbuf)
Read interrupt status and TX recycled buffer status.
Definition: efi_snp.c:552
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884
#define PXE_STATFLAGS_GET_STATUS_TRANSMIT
If set, at least one transmit interrupt occurred.
Definition: UefiPxe.h:550
#define EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT
void * memset(void *dest, int character, size_t len) __nonnull
A persistent I/O buffer.
Definition: iobuf.h:38

References db, DBGC2, EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT, EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT, efi_snp_get_status(), iob_len(), io_buffer::list, list_first_entry, memset(), efi_snp_device::netdev, netdev_link_ok(), PXE_STATFLAGS_GET_STATUS_NO_MEDIA, PXE_STATFLAGS_GET_STATUS_NO_TXBUFS_WRITTEN, PXE_STATFLAGS_GET_STATUS_RECEIVE, PXE_STATFLAGS_GET_STATUS_TRANSMIT, PXE_STATFLAGS_GET_STATUS_TXBUF_QUEUE_EMPTY, efi_snp_device::rx, efi_snp_device::snp, s_pxe_cdb::StatFlags, efi_snp_device::tx_cons, efi_snp_device::tx_prod, and VOID.

Referenced by efi_undi_issue().

◆ efi_undi_fill_header()

static EFI_STATUS efi_undi_fill_header ( struct efi_snp_device snpdev,
PXE_CDB cdb,
PXE_CPB_ANY cpb 
)
static

Fill header.

Parameters
snpdevSNP device
cdbCommand description block
cpbCommand parameter block
efircEFI status code

Definition at line 1255 of file efi_snp.c.

1256  {
1257  struct net_device *netdev = snpdev->netdev;
1259  PXE_CPB_FILL_HEADER *whole = &cpb->fill_header;
1261  VOID *data;
1262  void *dest;
1263  void *src;
1264  uint16_t proto;
1265  struct io_buffer iobuf;
1266  int rc;
1267 
1268  /* SnpDxe will (pointlessly) use PXE_CPB_FILL_HEADER_FRAGMENTED
1269  * even though we choose to explicitly not claim support for
1270  * fragments via PXE_ROMID_IMP_FRAG_SUPPORTED.
1271  */
1273  data = ( ( void * ) ( intptr_t ) fragged->FragDesc[0].FragAddr);
1274  dest = &fragged->DestAddr;
1275  src = &fragged->SrcAddr;
1276  proto = fragged->Protocol;
1277  } else {
1278  data = ( ( void * ) ( intptr_t ) whole->MediaHeader );
1279  dest = &whole->DestAddr;
1280  src = &whole->SrcAddr;
1281  proto = whole->Protocol;
1282  }
1283 
1284  /* Construct link-layer header */
1285  iob_populate ( &iobuf, data, 0, ll_protocol->ll_header_len );
1286  iob_reserve ( &iobuf, ll_protocol->ll_header_len );
1287  if ( ( rc = ll_protocol->push ( netdev, &iobuf, dest, src,
1288  proto ) ) != 0 )
1289  return EFIRC ( rc );
1290 
1291  return 0;
1292 }
PXE_UINT16 Protocol
Protocol type.
Definition: UefiPxe.h:1595
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
unsigned short uint16_t
Definition: stdint.h:11
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
PXE_MAC_ADDR SrcAddr
Source and destination MAC addresses.
Definition: UefiPxe.h:1612
PXE_OPFLAGS OpFlags
Definition: UefiPxe.h:878
static void iob_populate(struct io_buffer *iobuf, void *data, size_t len, size_t max_len)
Create a temporary I/O buffer.
Definition: iobuf.h:195
unsigned long intptr_t
Definition: stdint.h:21
PXE_MAC_ADDR DestAddr
Definition: UefiPxe.h:1577
PXE_MAC_ADDR SrcAddr
Source and destination MAC addresses.
Definition: UefiPxe.h:1576
A link-layer protocol.
Definition: netdevice.h:115
int(* push)(struct net_device *netdev, struct io_buffer *iobuf, const void *ll_dest, const void *ll_source, uint16_t net_proto)
Add link-layer header.
Definition: netdevice.h:128
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
PXE_CPB_FILL_HEADER_FRAGMENTED fill_header_fragmented
Definition: efi_snp.c:901
static const void * src
Definition: string.h:48
PXE_MEDIA_PROTOCOL Protocol
Protocol type.
Definition: UefiPxe.h:1625
static struct net_device * netdev
Definition: gdbudp.c:52
#define PXE_OPFLAGS_FILL_HEADER_FRAGMENTED
Definition: UefiPxe.h:376
A network device.
Definition: netdevice.h:353
PXE_CPB_FILL_HEADER fill_header
Definition: efi_snp.c:900
#define VOID
Undeclared type.
Definition: Base.h:272
#define iob_reserve(iobuf, len)
Definition: iobuf.h:72
PXE_UINT64 MediaHeader
Address of first byte of media header.
Definition: UefiPxe.h:1583
if(len >=6 *4) __asm__ __volatile__("movsl" if(len >=5 *4) __asm__ __volatile__("movsl" if(len >=4 *4) __asm__ __volatile__("movsl" if(len >=3 *4) __asm__ __volatile__("movsl" if(len >=2 *4) __asm__ __volatile__("movsl" if(len >=1 *4) __asm__ __volatile__("movsl" if((len % 4) >=2) __asm__ __volatile__("movsw" if((len % 2) >=1) __asm__ __volatile__("movsb" return dest
Definition: string.h:151
uint8_t data[48]
Additional event data.
Definition: ena.h:22
struct s_pxe_cpb_fill_header_fragmented::@607 FragDesc[MAX_XMIT_FRAGMENTS]
Array of packet fragment descriptors.
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
PXE_UINT64 FragAddr
Address of this packet fragment.
Definition: UefiPxe.h:1650
A persistent I/O buffer.
Definition: iobuf.h:38

References data, dest, s_pxe_cpb_fill_header::DestAddr, s_pxe_cpb_fill_header_fragmented::DestAddr, EFIRC, PXE_CPB_ANY::fill_header, PXE_CPB_ANY::fill_header_fragmented, s_pxe_cpb_fill_header_fragmented::FragAddr, s_pxe_cpb_fill_header_fragmented::FragDesc, iob_populate(), iob_reserve, ll_protocol::ll_header_len, net_device::ll_protocol, s_pxe_cpb_fill_header::MediaHeader, efi_snp_device::netdev, netdev, s_pxe_cdb::OpFlags, s_pxe_cpb_fill_header::Protocol, s_pxe_cpb_fill_header_fragmented::Protocol, ll_protocol::push, PXE_OPFLAGS_FILL_HEADER_FRAGMENTED, rc, src, s_pxe_cpb_fill_header::SrcAddr, s_pxe_cpb_fill_header_fragmented::SrcAddr, and VOID.

Referenced by efi_undi_issue().

◆ efi_undi_transmit()

static EFI_STATUS efi_undi_transmit ( struct efi_snp_device snpdev,
PXE_CPB_TRANSMIT cpb 
)
static

Transmit.

Parameters
snpdevSNP device
cpbCommand parameter block
efircEFI status code

Definition at line 1301 of file efi_snp.c.

1302  {
1303  VOID *data = ( ( void * ) ( intptr_t ) cpb->FrameAddr );
1304  EFI_STATUS efirc;
1305 
1306  DBGC2 ( snpdev, "UNDI %p TRANSMIT\n", snpdev );
1307 
1308  /* Transmit packet */
1309  if ( ( efirc = efi_snp_transmit ( &snpdev->snp, 0, cpb->DataLen,
1310  data, NULL, NULL, NULL ) ) != 0 )
1311  return efirc;
1312 
1313  return 0;
1314 }
PXE_UINT32 DataLen
Length of the data portion of the frame buffer in bytes.
Definition: UefiPxe.h:1675
unsigned long intptr_t
Definition: stdint.h:21
PXE_UINT64 FrameAddr
Address of first byte of frame buffer.
Definition: UefiPxe.h:1669
static EFI_STATUS EFIAPI efi_snp_transmit(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN ll_header_len, UINTN len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
Start packet transmission.
Definition: efi_snp.c:611
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
#define VOID
Undeclared type.
Definition: Base.h:272
#define DBGC2(...)
Definition: compiler.h:522
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
uint8_t data[48]
Additional event data.
Definition: ena.h:22
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322

References data, s_pxe_cpb_transmit::DataLen, DBGC2, efi_snp_transmit(), s_pxe_cpb_transmit::FrameAddr, NULL, efi_snp_device::snp, and VOID.

Referenced by efi_undi_issue().

◆ efi_undi_receive()

static EFI_STATUS efi_undi_receive ( struct efi_snp_device snpdev,
PXE_CPB_RECEIVE cpb,
PXE_DB_RECEIVE db 
)
static

Receive.

Parameters
snpdevSNP device
cpbCommand parameter block
efircEFI status code

Definition at line 1323 of file efi_snp.c.

1325  {
1326  struct net_device *netdev = snpdev->netdev;
1328  VOID *data = ( ( void * ) ( intptr_t ) cpb->BufferAddr );
1329  UINTN hdr_len;
1330  UINTN len = cpb->BufferLen;
1333  UINT16 proto;
1334  EFI_STATUS efirc;
1335 
1336  DBGC2 ( snpdev, "UNDI %p RECEIVE\n", snpdev );
1337 
1338  /* Receive packet */
1339  if ( ( efirc = efi_snp_receive ( &snpdev->snp, &hdr_len, &len, data,
1340  &src, &dest, &proto ) ) != 0 )
1341  return efirc;
1342 
1343  /* Describe frame */
1344  memset ( db, 0, sizeof ( *db ) );
1345  memcpy ( &db->SrcAddr, &src, ll_protocol->ll_addr_len );
1346  memcpy ( &db->DestAddr, &dest, ll_protocol->ll_addr_len );
1347  db->FrameLen = len;
1348  db->Protocol = proto;
1349  db->MediaHeaderLen = ll_protocol->ll_header_len;
1351 
1352  return 0;
1353 }
PXE_UINT32 BufferLen
Length of receive buffer.
Definition: UefiPxe.h:1738
uint8_t ll_header_len
Link-layer header length.
Definition: netdevice.h:201
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
32-byte buffer containing a network Media Access Control address.
Definition: UefiBaseType.h:98
unsigned long intptr_t
Definition: stdint.h:21
A link-layer protocol.
Definition: netdevice.h:115
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void * memcpy(void *dest, const void *src, size_t len) __nonnull
static EFI_STATUS EFIAPI efi_snp_receive(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN *ll_header_len, UINTN *len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
Receive packet.
Definition: efi_snp.c:761
static const void * src
Definition: string.h:48
ring len
Length.
Definition: dwmac.h:231
static struct net_device * netdev
Definition: gdbudp.c:52
unsigned short UINT16
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
PXE_UINT64 BufferAddr
Address of first byte of receive buffer.
Definition: UefiPxe.h:1731
A network device.
Definition: netdevice.h:353
UINT64 UINTN
Unsigned value of native width.
#define VOID
Undeclared type.
Definition: Base.h:272
static struct dmfe_private * db
Definition: dmfe.c:177
#define DBGC2(...)
Definition: compiler.h:522
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
if(len >=6 *4) __asm__ __volatile__("movsl" if(len >=5 *4) __asm__ __volatile__("movsl" if(len >=4 *4) __asm__ __volatile__("movsl" if(len >=3 *4) __asm__ __volatile__("movsl" if(len >=2 *4) __asm__ __volatile__("movsl" if(len >=1 *4) __asm__ __volatile__("movsl" if((len % 4) >=2) __asm__ __volatile__("movsw" if((len % 2) >=1) __asm__ __volatile__("movsb" return dest
Definition: string.h:151
uint8_t data[48]
Additional event data.
Definition: ena.h:22
#define PXE_FRAME_TYPE_PROMISCUOUS
Definition: UefiPxe.h:667
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
void * memset(void *dest, int character, size_t len) __nonnull

References s_pxe_cpb_receive::BufferAddr, s_pxe_cpb_receive::BufferLen, data, db, DBGC2, dest, efi_snp_receive(), len, ll_protocol::ll_addr_len, ll_protocol::ll_header_len, net_device::ll_protocol, memcpy(), memset(), efi_snp_device::netdev, netdev, PXE_FRAME_TYPE_PROMISCUOUS, efi_snp_device::snp, src, and VOID.

Referenced by efi_undi_issue().

◆ efi_undi_issue()

static EFIAPI VOID efi_undi_issue ( UINT64  cdb_phys)
static

UNDI entry point.

Definition at line 1356 of file efi_snp.c.

1356  {
1357  PXE_CDB *cdb = ( ( void * ) ( intptr_t ) cdb_phys );
1358  PXE_CPB_ANY *cpb = ( ( void * ) ( intptr_t ) cdb->CPBaddr );
1359  PXE_DB_ANY *db = ( ( void * ) ( intptr_t ) cdb->DBaddr );
1360  struct efi_snp_device *snpdev;
1361  EFI_STATUS efirc;
1362 
1363  /* Identify device */
1364  snpdev = efi_undi_snpdev ( cdb->IFnum );
1365  if ( ! snpdev ) {
1366  DBGC ( cdb, "UNDI invalid interface number %d\n", cdb->IFnum );
1369  return;
1370  }
1371 
1372  /* Fail if net device is currently claimed for use by iPXE */
1373  if ( efi_snp_claimed ) {
1374  cdb->StatCode = PXE_STATCODE_BUSY;
1376  return;
1377  }
1378 
1379  /* Handle opcode */
1382  switch ( cdb->OpCode ) {
1383 
1384  case PXE_OPCODE_GET_STATE:
1385  efirc = efi_undi_get_state ( snpdev, cdb );
1386  break;
1387 
1388  case PXE_OPCODE_START:
1389  efirc = efi_undi_start ( snpdev );
1390  break;
1391 
1392  case PXE_OPCODE_STOP:
1393  efirc = efi_undi_stop ( snpdev );
1394  break;
1395 
1397  efirc = efi_undi_get_init_info ( snpdev, cdb,
1398  &db->get_init_info );
1399  break;
1400 
1401  case PXE_OPCODE_INITIALIZE:
1402  efirc = efi_undi_initialize ( snpdev, cdb );
1403  break;
1404 
1405  case PXE_OPCODE_RESET:
1406  efirc = efi_undi_reset ( snpdev );
1407  break;
1408 
1409  case PXE_OPCODE_SHUTDOWN:
1410  efirc = efi_undi_shutdown ( snpdev );
1411  break;
1412 
1414  efirc = efi_undi_receive_filters ( snpdev, cdb );
1415  break;
1416 
1418  efirc = efi_undi_station_address ( snpdev, cdb,
1419  &cpb->station_address,
1420  &db->station_address );
1421  break;
1422 
1423  case PXE_OPCODE_GET_STATUS:
1424  efirc = efi_undi_get_status ( snpdev, cdb, &db->get_status );
1425  break;
1426 
1428  efirc = efi_undi_fill_header ( snpdev, cdb, cpb );
1429  break;
1430 
1431  case PXE_OPCODE_TRANSMIT:
1432  efirc = efi_undi_transmit ( snpdev, &cpb->transmit );
1433  break;
1434 
1435  case PXE_OPCODE_RECEIVE:
1436  efirc = efi_undi_receive ( snpdev, &cpb->receive,
1437  &db->receive );
1438  break;
1439 
1440  default:
1441  DBGC ( snpdev, "UNDI %p unsupported opcode %#04x\n",
1442  snpdev, cdb->OpCode );
1443  efirc = EFI_UNSUPPORTED;
1444  break;
1445  }
1446 
1447  /* Convert EFI status code to UNDI status code */
1448  if ( efirc != 0 ) {
1451  cdb->StatCode = efi_undi_statcode ( efirc );
1452  }
1453 }
static EFI_STATUS efi_undi_shutdown(struct efi_snp_device *snpdev)
Shutdown.
Definition: efi_snp.c:1118
#define EFI_UNSUPPORTED
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:118
static PXE_STATCODE efi_undi_statcode(EFI_STATUS efirc)
Convert EFI status code to UNDI status code.
Definition: efi_snp.c:967
static EFI_STATUS efi_undi_get_state(struct efi_snp_device *snpdev, PXE_CDB *cdb)
Get state.
Definition: efi_snp.c:987
#define PXE_OPCODE_SHUTDOWN
Change the UNDI operational state from Initialized to Started.
Definition: UefiPxe.h:123
PXE_STATCODE StatCode
Definition: UefiPxe.h:883
static EFI_STATUS efi_undi_receive_filters(struct efi_snp_device *snpdev, PXE_CDB *cdb)
Get/set receive filters.
Definition: efi_snp.c:1137
static EFI_STATUS efi_undi_transmit(struct efi_snp_device *snpdev, PXE_CPB_TRANSMIT *cpb)
Transmit.
Definition: efi_snp.c:1301
#define DBGC(...)
Definition: compiler.h:505
#define PXE_STATFLAGS_COMMAND_FAILED
Definition: UefiPxe.h:418
#define PXE_OPCODE_INITIALIZE
Changed UNDI operational state from Started to Initialized.
Definition: UefiPxe.h:113
static EFI_STATUS efi_undi_get_init_info(struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_DB_GET_INIT_INFO *db)
Get initialisation information.
Definition: efi_snp.c:1049
#define PXE_STATCODE_BUSY
Definition: UefiPxe.h:609
unsigned long intptr_t
Definition: stdint.h:21
#define PXE_OPCODE_FILL_HEADER
Fill media header in packet for transmit.
Definition: UefiPxe.h:163
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
PXE_CPB_RECEIVE receive
Definition: efi_snp.c:903
static EFI_STATUS efi_undi_stop(struct efi_snp_device *snpdev)
Stop.
Definition: efi_snp.c:1029
#define PXE_OPCODE_STATION_ADDRESS
Read & change station MAC address.
Definition: UefiPxe.h:138
static EFI_STATUS efi_undi_station_address(struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_CPB_STATION_ADDRESS *cpb, PXE_DB_STATION_ADDRESS *db)
Get/set station address.
Definition: efi_snp.c:1159
static EFI_STATUS efi_undi_reset(struct efi_snp_device *snpdev)
Reset.
Definition: efi_snp.c:1100
#define PXE_OPCODE_RESET
Re-initialize the NIC H/W.
Definition: UefiPxe.h:118
#define PXE_OPCODE_TRANSMIT
Transmit packet(s).
Definition: UefiPxe.h:168
#define PXE_STATFLAGS_STATUS_MASK
Common StatFlags that can be returned by all commands.
Definition: UefiPxe.h:416
PXE_CPB_STATION_ADDRESS station_address
Definition: efi_snp.c:899
PXE_UINT64 CPBaddr
Definition: UefiPxe.h:881
static EFI_STATUS efi_undi_receive(struct efi_snp_device *snpdev, PXE_CPB_RECEIVE *cpb, PXE_DB_RECEIVE *db)
Receive.
Definition: efi_snp.c:1323
static struct efi_snp_device * efi_undi_snpdev(unsigned int ifnum)
Identify UNDI SNP device.
Definition: efi_snp.c:951
Union type for data blocks.
Definition: efi_snp.c:907
An SNP device.
Definition: efi_snp.h:29
PXE_CPB_TRANSMIT transmit
Definition: efi_snp.c:902
#define PXE_OPCODE_STOP
Change UNDI operational state from Started to Stopped.
Definition: UefiPxe.h:98
#define PXE_OPCODE_GET_STATUS
Get & clear interrupt status.
Definition: UefiPxe.h:158
static struct dmfe_private * db
Definition: dmfe.c:177
static EFI_STATUS efi_undi_fill_header(struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_CPB_ANY *cpb)
Fill header.
Definition: efi_snp.c:1255
static EFI_STATUS efi_undi_get_status(struct efi_snp_device *snpdev, PXE_CDB *cdb, PXE_DB_GET_STATUS *db)
Get interrupt status.
Definition: efi_snp.c:1201
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
PXE_STATFLAGS StatFlags
Definition: UefiPxe.h:884
#define PXE_OPCODE_RECEIVE
Receive packet.
Definition: UefiPxe.h:173
#define PXE_OPCODE_RECEIVE_FILTERS
Read & change state of packet receive filters.
Definition: UefiPxe.h:133
#define PXE_STATCODE_INVALID_CDB
Definition: UefiPxe.h:607
#define PXE_OPCODE_GET_STATE
Return UNDI operational state.
Definition: UefiPxe.h:88
#define PXE_OPCODE_GET_INIT_INFO
Get UNDI initialization information.
Definition: UefiPxe.h:103
static EFI_STATUS efi_undi_initialize(struct efi_snp_device *snpdev, PXE_CDB *cdb)
Initialise.
Definition: efi_snp.c:1076
PXE_UINT16 IFnum
Definition: UefiPxe.h:885
#define PXE_OPCODE_START
Change UNDI operational state from Stopped to Started.
Definition: UefiPxe.h:93
PXE_OPCODE OpCode
Definition: UefiPxe.h:877
#define PXE_STATFLAGS_COMMAND_COMPLETE
Definition: UefiPxe.h:417
Union type for command parameter blocks.
Definition: efi_snp.c:898
PXE_UINT64 DBaddr
Definition: UefiPxe.h:882
#define PXE_STATCODE_SUCCESS
Common StatCodes returned by all UNDI commands, UNDI protocol functions and BC protocol functions.
Definition: UefiPxe.h:605
static EFI_STATUS efi_undi_start(struct efi_snp_device *snpdev)
Start.
Definition: efi_snp.c:1011

References s_pxe_cdb::CPBaddr, db, s_pxe_cdb::DBaddr, DBGC, efi_snp_claimed, efi_undi_fill_header(), efi_undi_get_init_info(), efi_undi_get_state(), efi_undi_get_status(), efi_undi_initialize(), efi_undi_receive(), efi_undi_receive_filters(), efi_undi_reset(), efi_undi_shutdown(), efi_undi_snpdev(), efi_undi_start(), efi_undi_statcode(), efi_undi_station_address(), efi_undi_stop(), efi_undi_transmit(), EFI_UNSUPPORTED, s_pxe_cdb::IFnum, s_pxe_cdb::OpCode, PXE_OPCODE_FILL_HEADER, PXE_OPCODE_GET_INIT_INFO, PXE_OPCODE_GET_STATE, PXE_OPCODE_GET_STATUS, PXE_OPCODE_INITIALIZE, PXE_OPCODE_RECEIVE, PXE_OPCODE_RECEIVE_FILTERS, PXE_OPCODE_RESET, PXE_OPCODE_SHUTDOWN, PXE_OPCODE_START, PXE_OPCODE_STATION_ADDRESS, PXE_OPCODE_STOP, PXE_OPCODE_TRANSMIT, PXE_STATCODE_BUSY, PXE_STATCODE_INVALID_CDB, PXE_STATCODE_SUCCESS, PXE_STATFLAGS_COMMAND_COMPLETE, PXE_STATFLAGS_COMMAND_FAILED, PXE_STATFLAGS_STATUS_MASK, PXE_CPB_ANY::receive, s_pxe_cdb::StatCode, s_pxe_cdb::StatFlags, PXE_CPB_ANY::station_address, and PXE_CPB_ANY::transmit.

Referenced by efi_snp_probe().

◆ efi_vlan_set()

static EFI_STATUS EFIAPI efi_vlan_set ( EFI_VLAN_CONFIG_PROTOCOL vcfg,
UINT16  tag,
UINT8  priority 
)
static

Create or modify VLAN device.

Parameters
vcfgVLAN configuration protocol
tagVLAN tag
priorityDefault VLAN priority
Return values
efircEFI status code

Definition at line 1507 of file efi_snp.c.

1508  {
1509  struct efi_snp_device *snpdev =
1510  container_of ( vcfg, struct efi_snp_device, vcfg );
1511  struct net_device *trunk = snpdev->netdev;
1512  struct efi_saved_tpl tpl;
1513  int rc;
1514 
1515  /* Raise TPL */
1516  efi_raise_tpl ( &tpl );
1517 
1518  /* Create or modify VLAN device */
1519  if ( ( rc = vlan_create ( trunk, tag, priority ) ) != 0 ) {
1520  DBGC ( snpdev, "SNPDEV %p could not create VLAN tag %d: %s\n",
1521  snpdev, tag, strerror ( rc ) );
1522  goto err_create;
1523  }
1524  DBGC ( snpdev, "SNPDEV %p created VLAN tag %d priority %d\n",
1525  snpdev, tag, priority );
1526 
1527  err_create:
1528  efi_restore_tpl ( &tpl );
1529  return EFIRC ( rc );
1530 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
EFI_VLAN_CONFIG_PROTOCOL vcfg
VLAN configuration protocol.
Definition: efi_snp.h:57
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define DBGC(...)
Definition: compiler.h:505
int vlan_create(struct net_device *trunk, unsigned int tag, unsigned int priority)
Create VLAN device.
Definition: vlan.c:344
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
A network device.
Definition: netdevice.h:353
An SNP device.
Definition: efi_snp.h:29
An EFI saved task priority level.
Definition: efi.h:80
uint16_t priority
Priotity.
Definition: stp.h:13
uint64_t tag
Identity tag.
Definition: edd.h:31
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167

References container_of, DBGC, efi_raise_tpl(), efi_restore_tpl(), EFIRC, efi_snp_device::netdev, priority, rc, strerror(), tag, efi_snp_device::vcfg, and vlan_create().

◆ efi_vlan_find()

static EFI_STATUS EFIAPI efi_vlan_find ( EFI_VLAN_CONFIG_PROTOCOL vcfg,
UINT16 filter,
UINT16 count,
EFI_VLAN_FIND_DATA **  entries 
)
static

Find VLAN device(s)

Parameters
vcfgVLAN configuration protocol
filterVLAN tag, or NULL to find all VLANs
countNumber of VLANs
entriesList of VLANs
Return values
efircEFI status code

Definition at line 1541 of file efi_snp.c.

1543  {
1545  struct efi_snp_device *snpdev =
1546  container_of ( vcfg, struct efi_snp_device, vcfg );
1547  struct net_device *trunk = snpdev->netdev;
1548  struct net_device *vlan;
1549  struct efi_saved_tpl tpl;
1550  EFI_VLAN_FIND_DATA *entry;
1551  VOID *buffer;
1552  unsigned int tag;
1553  unsigned int tci;
1554  size_t len;
1555  EFI_STATUS efirc;
1556  int rc;
1557 
1558  /* Raise TPL */
1559  efi_raise_tpl ( &tpl );
1560 
1561  /* Count number of matching VLANs */
1562  *count = 0;
1563  for ( tag = 1 ; VLAN_TAG_IS_VALID ( tag ) ; tag++ ) {
1564  if ( filter && ( tag != *filter ) )
1565  continue;
1566  if ( ! ( vlan = vlan_find ( trunk, tag ) ) )
1567  continue;
1568  (*count)++;
1569  }
1570 
1571  /* Allocate buffer to hold results */
1572  len = ( (*count) * sizeof ( *entry ) );
1573  if ( ( efirc = bs->AllocatePool ( EfiBootServicesData, len,
1574  &buffer ) ) != 0 ) {
1575  rc = -EEFI ( efirc );
1576  goto err_alloc;
1577  }
1578 
1579  /* Fill in buffer */
1580  *entries = buffer;
1581  entry = *entries;
1582  for ( tag = 1 ; VLAN_TAG_IS_VALID ( tag ) ; tag++ ) {
1583  if ( filter && ( tag != *filter ) )
1584  continue;
1585  if ( ! ( vlan = vlan_find ( trunk, tag ) ) )
1586  continue;
1587  tci = vlan_tci ( vlan );
1588  entry->VlanId = VLAN_TAG ( tci );
1589  entry->Priority = VLAN_PRIORITY ( tci );
1590  assert ( entry->VlanId == tag );
1591  entry++;
1592  }
1593  assert ( entry == &(*entries)[*count] );
1594 
1595  /* Success */
1596  rc = 0;
1597 
1598  err_alloc:
1599  efi_restore_tpl ( &tpl );
1600  return EFIRC ( rc );
1601 }
#define VLAN_TAG(tci)
Extract VLAN tag from tag control information.
Definition: vlan.h:30
EFI_BOOT_SERVICES * BootServices
A pointer to the EFI Boot Services Table.
Definition: UefiSpec.h:2099
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define EEFI(efirc)
Convert an EFI status code to an iPXE status code.
Definition: efi.h:175
EFI_VLAN_CONFIG_PROTOCOL vcfg
VLAN configuration protocol.
Definition: efi_snp.h:57
UINT8_t filter
Receive packet filter.
Definition: pxe_api.h:68
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
uint32_t buffer
Buffer index (or NETVSC_RNDIS_NO_BUFFER)
Definition: netvsc.h:16
#define VLAN_TAG_IS_VALID(tag)
Check VLAN tag is valid.
Definition: vlan.h:55
struct net_device * vlan_find(struct net_device *trunk, unsigned int tag)
Identify VLAN device.
Definition: vlan.c:209
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
ring len
Length.
Definition: dwmac.h:231
static unsigned int count
Number of entries.
Definition: dwmac.h:225
EFI Boot Services Table.
Definition: UefiSpec.h:1931
EFI_VLAN_FIND_DATA.
Definition: VlanConfig.h:28
A network device.
Definition: netdevice.h:353
An SNP device.
Definition: efi_snp.h:29
#define VOID
Undeclared type.
Definition: Base.h:272
An EFI saved task priority level.
Definition: efi.h:80
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
__weak unsigned int vlan_tci(struct net_device *netdev __unused)
Get the VLAN tag control information (when VLAN support is not present)
Definition: netdevice.c:1199
EFI_SYSTEM_TABLE * efi_systab
The data portions of a loaded Boot Serves Driver, and the default data allocation type used by a Boot...
uint64_t tag
Identity tag.
Definition: edd.h:31
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define VLAN_PRIORITY(tci)
Extract VLAN priority from tag control information.
Definition: vlan.h:38
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167
EFI_ALLOCATE_POOL AllocatePool
Definition: UefiSpec.h:1949

References EFI_BOOT_SERVICES::AllocatePool, assert(), EFI_SYSTEM_TABLE::BootServices, buffer, container_of, count, EEFI, efi_raise_tpl(), efi_restore_tpl(), efi_systab, EfiBootServicesData, EFIRC, filter, len, efi_snp_device::netdev, rc, tag, efi_snp_device::vcfg, vlan_find(), VLAN_PRIORITY, VLAN_TAG, VLAN_TAG_IS_VALID, vlan_tci(), and VOID.

◆ efi_vlan_remove()

static EFI_STATUS EFIAPI efi_vlan_remove ( EFI_VLAN_CONFIG_PROTOCOL vcfg,
UINT16  tag 
)
static

Remove VLAN device.

Parameters
vcfgVLAN configuration protocol
tagVLAN tag
Return values
efircEFI status code

Definition at line 1610 of file efi_snp.c.

1611  {
1612  struct efi_snp_device *snpdev =
1613  container_of ( vcfg, struct efi_snp_device, vcfg );
1614  struct net_device *trunk = snpdev->netdev;
1615  struct net_device *vlan;
1616  struct efi_saved_tpl tpl;
1617  int rc;
1618 
1619  /* Raise TPL */
1620  efi_raise_tpl ( &tpl );
1621 
1622  /* Identify VLAN device */
1623  vlan = vlan_find ( trunk, tag );
1624  if ( ! vlan ) {
1625  DBGC ( snpdev, "SNPDEV %p could not find VLAN tag %d\n",
1626  snpdev, tag );
1627  rc = -ENOENT;
1628  goto err_find;
1629  }
1630 
1631  /* Remove VLAN device */
1632  vlan_destroy ( vlan );
1633  DBGC ( snpdev, "SNPDEV %p removed VLAN tag %d\n", snpdev, tag );
1634 
1635  /* Success */
1636  rc = 0;
1637 
1638  err_find:
1639  efi_restore_tpl ( &tpl );
1640  return EFIRC ( rc );
1641 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
EFI_VLAN_CONFIG_PROTOCOL vcfg
VLAN configuration protocol.
Definition: efi_snp.h:57
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
#define DBGC(...)
Definition: compiler.h:505
#define ENOENT
No such file or directory.
Definition: errno.h:515
struct net_device * vlan_find(struct net_device *trunk, unsigned int tag)
Identify VLAN device.
Definition: vlan.c:209
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
A network device.
Definition: netdevice.h:353
An SNP device.
Definition: efi_snp.h:29
int vlan_destroy(struct net_device *netdev)
Destroy VLAN device.
Definition: vlan.c:434
An EFI saved task priority level.
Definition: efi.h:80
uint64_t tag
Identity tag.
Definition: edd.h:31
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167

References container_of, DBGC, efi_raise_tpl(), efi_restore_tpl(), EFIRC, ENOENT, efi_snp_device::netdev, rc, tag, efi_snp_device::vcfg, vlan_destroy(), and vlan_find().

◆ efi_snp_get_driver_name()

static EFI_STATUS EFIAPI efi_snp_get_driver_name ( EFI_COMPONENT_NAME2_PROTOCOL name2,
CHAR8 *language  __unused,
CHAR16 **  driver_name 
)
static

Look up driver name.

Parameters
name2Component name protocol
languageLanguage to use
driver_nameDriver name to fill in
Return values
efircEFI status code

Definition at line 1666 of file efi_snp.c.

1667  {
1668  struct efi_snp_device *snpdev =
1669  container_of ( name2, struct efi_snp_device, name2 );
1670 
1671  *driver_name = snpdev->driver_name;
1672  return 0;
1673 }
EFI_COMPONENT_NAME2_PROTOCOL name2
Component name protocol.
Definition: efi_snp.h:59
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
An SNP device.
Definition: efi_snp.h:29
wchar_t driver_name[16]
Driver name.
Definition: efi_snp.h:75

References container_of, efi_snp_device::driver_name, and efi_snp_device::name2.

Referenced by efi_snp_probe().

◆ efi_snp_get_controller_name()

static EFI_STATUS EFIAPI efi_snp_get_controller_name ( EFI_COMPONENT_NAME2_PROTOCOL name2,
EFI_HANDLE device  __unused,
EFI_HANDLE child  __unused,
CHAR8 *language  __unused,
CHAR16 **  controller_name 
)
static

Look up controller name.

Parameters
name2Component name protocol
deviceDevice
childChild device, or NULL
languageLanguage to use
driver_nameDevice name to fill in
Return values
efircEFI status code

Definition at line 1686 of file efi_snp.c.

1690  {
1691  struct efi_snp_device *snpdev =
1692  container_of ( name2, struct efi_snp_device, name2 );
1693 
1694  *controller_name = snpdev->controller_name;
1695  return 0;
1696 }
EFI_COMPONENT_NAME2_PROTOCOL name2
Component name protocol.
Definition: efi_snp.h:59
wchar_t controller_name[64]
Controller name.
Definition: efi_snp.h:77
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
An SNP device.
Definition: efi_snp.h:29

References container_of, efi_snp_device::controller_name, and efi_snp_device::name2.

Referenced by efi_snp_probe().

◆ efi_snp_load_file()

static EFI_STATUS EFIAPI efi_snp_load_file ( EFI_LOAD_FILE_PROTOCOL load_file,
EFI_DEVICE_PATH_PROTOCOL *path  __unused,
BOOLEAN  booting,
UINTN *len  __unused,
VOID *data  __unused 
)
static

Load file.

Parameters
loadfileLoad file protocol
pathFile path
bootingLoading as part of a boot attempt
Return values
efircEFI status code

Definition at line 1714 of file efi_snp.c.

1717  {
1718  struct efi_snp_device *snpdev =
1720  struct net_device *netdev = snpdev->netdev;
1721  int rc;
1722 
1723  /* Fail unless this is a boot attempt */
1724  if ( ! booting ) {
1725  DBGC ( snpdev, "SNPDEV %p cannot load non-boot file\n",
1726  snpdev );
1727  return EFI_UNSUPPORTED;
1728  }
1729 
1730  /* Claim network devices for use by iPXE */
1731  efi_snp_claim();
1732 
1733  /* Start watchdog holdoff timer */
1735 
1736  /* Boot from network device */
1737  if ( ( rc = ipxe ( netdev ) ) != 0 )
1738  goto err_ipxe;
1739 
1740  /* Reset console */
1741  console_reset();
1742 
1743  err_ipxe:
1745  efi_snp_release();
1746  return EFIRC ( rc );
1747 }
#define EFI_UNSUPPORTED
Enumeration of EFI_STATUS.
Definition: UefiBaseType.h:118
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_claim(void)
Claim network devices for use by iPXE.
Definition: efi_snp.h:92
int ipxe(struct net_device *netdev)
Main iPXE flow of execution.
Definition: autoboot.c:586
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:36
static void efi_watchdog_start(void)
Start EFI watchdog holdoff timer.
Definition: efi_watchdog.h:18
static struct net_device * netdev
Definition: gdbudp.c:52
static void efi_watchdog_stop(void)
Stop EFI watchdog holdoff timer.
Definition: efi_watchdog.h:27
A network device.
Definition: netdevice.h:353
An SNP device.
Definition: efi_snp.h:29
static void efi_snp_release(void)
Release network devices for use via SNP.
Definition: efi_snp.h:100
static void console_reset(void)
Reset console.
Definition: console.h:215
EFI_LOAD_FILE_PROTOCOL load_file
Load file protocol handle.
Definition: efi_snp.h:61
#define EFIRC(rc)
Convert an iPXE status code to an EFI status code.
Definition: efi.h:167

References console_reset(), container_of, DBGC, efi_snp_claim(), efi_snp_release(), EFI_UNSUPPORTED, efi_watchdog_start(), efi_watchdog_stop(), EFIRC, ipxe(), efi_snp_device::load_file, efi_snp_device::netdev, netdev, and rc.

◆ efi_snp_demux()

static struct efi_snp_device* efi_snp_demux ( struct net_device netdev)
static

Locate SNP device corresponding to network device.

Parameters
netdevNetwork device
Return values
snpSNP device, or NULL if not found

Definition at line 1767 of file efi_snp.c.

1767  {
1768  struct efi_snp_device *snpdev;
1769 
1770  list_for_each_entry ( snpdev, &efi_snp_devices, list ) {
1771  if ( snpdev->netdev == netdev )
1772  return snpdev;
1773  }
1774  return NULL;
1775 }
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:432
static struct net_device * netdev
Definition: gdbudp.c:52
An SNP device.
Definition: efi_snp.h:29
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31

References efi_snp_device::list, list_for_each_entry, efi_snp_device::netdev, netdev, and NULL.

Referenced by efi_snp_notify(), efi_snp_remove(), and last_opened_snpdev().

◆ efi_snp_probe()

static int efi_snp_probe ( struct net_device netdev,
void *priv  __unused 
)
static

Create SNP device.

Parameters
netdevNetwork device
privPrivate data
Return values
rcReturn status code

Definition at line 1784 of file efi_snp.c.

1784  {
1786  struct efi_device *efidev;
1787  struct efi_snp_device *snpdev;
1788  unsigned int ifcnt;
1789  void *interface;
1790  unsigned int tci;
1791  char vlan_name[ 12 /* ", VLAN xxxx" + NUL */ ];
1792  int leak = 0;
1793  EFI_STATUS efirc;
1794  int rc;
1795 
1796  /* Allocate the SNP device */
1797  snpdev = zalloc ( sizeof ( *snpdev ) );
1798  if ( ! snpdev ) {
1799  rc = -ENOMEM;
1800  goto err_alloc_snp;
1801  }
1802  snpdev->netdev = netdev_get ( netdev );
1803  INIT_LIST_HEAD ( &snpdev->rx );
1804 
1805  /* Find parent EFI device, if any */
1806  efidev = efidev_parent ( netdev->dev );
1807  if ( efidev )
1808  snpdev->parent = efidev->device;
1809 
1810  /* Sanity check */
1811  if ( netdev->ll_protocol->ll_addr_len > sizeof ( EFI_MAC_ADDRESS ) ) {
1812  DBGC ( snpdev, "SNPDEV %p cannot support link-layer address "
1813  "length %d for %s\n", snpdev,
1815  rc = -ENOTSUP;
1816  goto err_ll_addr_len;
1817  }
1818 
1819  /* Populate the SNP structure */
1820  memcpy ( &snpdev->snp, &efi_snp_device_snp, sizeof ( snpdev->snp ) );
1821  snpdev->snp.Mode = &snpdev->mode;
1822  if ( ( efirc = bs->CreateEvent ( EVT_NOTIFY_WAIT, TPL_NOTIFY,
1823  efi_snp_wait_for_packet, snpdev,
1824  &snpdev->snp.WaitForPacket ) ) != 0 ){
1825  rc = -EEFI ( efirc );
1826  DBGC ( snpdev, "SNPDEV %p could not create event: %s\n",
1827  snpdev, strerror ( rc ) );
1828  goto err_create_event;
1829  }
1830 
1831  /* Populate the SNP mode structure */
1833  efi_snp_set_mode ( snpdev );
1834 
1835  /* Populate the NII structure */
1836  memcpy ( &snpdev->nii, &efi_snp_device_nii, sizeof ( snpdev->nii ) );
1837  snpdev->nii.Id = ( ( intptr_t ) &efi_snp_undi );
1838  snpdev->nii.IfNum = efi_undi_ifnum ( snpdev );
1840  ifcnt = ( ( efi_snp_undi.IFcntExt << 8 ) | efi_snp_undi.IFcnt );
1841  if ( ifcnt < snpdev->nii.IfNum )
1842  ifcnt = snpdev->nii.IfNum;
1843  efi_snp_undi.IFcnt = ( ifcnt & 0xff );
1844  efi_snp_undi.IFcntExt = ( ifcnt >> 8 );
1846  sizeof ( efi_snp_undi ) );
1847 
1848  /* Populate the VLAN configuration protocol */
1849  memcpy ( &snpdev->vcfg, &efi_vlan, sizeof ( snpdev->vcfg ) );
1850 
1851  /* Populate the component name structure */
1852  efi_snprintf ( snpdev->driver_name,
1853  ( sizeof ( snpdev->driver_name ) /
1854  sizeof ( snpdev->driver_name[0] ) ),
1855  "%s %s", product_short_name, netdev->dev->driver_name );
1856  tci = vlan_tci ( netdev );
1857  if ( tci ) {
1858  snprintf ( vlan_name, sizeof ( vlan_name ), ", VLAN %d",
1859  VLAN_TAG ( tci ) );
1860  } else {
1861  vlan_name[0] = '\0';
1862  }
1863  efi_snprintf ( snpdev->controller_name,
1864  ( sizeof ( snpdev->controller_name ) /
1865  sizeof ( snpdev->controller_name[0] ) ),
1866  "%s %s (%s, %s%s)", product_short_name,
1868  netdev_addr ( netdev ), vlan_name );
1871  snpdev->name2.SupportedLanguages = "en";
1872 
1873  /* Populate the load file protocol structure */
1875  sizeof ( snpdev->load_file ) );
1876 
1877  /* Populate the device name */
1878  efi_snprintf ( snpdev->name, ( sizeof ( snpdev->name ) /
1879  sizeof ( snpdev->name[0] ) ),
1880  "%s", netdev->name );
1881 
1882  /* Construct device path */
1883  snpdev->path = efi_netdev_path ( netdev );
1884  if ( ! snpdev->path ) {
1885  rc = -ENOMEM;
1886  goto err_path;
1887  }
1888 
1889  /* Install the SNP */
1890  if ( ( efirc = bs->InstallMultipleProtocolInterfaces (
1891  &snpdev->handle,
1894  &efi_nii_protocol_guid, &snpdev->nii,
1895  &efi_nii31_protocol_guid, &snpdev->nii,
1899  NULL ) ) != 0 ) {
1900  rc = -EEFI ( efirc );
1901  DBGC ( snpdev, "SNPDEV %p could not install protocols: %s\n",
1902  snpdev, strerror ( rc ) );
1903  goto err_install_protocol_interface;
1904  }
1905 
1906  /* SnpDxe will repeatedly start up and shut down our NII/UNDI
1907  * interface (in order to obtain the MAC address) before
1908  * discovering that it cannot install another SNP on the same
1909  * handle. This causes the underlying network device to be
1910  * unexpectedly closed.
1911  *
1912  * Prevent this by opening our own NII (and NII31) protocol
1913  * instances to prevent SnpDxe from attempting to bind to
1914  * them.
1915  */
1916  if ( ( rc = efi_open_by_driver ( snpdev->handle,
1918  &interface ) ) != 0 ) {
1919  DBGC ( snpdev, "SNPDEV %p could not open NII protocol: %s\n",
1920  snpdev, strerror ( rc ) );
1921  goto err_open_nii;
1922  }
1923  if ( ( rc = efi_open_by_driver ( snpdev->handle,
1925  &interface ) ) != 0 ) {
1926  DBGC ( snpdev, "SNPDEV %p could not open NII31 protocol: %s\n",
1927  snpdev, strerror ( rc ) );
1928  goto err_open_nii31;
1929  }
1930 
1931  /* Add as child of EFI parent device, if applicable */
1932  if ( snpdev->parent &&
1933  ( ( rc = efi_child_add ( snpdev->parent,
1934  snpdev->handle ) ) != 0 ) ) {
1935  DBGC ( snpdev, "SNPDEV %p could not become child of %s: %s\n",
1936  snpdev, efi_handle_name ( efidev->device ),
1937  strerror ( rc ) );
1938  goto err_efi_child_add;
1939  }
1940 
1941  /* Install HII */
1942  if ( ( rc = efi_snp_hii_install ( snpdev ) ) != 0 ) {
1943  DBGC ( snpdev, "SNPDEV %p could not install HII: %s\n",
1944  snpdev, strerror ( rc ) );
1945  /* HII fails on several platforms. It's
1946  * non-essential, so treat this as a non-fatal
1947  * error.
1948  */
1949  }
1950 
1951  /* Add to list of SNP devices */
1952  list_add ( &snpdev->list, &efi_snp_devices );
1953 
1954  DBGC ( snpdev, "SNPDEV %p installed for %s as device %s\n",
1955  snpdev, netdev->name, efi_handle_name ( snpdev->handle ) );
1956  return 0;
1957 
1958  list_del ( &snpdev->list );
1959  if ( snpdev->package_list )
1960  leak |= efi_snp_hii_uninstall ( snpdev );
1961  if ( snpdev->parent )
1962  efi_child_del ( snpdev->parent, snpdev->handle );
1963  err_efi_child_add:
1965  err_open_nii31:
1967  err_open_nii:
1968  if ( ( efirc = bs->UninstallMultipleProtocolInterfaces (
1969  snpdev->handle,
1972  &efi_nii_protocol_guid, &snpdev->nii,
1973  &efi_nii31_protocol_guid, &snpdev->nii,
1977  NULL ) ) != 0 ) {
1978  DBGC ( snpdev, "SNPDEV %p could not uninstall: %s\n",
1979  snpdev, strerror ( -EEFI ( efirc ) ) );
1980  leak = 1;
1981  }
1982  efi_nullify_snp ( &snpdev->snp );
1983  efi_nullify_nii ( &snpdev->nii );
1984  efi_nullify_vlan ( &snpdev->vcfg );
1985  efi_nullify_name2 ( &snpdev->name2 );
1986  efi_nullify_load_file ( &snpdev->load_file );
1987  err_install_protocol_interface:
1988  if ( ! leak )
1989  free ( snpdev->path );
1990  err_path:
1991  bs->CloseEvent ( snpdev->snp.WaitForPacket );
1992  err_create_event:
1993  err_ll_addr_len:
1994  if ( ! leak ) {
1995  netdev_put ( netdev );
1996  free ( snpdev );
1997  }
1998  err_alloc_snp:
1999  if ( leak )
2000  DBGC ( snpdev, "SNPDEV %p nullified and leaked\n", snpdev );
2001  return rc;
2002 }
EFI_GUID efi_nii31_protocol_guid
Network interface identifier protocol GUID (new version)
Definition: efi_guid.c:309
const char product_short_name[]
Product short name string.
Definition: version.c:77
#define VLAN_TAG(tci)
Extract VLAN tag from tag control information.
Definition: vlan.h:30
EFI_BOOT_SERVICES * BootServices
A pointer to the EFI Boot Services Table.
Definition: UefiSpec.h:2099
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define EEFI(efirc)
Convert an EFI status code to an iPXE status code.
Definition: efi.h:175
uint8_t ll_addr_len
Link-layer address length.
Definition: netdevice.h:199
EFI_VLAN_CONFIG_PROTOCOL vcfg
VLAN configuration protocol.
Definition: efi_snp.h:57
#define list_add(new, head)
Add a new entry to the head of a list.
Definition: list.h:70
EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL nii
The network interface identifier.
Definition: efi_snp.h:55
EFI_COMPONENT_NAME2_PROTOCOL name2
Component name protocol.
Definition: efi_snp.h:59
32-byte buffer containing a network Media Access Control address.
Definition: UefiBaseType.h:98
EFI_GUID efi_simple_network_protocol_guid
Simple network protocol GUID.
Definition: efi_guid.c:341
#define DBGC(...)
Definition: compiler.h:505
static PXE_SW_UNDI efi_snp_undi
UNDI interface.
Definition: efi_snp.c:1460
char name[40]
Name.
Definition: device.h:79
EFI_INSTALL_MULTIPLE_PROTOCOL_INTERFACES InstallMultipleProtocolInterfaces
Definition: UefiSpec.h:2010
EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME GetControllerName
EFI_CLOSE_EVENT CloseEvent
Definition: UefiSpec.h:1959
static unsigned int efi_undi_ifnum(struct efi_snp_device *snpdev)
Get UNDI SNP device interface number.
Definition: efi_snp.c:936
EFI_HANDLE device
EFI device handle.
Definition: efi_driver.h:22
UINT32 State
Reports the current state of the network interface.
int efi_child_add(EFI_HANDLE parent, EFI_HANDLE child)
Add EFI device as child of another EFI device.
Definition: efi_utils.c:111
unsigned long intptr_t
Definition: stdint.h:21
wchar_t controller_name[64]
Controller name.
Definition: efi_snp.h:77
static const char * netdev_addr(struct net_device *netdev)
Get printable network device link-layer address.
Definition: netdevice.h:542
EFI_HANDLE handle
EFI device handle.
Definition: efi_snp.h:37
#define TPL_NOTIFY
Definition: UefiSpec.h:650
static EFI_SIMPLE_NETWORK_PROTOCOL efi_snp_device_snp
SNP interface.
Definition: efi_snp.c:873
#define ENOTSUP
Operation not supported.
Definition: errno.h:590
UINT64 Id
The address of the first byte of the identifying structure for this network interface.
static EFI_STATUS EFIAPI efi_snp_get_driver_name(EFI_COMPONENT_NAME2_PROTOCOL *name2, CHAR8 *language __unused, CHAR16 **driver_name)
Look up driver name.
Definition: efi_snp.c:1666
EFI_SIMPLE_NETWORK_MODE * Mode
Pointer to the EFI_SIMPLE_NETWORK_MODE data for the device.
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void efi_child_del(EFI_HANDLE parent, EFI_HANDLE child)
Remove EFI device as child of another EFI device.
Definition: efi_utils.c:138
#define list_del(list)
Delete an entry from a list.
Definition: list.h:120
#define ENOMEM
Not enough space.
Definition: errno.h:535
void * memcpy(void *dest, const void *src, size_t len) __nonnull
int efi_snp_hii_uninstall(struct efi_snp_device *snpdev)
Uninstall HII protocol and package for SNP device.
Definition: efi_snp_hii.c:797
int efi_snp_hii_install(struct efi_snp_device *snpdev)
Install HII protocol and packages for SNP device.
Definition: efi_snp_hii.c:659
EFI_HII_PACKAGE_LIST_HEADER * package_list
HII package list.
Definition: efi_snp.h:65
static void netdev_put(struct net_device *netdev)
Drop reference to network device.
Definition: netdevice.h:576
An object interface.
Definition: interface.h:125
void efi_close_by_driver(EFI_HANDLE handle, EFI_GUID *protocol)
Close protocol opened for persistent use by a driver.
Definition: efi_open.c:279
#define efi_open_by_driver(handle, protocol, interface)
Open protocol for persistent use by a driver.
Definition: efi.h:474
EFI_COMPONENT_NAME2_GET_DRIVER_NAME GetDriverName
static struct net_device * netdev
Definition: gdbudp.c:52
int efi_snprintf(wchar_t *wbuf, size_t wsize, const char *fmt,...)
Write a formatted string to a buffer.
Definition: efi_strings.c:107
EFI_CREATE_EVENT CreateEvent
Definition: UefiSpec.h:1955
static EFI_VLAN_CONFIG_PROTOCOL efi_vlan
VLAN configuration protocol.
Definition: efi_snp.c:1644
EFI_GUID efi_vlan_config_protocol_guid
VLAN configuration protocol GUID.
Definition: efi_guid.c:433
static EFI_LOAD_FILE_PROTOCOL efi_snp_load_file_protocol
Load file protocol.
Definition: efi_snp.c:1750
const char * driver_name
Driver name.
Definition: device.h:81
wchar_t name[sizeof(((struct net_device *) NULL) ->name)]
Device name.
Definition: efi_snp.h:73
const char * efi_handle_name(EFI_HANDLE handle)
Get name of an EFI handle.
Definition: efi_debug.c:652
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
static EFIAPI VOID efi_undi_issue(UINT64 cdb_phys)
UNDI entry point.
Definition: efi_snp.c:1356
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
EFI_DEVICE_PATH_PROTOCOL * efi_netdev_path(struct net_device *netdev)
Construct EFI device path for network device.
Definition: efi_path.c:411
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:55
void * zalloc(size_t size)
Allocate cleared memory.
Definition: malloc.c:662
EFI Boot Services Table.
Definition: UefiSpec.h:1931
static void efi_snp_set_mode(struct efi_snp_device *snpdev)
Set EFI SNP mode based on iPXE net device parameters.
Definition: efi_snp.c:121
EFI_UNINSTALL_MULTIPLE_PROTOCOL_INTERFACES UninstallMultipleProtocolInterfaces
Definition: UefiSpec.h:2011
An SNP device.
Definition: efi_snp.h:29
PXE_UINT8 Fudge
makes 8-bit cksum zero.
Definition: UefiPxe.h:813
#define EVT_NOTIFY_WAIT
Definition: UefiSpec.h:453
An EFI device.
Definition: efi_driver.h:18
static struct net_device * netdev_get(struct net_device *netdev)
Get reference to network device.
Definition: netdevice.h:565
void efi_nullify_vlan(EFI_VLAN_CONFIG_PROTOCOL *vcfg)
Nullify VLAN configuration interface.
Definition: efi_null.c:234
EFI_GUID efi_device_path_protocol_guid
Device path protocol GUID.
Definition: efi_guid.c:169
EFI_GUID efi_component_name2_protocol_guid
Component name 2 protocol GUID.
Definition: efi_guid.c:161
static uint8_t efi_undi_checksum(void *data, size_t len)
Calculate UNDI byte checksum.
Definition: efi_snp.c:921
struct list_head rx
Receive queue.
Definition: efi_snp.h:53
static EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL efi_snp_device_nii
Network Identification Interface (NII)
Definition: efi_snp.c:1483
wchar_t driver_name[16]
Driver name.
Definition: efi_snp.h:75
struct device * dev
Underlying hardware device.
Definition: netdevice.h:365
EFI_GUID efi_nii_protocol_guid
Network interface identifier protocol GUID (old version)
Definition: efi_guid.c:305
void efi_nullify_name2(EFI_COMPONENT_NAME2_PROTOCOL *name2)
Nullify Component Name Protocol interface.
Definition: efi_null.c:273
#define INIT_LIST_HEAD(list)
Initialise a list head.
Definition: list.h:46
char name[NETDEV_NAME_LEN]
Name of this network device.
Definition: netdevice.h:363
CHAR8 * SupportedLanguages
A Null-terminated ASCII string array that contains one or more supported language codes.
PXE_UINT8 IFcntExt
physical connector count upper byte.
Definition: UefiPxe.h:818
EFI_LOAD_FILE_PROTOCOL load_file
Load file protocol handle.
Definition: efi_snp.h:61
PXE_UINT64 EntryPoint
API entry point.
Definition: UefiPxe.h:821
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
PXE_UINT8 IFcnt
physical connector count lower byte.
Definition: UefiPxe.h:815
void efi_nullify_load_file(EFI_LOAD_FILE_PROTOCOL *load_file)
Nullify Load File Protocol interface.
Definition: efi_null.c:298
__weak unsigned int vlan_tci(struct net_device *netdev __unused)
Get the VLAN tag control information (when VLAN support is not present)
Definition: netdevice.c:1199
int snprintf(char *buf, size_t size, const char *fmt,...)
Write a formatted string to a buffer.
Definition: vsprintf.c:383
EFI_SYSTEM_TABLE * efi_systab
void efi_nullify_nii(EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL *nii)
Nullify NII interface.
Definition: efi_null.c:192
struct efi_device * efidev_parent(struct device *dev)
Get parent EFI device.
Definition: efi_driver.c:129
UINT16 IfNum
The network interface number that is being identified by this Network Interface Identifier Protocol.
EFI_GUID efi_load_file_protocol_guid
Load file protocol GUID.
Definition: efi_guid.c:265
EFI_DEVICE_PATH_PROTOCOL * path
The device path.
Definition: efi_snp.h:79
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
static VOID EFIAPI efi_snp_wait_for_packet(EFI_EVENT event __unused, VOID *context)
Poll event.
Definition: efi_snp.c:847
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
EFI_EVENT WaitForPacket
Event used with WaitForEvent() to wait for a packet to be received.
void efi_nullify_snp(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Nullify SNP interface.
Definition: efi_null.c:157
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31
EFI_HANDLE parent
EFI parent device handle (if any)
Definition: efi_snp.h:35
struct ll_protocol * ll_protocol
Link-layer protocol.
Definition: netdevice.h:373
static EFI_STATUS EFIAPI efi_snp_get_controller_name(EFI_COMPONENT_NAME2_PROTOCOL *name2, EFI_HANDLE device __unused, EFI_HANDLE child __unused, CHAR8 *language __unused, CHAR16 **controller_name)
Look up controller name.
Definition: efi_snp.c:1686

References EFI_SYSTEM_TABLE::BootServices, EFI_BOOT_SERVICES::CloseEvent, efi_snp_device::controller_name, EFI_BOOT_SERVICES::CreateEvent, DBGC, net_device::dev, efi_device::device, efi_snp_device::driver_name, device::driver_name, EEFI, efi_child_add(), efi_child_del(), efi_close_by_driver(), efi_component_name2_protocol_guid, efi_device_path_protocol_guid, efi_handle_name(), efi_load_file_protocol_guid, efi_netdev_path(), efi_nii31_protocol_guid, efi_nii_protocol_guid, efi_nullify_load_file(), efi_nullify_name2(), efi_nullify_nii(), efi_nullify_snp(), efi_nullify_vlan(), efi_open_by_driver, efi_simple_network_protocol_guid, efi_snp_device_nii, efi_snp_device_snp, efi_snp_get_controller_name(), efi_snp_get_driver_name(), efi_snp_hii_install(), efi_snp_hii_uninstall(), efi_snp_load_file_protocol, efi_snp_set_mode(), efi_snp_undi, efi_snp_wait_for_packet(), efi_snprintf(), efi_systab, efi_undi_checksum(), efi_undi_ifnum(), efi_undi_issue(), efi_vlan, efi_vlan_config_protocol_guid, efidev_parent(), EfiSimpleNetworkStopped, ENOMEM, ENOTSUP, s_pxe_sw_undi::EntryPoint, EVT_NOTIFY_WAIT, free, s_pxe_sw_undi::Fudge, _EFI_COMPONENT_NAME2_PROTOCOL::GetControllerName, _EFI_COMPONENT_NAME2_PROTOCOL::GetDriverName, efi_snp_device::handle, _EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL::Id, s_pxe_sw_undi::IFcnt, s_pxe_sw_undi::IFcntExt, _EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL::IfNum, INIT_LIST_HEAD, EFI_BOOT_SERVICES::InstallMultipleProtocolInterfaces, efi_snp_device::list, list_add, list_del, ll_protocol::ll_addr_len, net_device::ll_protocol, efi_snp_device::load_file, memcpy(), efi_snp_device::mode, _EFI_SIMPLE_NETWORK_PROTOCOL::Mode, efi_snp_device::name, device::name, net_device::name, efi_snp_device::name2, efi_snp_device::netdev, netdev, netdev_addr(), netdev_get(), netdev_put(), efi_snp_device::nii, NULL, efi_snp_device::package_list, efi_snp_device::parent, efi_snp_device::path, product_short_name, rc, efi_snp_device::rx, efi_snp_device::snp, snprintf(), EFI_SIMPLE_NETWORK_MODE::State, strerror(), _EFI_COMPONENT_NAME2_PROTOCOL::SupportedLanguages, TPL_NOTIFY, EFI_BOOT_SERVICES::UninstallMultipleProtocolInterfaces, efi_snp_device::vcfg, VLAN_TAG, vlan_tci(), _EFI_SIMPLE_NETWORK_PROTOCOL::WaitForPacket, and zalloc().

◆ efi_snp_notify()

static void efi_snp_notify ( struct net_device netdev,
void *priv  __unused 
)
static

Handle SNP device or link state change.

Parameters
netdevNetwork device
privPrivate data

Definition at line 2010 of file efi_snp.c.

2010  {
2011  struct efi_snp_device *snpdev;
2012 
2013  /* Locate SNP device */
2014  snpdev = efi_snp_demux ( netdev );
2015  if ( ! snpdev ) {
2016  DBG ( "SNP skipping non-SNP device %s\n", netdev->name );
2017  return;
2018  }
2019 
2020  /* Update link state */
2021  snpdev->mode.MediaPresent =
2022  ( netdev_link_ok ( netdev ) ? TRUE : FALSE );
2023  DBGC ( snpdev, "SNPDEV %p link is %s\n", snpdev,
2024  ( snpdev->mode.MediaPresent ? "up" : "down" ) );
2025 
2026  /* Update mode state */
2027  efi_snp_set_state ( snpdev );
2028 }
BOOLEAN MediaPresent
TRUE if media are connected to the network interface; otherwise FALSE.
#define DBGC(...)
Definition: compiler.h:505
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int netdev_link_ok(struct net_device *netdev)
Check link state of network device.
Definition: netdevice.h:640
static struct net_device * netdev
Definition: gdbudp.c:52
An SNP device.
Definition: efi_snp.h:29
#define TRUE
Definition: tlan.h:46
char name[NETDEV_NAME_LEN]
Name of this network device.
Definition: netdevice.h:363
#define FALSE
Definition: tlan.h:45
#define DBG(...)
Print a debugging message.
Definition: compiler.h:498
EFI_SIMPLE_NETWORK_MODE mode
The SNP "mode" (parameters)
Definition: efi_snp.h:41
static struct efi_snp_device * efi_snp_demux(struct net_device *netdev)
Locate SNP device corresponding to network device.
Definition: efi_snp.c:1767

References DBG, DBGC, efi_snp_demux(), efi_snp_set_state(), FALSE, EFI_SIMPLE_NETWORK_MODE::MediaPresent, efi_snp_device::mode, net_device::name, netdev, netdev_link_ok(), and TRUE.

◆ efi_snp_remove()

static void efi_snp_remove ( struct net_device netdev,
void *priv  __unused 
)
static

Destroy SNP device.

Parameters
netdevNetwork device
privPrivate data

Definition at line 2036 of file efi_snp.c.

2036  {
2038  struct efi_snp_device *snpdev;
2039  int leak = efi_shutdown_in_progress;
2040  EFI_STATUS efirc;
2041 
2042  /* Locate SNP device */
2043  snpdev = efi_snp_demux ( netdev );
2044  if ( ! snpdev ) {
2045  DBG ( "SNP skipping non-SNP device %s\n", netdev->name );
2046  return;
2047  }
2048 
2049  /* Uninstall the SNP */
2050  list_del ( &snpdev->list );
2051  if ( snpdev->package_list )
2052  leak |= efi_snp_hii_uninstall ( snpdev );
2053  if ( snpdev->parent )
2054  efi_child_del ( snpdev->parent, snpdev->handle );
2057  if ( ( ! efi_shutdown_in_progress ) &&
2058  ( ( efirc = bs->UninstallMultipleProtocolInterfaces (
2059  snpdev->handle,
2062  &efi_nii_protocol_guid, &snpdev->nii,
2063  &efi_nii31_protocol_guid, &snpdev->nii,
2067  NULL ) ) != 0 ) ) {
2068  DBGC ( snpdev, "SNPDEV %p could not uninstall: %s\n",
2069  snpdev, strerror ( -EEFI ( efirc ) ) );
2070  leak = 1;
2071  }
2072  efi_nullify_snp ( &snpdev->snp );
2073  efi_nullify_nii ( &snpdev->nii );
2074  efi_nullify_vlan ( &snpdev->vcfg );
2075  efi_nullify_name2 ( &snpdev->name2 );
2076  efi_nullify_load_file ( &snpdev->load_file );
2077  if ( ! leak )
2078  free ( snpdev->path );
2079  bs->CloseEvent ( snpdev->snp.WaitForPacket );
2080  if ( ! leak ) {
2081  netdev_put ( snpdev->netdev );
2082  free ( snpdev );
2083  }
2084 
2085  /* Report leakage, if applicable */
2086  if ( leak && ( ! efi_shutdown_in_progress ) )
2087  DBGC ( snpdev, "SNPDEV %p nullified and leaked\n", snpdev );
2088 }
EFI_GUID efi_nii31_protocol_guid
Network interface identifier protocol GUID (new version)
Definition: efi_guid.c:309
EFI_BOOT_SERVICES * BootServices
A pointer to the EFI Boot Services Table.
Definition: UefiSpec.h:2099
#define EEFI(efirc)
Convert an EFI status code to an iPXE status code.
Definition: efi.h:175
EFI_VLAN_CONFIG_PROTOCOL vcfg
VLAN configuration protocol.
Definition: efi_snp.h:57
EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL nii
The network interface identifier.
Definition: efi_snp.h:55
EFI_COMPONENT_NAME2_PROTOCOL name2
Component name protocol.
Definition: efi_snp.h:59
EFI_GUID efi_simple_network_protocol_guid
Simple network protocol GUID.
Definition: efi_guid.c:341
#define DBGC(...)
Definition: compiler.h:505
EFI_CLOSE_EVENT CloseEvent
Definition: UefiSpec.h:1959
EFI_HANDLE handle
EFI device handle.
Definition: efi_snp.h:37
struct net_device * netdev
The underlying iPXE network device.
Definition: efi_snp.h:33
void efi_child_del(EFI_HANDLE parent, EFI_HANDLE child)
Remove EFI device as child of another EFI device.
Definition: efi_utils.c:138
#define list_del(list)
Delete an entry from a list.
Definition: list.h:120
int efi_snp_hii_uninstall(struct efi_snp_device *snpdev)
Uninstall HII protocol and package for SNP device.
Definition: efi_snp_hii.c:797
EFI_HII_PACKAGE_LIST_HEADER * package_list
HII package list.
Definition: efi_snp.h:65
static void netdev_put(struct net_device *netdev)
Drop reference to network device.
Definition: netdevice.h:576
void efi_close_by_driver(EFI_HANDLE handle, EFI_GUID *protocol)
Close protocol opened for persistent use by a driver.
Definition: efi_open.c:279
static struct net_device * netdev
Definition: gdbudp.c:52
EFI_GUID efi_vlan_config_protocol_guid
VLAN configuration protocol GUID.
Definition: efi_guid.c:433
EFI_SIMPLE_NETWORK_PROTOCOL snp
The SNP structure itself.
Definition: efi_snp.h:39
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:55
EFI Boot Services Table.
Definition: UefiSpec.h:1931
EFI_UNINSTALL_MULTIPLE_PROTOCOL_INTERFACES UninstallMultipleProtocolInterfaces
Definition: UefiSpec.h:2011
An SNP device.
Definition: efi_snp.h:29
void efi_nullify_vlan(EFI_VLAN_CONFIG_PROTOCOL *vcfg)
Nullify VLAN configuration interface.
Definition: efi_null.c:234
EFI_GUID efi_device_path_protocol_guid
Device path protocol GUID.
Definition: efi_guid.c:169
EFI_GUID efi_component_name2_protocol_guid
Component name 2 protocol GUID.
Definition: efi_guid.c:161
EFI_GUID efi_nii_protocol_guid
Network interface identifier protocol GUID (old version)
Definition: efi_guid.c:305
void efi_nullify_name2(EFI_COMPONENT_NAME2_PROTOCOL *name2)
Nullify Component Name Protocol interface.
Definition: efi_null.c:273
char name[NETDEV_NAME_LEN]
Name of this network device.
Definition: netdevice.h:363
EFI_LOAD_FILE_PROTOCOL load_file
Load file protocol handle.
Definition: efi_snp.h:61
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:32
void efi_nullify_load_file(EFI_LOAD_FILE_PROTOCOL *load_file)
Nullify Load File Protocol interface.
Definition: efi_null.c:298
EFI_SYSTEM_TABLE * efi_systab
void efi_nullify_nii(EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL *nii)
Nullify NII interface.
Definition: efi_null.c:192
#define DBG(...)
Print a debugging message.
Definition: compiler.h:498
EFI_GUID efi_load_file_protocol_guid
Load file protocol GUID.
Definition: efi_guid.c:265
EFI_DEVICE_PATH_PROTOCOL * path
The device path.
Definition: efi_snp.h:79
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
static struct efi_snp_device * efi_snp_demux(struct net_device *netdev)
Locate SNP device corresponding to network device.
Definition: efi_snp.c:1767
EFI_EVENT WaitForPacket
Event used with WaitForEvent() to wait for a packet to be received.
void efi_nullify_snp(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Nullify SNP interface.
Definition: efi_null.c:157
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31
EFI_HANDLE parent
EFI parent device handle (if any)
Definition: efi_snp.h:35
int efi_shutdown_in_progress
EFI shutdown is in progress.
Definition: efi_init.c:60

References EFI_SYSTEM_TABLE::BootServices, EFI_BOOT_SERVICES::CloseEvent, DBG, DBGC, EEFI, efi_child_del(), efi_close_by_driver(), efi_component_name2_protocol_guid, efi_device_path_protocol_guid, efi_load_file_protocol_guid, efi_nii31_protocol_guid, efi_nii_protocol_guid, efi_nullify_load_file(), efi_nullify_name2(), efi_nullify_nii(), efi_nullify_snp(), efi_nullify_vlan(), efi_shutdown_in_progress, efi_simple_network_protocol_guid, efi_snp_demux(), efi_snp_hii_uninstall(), efi_systab, efi_vlan_config_protocol_guid, free, efi_snp_device::handle, efi_snp_device::list, list_del, efi_snp_device::load_file, net_device::name, efi_snp_device::name2, efi_snp_device::netdev, netdev, netdev_put(), efi_snp_device::nii, NULL, efi_snp_device::package_list, efi_snp_device::parent, efi_snp_device::path, efi_snp_device::snp, strerror(), EFI_BOOT_SERVICES::UninstallMultipleProtocolInterfaces, efi_snp_device::vcfg, and _EFI_SIMPLE_NETWORK_PROTOCOL::WaitForPacket.

◆ find_snpdev()

struct efi_snp_device* find_snpdev ( EFI_HANDLE  handle)

Find SNP device by EFI device handle.

Parameters
handleEFI device handle
Return values
snpdevSNP device, or NULL

Definition at line 2104 of file efi_snp.c.

2104  {
2105  struct efi_snp_device *snpdev;
2106 
2107  list_for_each_entry ( snpdev, &efi_snp_devices, list ) {
2108  if ( snpdev->handle == handle )
2109  return snpdev;
2110  }
2111  return NULL;
2112 }
EFI_HANDLE handle
EFI device handle.
Definition: efi_snp.h:37
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:432
An SNP device.
Definition: efi_snp.h:29
uint16_t handle
Handle.
Definition: smbios.h:17
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31

References handle, efi_snp_device::handle, efi_snp_device::list, list_for_each_entry, and NULL.

Referenced by snpnet_supported().

◆ last_opened_snpdev()

struct efi_snp_device* last_opened_snpdev ( void  )

Get most recently opened SNP device.

Return values
snpdevMost recently opened SNP device, or NULL

Definition at line 2119 of file efi_snp.c.

2119  {
2120  struct net_device *netdev;
2121 
2123  if ( ! netdev )
2124  return NULL;
2125 
2126  return efi_snp_demux ( netdev );
2127 }
static struct net_device * netdev
Definition: gdbudp.c:52
struct net_device * last_opened_netdev(void)
Get most recently opened network device.
Definition: netdevice.c:1048
A network device.
Definition: netdevice.h:353
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
static struct efi_snp_device * efi_snp_demux(struct net_device *netdev)
Locate SNP device corresponding to network device.
Definition: efi_snp.c:1767

References efi_snp_demux(), last_opened_netdev(), netdev, and NULL.

Referenced by efi_image_exec().

◆ efi_snp_add_claim()

void efi_snp_add_claim ( int  delta)

Add to SNP claimed/released count.

Parameters
deltaClaim count change

Definition at line 2134 of file efi_snp.c.

2134  {
2135  struct efi_snp_device *snpdev;
2136 
2137  /* Raise TPL if we are about to claim devices */
2138  if ( ! efi_snp_claimed )
2140 
2141  /* Claim SNP devices */
2142  efi_snp_claimed += delta;
2143  assert ( efi_snp_claimed >= 0 );
2144 
2145  /* Update SNP mode state for each interface */
2146  list_for_each_entry ( snpdev, &efi_snp_devices, list )
2147  efi_snp_set_state ( snpdev );
2148 
2149  /* Restore TPL if we have released devices */
2150  if ( ! efi_snp_claimed )
2152 }
void efi_raise_tpl(struct efi_saved_tpl *tpl)
Raise task priority level to internal level.
Definition: efi_init.c:383
static void efi_snp_set_state(struct efi_snp_device *snpdev)
Set EFI SNP mode state.
Definition: efi_snp.c:92
static int efi_snp_claimed
Network devices are currently claimed for use by iPXE.
Definition: efi_snp.c:49
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:432
static struct efi_saved_tpl efi_snp_saved_tpl
TPL prior to network devices being claimed.
Definition: efi_snp.c:52
An SNP device.
Definition: efi_snp.h:29
void efi_restore_tpl(struct efi_saved_tpl *tpl)
Restore task priority level.
Definition: efi_init.c:399
struct list_head list
List of SNP devices.
Definition: efi_snp.h:31

References assert(), efi_raise_tpl(), efi_restore_tpl(), efi_snp_claimed, efi_snp_saved_tpl, efi_snp_set_state(), efi_snp_device::list, and list_for_each_entry.

Referenced by efi_snp_claim(), and efi_snp_release().

Variable Documentation

◆ efi_snp_claimed

int efi_snp_claimed
static

◆ efi_snp_saved_tpl

struct efi_saved_tpl efi_snp_saved_tpl
static

TPL prior to network devices being claimed.

Definition at line 52 of file efi_snp.c.

Referenced by efi_snp_add_claim().

◆ efi_snp_device_snp

EFI_SIMPLE_NETWORK_PROTOCOL efi_snp_device_snp
static
Initial value:
= {
.Start = efi_snp_start,
.Stop = efi_snp_stop,
.Initialize = efi_snp_initialize,
.Reset = efi_snp_reset,
.Shutdown = efi_snp_shutdown,
.ReceiveFilters = efi_snp_receive_filters,
.StationAddress = efi_snp_station_address,
.Statistics = efi_snp_statistics,
.MCastIpToMac = efi_snp_mcast_ip_to_mac,
.NvData = efi_snp_nvdata,
.GetStatus = efi_snp_get_status,
.Transmit = efi_snp_transmit,
.Receive = efi_snp_receive,
}
static EFI_STATUS EFIAPI efi_snp_initialize(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN extra_rx_bufsize, UINTN extra_tx_bufsize)
Open the network device.
Definition: efi_snp.c:239
static EFI_STATUS EFIAPI efi_snp_start(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Change SNP state from "stopped" to "started".
Definition: efi_snp.c:190
static EFI_STATUS EFIAPI efi_snp_station_address(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN reset, EFI_MAC_ADDRESS *new)
Set station address.
Definition: efi_snp.c:401
static EFI_STATUS EFIAPI efi_snp_receive_filters(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINT32 enable, UINT32 disable, BOOLEAN mcast_reset, UINTN mcast_count, EFI_MAC_ADDRESS *mcast)
Manage receive filters.
Definition: efi_snp.c:367
static EFI_STATUS EFIAPI efi_snp_nvdata(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN read, UINTN offset, UINTN len, VOID *data)
Read or write non-volatile storage.
Definition: efi_snp.c:525
static EFI_STATUS EFIAPI efi_snp_receive(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN *ll_header_len, UINTN *len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
Receive packet.
Definition: efi_snp.c:761
#define EFI_SIMPLE_NETWORK_PROTOCOL_REVISION
static EFI_STATUS EFIAPI efi_snp_stop(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Change SNP state from "started" to "stopped".
Definition: efi_snp.c:214
static EFI_STATUS EFIAPI efi_snp_mcast_ip_to_mac(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN ipv6, EFI_IP_ADDRESS *ip, EFI_MAC_ADDRESS *mac)
Convert multicast IP address to MAC address.
Definition: efi_snp.c:487
static EFI_STATUS EFIAPI efi_snp_transmit(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINTN ll_header_len, UINTN len, VOID *data, EFI_MAC_ADDRESS *ll_src, EFI_MAC_ADDRESS *ll_dest, UINT16 *net_proto)
Start packet transmission.
Definition: efi_snp.c:611
static EFI_STATUS EFIAPI efi_snp_statistics(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN reset, UINTN *stats_len, EFI_NETWORK_STATISTICS *stats)
Get (or reset) statistics.
Definition: efi_snp.c:438
static EFI_STATUS EFIAPI efi_snp_shutdown(EFI_SIMPLE_NETWORK_PROTOCOL *snp)
Shut down the network device.
Definition: efi_snp.c:330
static EFI_STATUS EFIAPI efi_snp_get_status(EFI_SIMPLE_NETWORK_PROTOCOL *snp, UINT32 *interrupts, VOID **txbuf)
Read interrupt status and TX recycled buffer status.
Definition: efi_snp.c:552
static EFI_STATUS EFIAPI efi_snp_reset(EFI_SIMPLE_NETWORK_PROTOCOL *snp, BOOLEAN ext_verify)
Reset the network device.
Definition: efi_snp.c:286

SNP interface.

Definition at line 873 of file efi_snp.c.

Referenced by efi_snp_probe().

◆ efi_snp_undi

PXE_SW_UNDI efi_snp_undi
static
Initial value:
= {
.Signature = PXE_ROMID_SIGNATURE,
.Len = sizeof ( efi_snp_undi ),
.MajorVer = PXE_ROMID_MAJORVER,
.MinorVer = PXE_ROMID_MINORVER,
.Implementation = ( PXE_ROMID_IMP_SW_VIRT_ADDR |
.BusCnt = 1,
.BusType[0] = PXE_BUSTYPE ( 'i', 'P', 'X', 'E' ),
}
#define PXE_ROMID_MAJORVER
UNDI command interface revision.
Definition: UefiPxe.h:847
#define PXE_ROMID_SIGNATURE
Signature of !PXE structure.
Definition: UefiPxe.h:835
#define PXE_ROMID_IMP_PACKET_RX_INT_SUPPORTED
Definition: UefiPxe.h:873
#define PXE_ROMID_IMP_BROADCAST_RX_SUPPORTED
Definition: UefiPxe.h:869
#define PXE_BUSTYPE(a, b, c, d)
Definition: UefiPxe.h:23
static PXE_SW_UNDI efi_snp_undi
UNDI interface.
Definition: efi_snp.c:1460
#define PXE_ROMID_IMP_STATION_ADDR_SETTABLE
Definition: UefiPxe.h:866
UINT8_t Rev
PCI revision.
Definition: pxe_api.h:62
#define PXE_ROMID_MINORVER
Definition: UefiPxe.h:848
#define PXE_ROMID_IMP_SW_VIRT_ADDR
Definition: UefiPxe.h:854
#define PXE_ROMID_REV
!PXE structure format revision
Definition: UefiPxe.h:840
#define PXE_ROMID_IMP_PROMISCUOUS_RX_SUPPORTED
Definition: UefiPxe.h:868
#define PXE_ROMID_IMP_PROMISCUOUS_MULTICAST_RX_SUPPORTED
Definition: UefiPxe.h:867
#define PXE_ROMID_IMP_TX_COMPLETE_INT_SUPPORTED
Definition: UefiPxe.h:872

UNDI interface.

Must be aligned on a 16-byte boundary, for no particularly good reason.

Definition at line 1460 of file efi_snp.c.

Referenced by efi_snp_probe().

◆ efi_snp_device_nii

EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL efi_snp_device_nii
static
Initial value:
= {
.StringId = "UNDI",
.MajorVer = 3,
.MinorVer = 1,
.Ipv6Supported = TRUE,
}
#define TRUE
Definition: tlan.h:46
#define EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL_REVISION

Network Identification Interface (NII)

Definition at line 1483 of file efi_snp.c.

Referenced by efi_snp_probe().

◆ efi_vlan

EFI_VLAN_CONFIG_PROTOCOL efi_vlan
static
Initial value:
= {
.Set = efi_vlan_set,
.Find = efi_vlan_find,
.Remove = efi_vlan_remove,
}
static EFI_STATUS EFIAPI efi_vlan_remove(EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 tag)
Remove VLAN device.
Definition: efi_snp.c:1610
static EFI_STATUS EFIAPI efi_vlan_find(EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 *filter, UINT16 *count, EFI_VLAN_FIND_DATA **entries)
Find VLAN device(s)
Definition: efi_snp.c:1541
static EFI_STATUS EFIAPI efi_vlan_set(EFI_VLAN_CONFIG_PROTOCOL *vcfg, UINT16 tag, UINT8 priority)
Create or modify VLAN device.
Definition: efi_snp.c:1507

VLAN configuration protocol.

Definition at line 1644 of file efi_snp.c.

Referenced by efi_snp_probe().

◆ efi_snp_load_file_protocol

EFI_LOAD_FILE_PROTOCOL efi_snp_load_file_protocol
static
Initial value:
= {
.LoadFile = efi_snp_load_file,
}
static EFI_STATUS EFIAPI efi_snp_load_file(EFI_LOAD_FILE_PROTOCOL *load_file, EFI_DEVICE_PATH_PROTOCOL *path __unused, BOOLEAN booting, UINTN *len __unused, VOID *data __unused)
Load file.
Definition: efi_snp.c:1714

Load file protocol.

Definition at line 1750 of file efi_snp.c.

Referenced by efi_snp_probe().

◆ __net_driver

struct net_driver efi_snp_driver __net_driver
Initial value:
= {
.name = "SNP",
.probe = efi_snp_probe,
.notify = efi_snp_notify,
.remove = efi_snp_remove,
}
static void efi_snp_notify(struct net_device *netdev, void *priv __unused)
Handle SNP device or link state change.
Definition: efi_snp.c:2010
static void efi_snp_remove(struct net_device *netdev, void *priv __unused)
Destroy SNP device.
Definition: efi_snp.c:2036
static int efi_snp_probe(struct net_device *netdev, void *priv __unused)
Create SNP device.
Definition: efi_snp.c:1784

SNP driver.

Definition at line 2091 of file efi_snp.c.