iPXE
Data Structures | Functions | Variables
pnic.c File Reference
#include <stdint.h>
#include <stdio.h>
#include <ipxe/io.h>
#include <errno.h>
#include <ipxe/pci.h>
#include <ipxe/if_ether.h>
#include <ipxe/ethernet.h>
#include <ipxe/iobuf.h>
#include <ipxe/netdevice.h>
#include "pnic_api.h"

Go to the source code of this file.

Data Structures

struct  pnic
 

Functions

 FILE_LICENCE (GPL2_OR_LATER)
 
static uint16_t pnic_command_quiet (struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
 
static uint16_t pnic_command (struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
 
static int pnic_api_check (uint16_t api_version)
 
static void pnic_poll (struct net_device *netdev)
 
static int pnic_transmit (struct net_device *netdev, struct io_buffer *iobuf)
 
static int pnic_open (struct net_device *netdev __unused)
 
static void pnic_close (struct net_device *netdev __unused)
 
static void pnic_irq (struct net_device *netdev, int enable)
 
static void pnic_remove (struct pci_device *pci)
 
static int pnic_probe (struct pci_device *pci)
 

Variables

static struct net_device_operations pnic_operations
 
static struct pci_device_id pnic_nics []
 
struct pci_driver pnic_driver __pci_driver
 

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( GPL2_OR_LATER  )

◆ pnic_command_quiet()

static uint16_t pnic_command_quiet ( struct pnic pnic,
uint16_t  command,
const void *  input,
uint16_t  input_length,
void *  output,
uint16_t  output_max_length,
uint16_t output_length 
)
static

Definition at line 55 of file pnic.c.

58  {
60  uint16_t _output_length;
61 
62  if ( input != NULL ) {
63  /* Write input length */
64  outw ( input_length, pnic->ioaddr + PNIC_REG_LEN );
65  /* Write input data */
66  outsb ( pnic->ioaddr + PNIC_REG_DATA, input, input_length );
67  }
68  /* Write command */
70  /* Retrieve status */
72  /* Retrieve output length */
73  _output_length = inw ( pnic->ioaddr + PNIC_REG_LEN );
74  if ( output_length == NULL ) {
75  if ( _output_length != output_max_length ) {
76  printf ( "pnic_command %#hx: wrong data length "
77  "returned (expected %d, got %d)\n", command,
78  output_max_length, _output_length );
79  }
80  } else {
81  *output_length = _output_length;
82  }
83  if ( output != NULL ) {
84  if ( _output_length > output_max_length ) {
85  printf ( "pnic_command %#hx: output buffer too small "
86  "(have %d, need %d)\n", command,
87  output_max_length, _output_length );
88  _output_length = output_max_length;
89  }
90  /* Retrieve output data */
91  insb ( pnic->ioaddr + PNIC_REG_DATA, output, _output_length );
92  }
93  return status;
94 }
unsigned short uint16_t
Definition: stdint.h:11
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition: vsprintf.c:464
uint16_t inw(volatile uint16_t *io_addr)
Read 16-bit word from I/O-mapped device.
#define outw(data, io_addr)
Definition: io.h:319
Definition: pnic.c:39
A command-line command.
Definition: command.h:9
void insb(volatile uint8_t *io_addr, uint8_t *data, unsigned int count)
Read bytes from I/O-mapped device.
unsigned short ioaddr
Definition: pnic.c:40
uint8_t status
Status.
Definition: ena.h:16
#define PNIC_REG_STAT
Definition: pnic_api.h:27
void outsb(volatile uint8_t *io_addr, const uint8_t *data, unsigned int count)
Write bytes to I/O-mapped device.
#define PNIC_REG_DATA
Definition: pnic_api.h:29
#define PNIC_REG_LEN
Definition: pnic_api.h:28
#define PNIC_REG_CMD
Definition: pnic_api.h:26
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References insb(), inw(), pnic::ioaddr, NULL, outsb(), outw, PNIC_REG_CMD, PNIC_REG_DATA, PNIC_REG_LEN, PNIC_REG_STAT, printf(), and status.

Referenced by pnic_command(), and pnic_probe().

◆ pnic_command()

static uint16_t pnic_command ( struct pnic pnic,
uint16_t  command,
const void *  input,
uint16_t  input_length,
void *  output,
uint16_t  output_max_length,
uint16_t output_length 
)
static

Definition at line 96 of file pnic.c.

99  {
101  input, input_length,
102  output, output_max_length,
103  output_length );
104  if ( status == PNIC_STATUS_OK ) return status;
105  printf ( "PNIC command %#hx (len %#hx) failed with status %#hx\n",
106  command, input_length, status );
107  return status;
108 }
unsigned short uint16_t
Definition: stdint.h:11
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition: vsprintf.c:464
Definition: pnic.c:39
A command-line command.
Definition: command.h:9
static uint16_t pnic_command_quiet(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:55
uint8_t status
Status.
Definition: ena.h:16
#define PNIC_STATUS_OK
Definition: pnic_api.h:54

References pnic_command_quiet(), PNIC_STATUS_OK, printf(), and status.

Referenced by pnic_irq(), pnic_poll(), pnic_probe(), pnic_remove(), and pnic_transmit().

◆ pnic_api_check()

static int pnic_api_check ( uint16_t  api_version)
static

Definition at line 111 of file pnic.c.

111  {
112  if ( api_version != PNIC_API_VERSION ) {
113  printf ( "Warning: API version mismatch! "
114  "(NIC's is %d.%d, ours is %d.%d)\n",
115  api_version >> 8, api_version & 0xff,
116  PNIC_API_VERSION >> 8, PNIC_API_VERSION & 0xff );
117  }
118  if ( api_version < PNIC_API_VERSION ) {
119  printf ( "** You may need to update your copy of Bochs **\n" );
120  }
121  return ( api_version == PNIC_API_VERSION );
122 }
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition: vsprintf.c:464
#define PNIC_API_VERSION
Definition: pnic_api.h:61

References PNIC_API_VERSION, and printf().

Referenced by pnic_probe().

◆ pnic_poll()

static void pnic_poll ( struct net_device netdev)
static

Definition at line 127 of file pnic.c.

127  {
128  struct pnic *pnic = netdev->priv;
129  struct io_buffer *iobuf;
131  uint16_t qlen;
132 
133  /* Fetch all available packets */
134  while ( 1 ) {
136  &qlen, sizeof ( qlen ), NULL )
137  != PNIC_STATUS_OK )
138  return;
139  if ( qlen == 0 )
140  return;
141  iobuf = alloc_iob ( ETH_FRAME_LEN );
142  if ( ! iobuf ) {
143  DBG ( "could not allocate buffer\n" );
145  return;
146  }
147  if ( pnic_command ( pnic, PNIC_CMD_RECV, NULL, 0,
148  iobuf->data, ETH_FRAME_LEN, &length )
149  != PNIC_STATUS_OK ) {
150  netdev_rx_err ( netdev, iobuf, -EIO );
151  return;
152  }
153  iob_put ( iobuf, length );
154  netdev_rx ( netdev, iobuf );
155  }
156 }
uint16_t length
Length.
Definition: intel.h:14
unsigned short uint16_t
Definition: stdint.h:11
#define iob_put(iobuf, len)
Definition: iobuf.h:116
void netdev_rx_err(struct net_device *netdev, struct io_buffer *iobuf, int rc)
Discard received packet.
Definition: netdevice.c:501
Definition: pnic.c:39
struct io_buffer * alloc_iob(size_t len)
Allocate I/O buffer.
Definition: iobuf.c:128
#define ENOMEM
Not enough space.
Definition: errno.h:534
#define ETH_FRAME_LEN
Definition: if_ether.h:11
void * priv
Driver private data.
Definition: netdevice.h:425
#define PNIC_STATUS_OK
Definition: pnic_api.h:54
#define PNIC_CMD_RECV
Definition: pnic_api.h:43
static struct net_device * netdev
Definition: gdbudp.c:52
#define PNIC_CMD_RECV_QLEN
Definition: pnic_api.h:44
void netdev_rx(struct net_device *netdev, struct io_buffer *iobuf)
Add packet to receive queue.
Definition: netdevice.c:470
void * data
Start of data.
Definition: iobuf.h:44
#define EIO
Input/output error.
Definition: errno.h:433
static uint16_t pnic_command(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:96
#define DBG(...)
Print a debugging message.
Definition: compiler.h:498
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
A persistent I/O buffer.
Definition: iobuf.h:32

References alloc_iob(), io_buffer::data, DBG, EIO, ENOMEM, ETH_FRAME_LEN, iob_put, length, netdev, netdev_rx(), netdev_rx_err(), NULL, PNIC_CMD_RECV, PNIC_CMD_RECV_QLEN, pnic_command(), PNIC_STATUS_OK, and net_device::priv.

◆ pnic_transmit()

static int pnic_transmit ( struct net_device netdev,
struct io_buffer iobuf 
)
static

Definition at line 161 of file pnic.c.

161  {
162  struct pnic *pnic = netdev->priv;
163 
164  /* Pad the packet */
165  iob_pad ( iobuf, ETH_ZLEN );
166 
167  /* Send packet */
168  pnic_command ( pnic, PNIC_CMD_XMIT, iobuf->data, iob_len ( iobuf ),
169  NULL, 0, NULL );
170 
171  netdev_tx_complete ( netdev, iobuf );
172  return 0;
173 }
static void netdev_tx_complete(struct net_device *netdev, struct io_buffer *iobuf)
Complete network transmission.
Definition: netdevice.h:746
Definition: pnic.c:39
void * priv
Driver private data.
Definition: netdevice.h:425
static struct net_device * netdev
Definition: gdbudp.c:52
#define PNIC_CMD_XMIT
Definition: pnic_api.h:42
static size_t iob_len(struct io_buffer *iobuf)
Calculate length of data in an I/O buffer.
Definition: iobuf.h:151
#define ETH_ZLEN
Definition: if_ether.h:10
void * data
Start of data.
Definition: iobuf.h:44
static uint16_t pnic_command(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:96
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
void iob_pad(struct io_buffer *iobuf, size_t min_len)
Pad I/O buffer.
Definition: iobpad.c:49

References io_buffer::data, ETH_ZLEN, iob_len(), iob_pad(), netdev, netdev_tx_complete(), NULL, PNIC_CMD_XMIT, pnic_command(), and net_device::priv.

◆ pnic_open()

static int pnic_open ( struct net_device *netdev  __unused)
static

Definition at line 178 of file pnic.c.

178  {
179  /* Nothing to do */
180  return 0;
181 }

◆ pnic_close()

static void pnic_close ( struct net_device *netdev  __unused)
static

Definition at line 186 of file pnic.c.

186  {
187  /* Nothing to do */
188 }

◆ pnic_irq()

static void pnic_irq ( struct net_device netdev,
int  enable 
)
static

Definition at line 193 of file pnic.c.

193  {
194  struct pnic *pnic = netdev->priv;
195  uint8_t mask = ( enable ? 1 : 0 );
196 
197  pnic_command ( pnic, PNIC_CMD_MASK_IRQ, &mask, sizeof ( mask ),
198  NULL, 0, NULL );
199 }
#define PNIC_CMD_MASK_IRQ
Definition: pnic_api.h:45
Definition: pnic.c:39
void * priv
Driver private data.
Definition: netdevice.h:425
static struct net_device * netdev
Definition: gdbudp.c:52
unsigned char uint8_t
Definition: stdint.h:10
static uint16_t pnic_command(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:96
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References netdev, NULL, PNIC_CMD_MASK_IRQ, pnic_command(), and net_device::priv.

◆ pnic_remove()

static void pnic_remove ( struct pci_device pci)
static

Definition at line 215 of file pnic.c.

215  {
216  struct net_device *netdev = pci_get_drvdata ( pci );
217  struct pnic *pnic = netdev->priv;
218 
222  netdev_put ( netdev );
223 }
Definition: pnic.c:39
static void netdev_put(struct net_device *netdev)
Drop reference to network device.
Definition: netdevice.h:555
void * priv
Driver private data.
Definition: netdevice.h:425
static struct net_device * netdev
Definition: gdbudp.c:52
#define PNIC_CMD_RESET
Definition: pnic_api.h:41
void unregister_netdev(struct net_device *netdev)
Unregister network device.
Definition: netdevice.c:844
A network device.
Definition: netdevice.h:348
static void netdev_nullify(struct net_device *netdev)
Stop using a network device.
Definition: netdevice.h:511
static void * pci_get_drvdata(struct pci_device *pci)
Get PCI driver-private data.
Definition: pci.h:348
static uint16_t pnic_command(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:96
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References netdev, netdev_nullify(), netdev_put(), NULL, pci_get_drvdata(), PNIC_CMD_RESET, pnic_command(), net_device::priv, and unregister_netdev().

◆ pnic_probe()

static int pnic_probe ( struct pci_device pci)
static

Definition at line 228 of file pnic.c.

228  {
229  struct net_device *netdev;
230  struct pnic *pnic;
231  uint16_t api_version;
233  int rc;
234 
235  /* Allocate net device */
236  netdev = alloc_etherdev ( sizeof ( *pnic ) );
237  if ( ! netdev )
238  return -ENOMEM;
240  pnic = netdev->priv;
241  pci_set_drvdata ( pci, netdev );
242  netdev->dev = &pci->dev;
243  pnic->ioaddr = pci->ioaddr;
244 
245  /* Fix up PCI device */
246  adjust_pci_device ( pci );
247 
248  /* API version check */
250  &api_version,
251  sizeof ( api_version ), NULL );
252  if ( status != PNIC_STATUS_OK ) {
253  printf ( "PNIC failed installation check, code %#hx\n",
254  status );
255  rc = -EIO;
256  goto err;
257  }
258  pnic_api_check ( api_version );
259 
260  /* Get MAC address */
263 
264  /* Register network device */
265  if ( ( rc = register_netdev ( netdev ) ) != 0 )
266  goto err;
267 
268  /* Mark as link up; PNIC has no concept of link state */
270 
271  return 0;
272 
273  err:
274  /* Free net device */
276  netdev_put ( netdev );
277  return rc;
278 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
unsigned short uint16_t
Definition: stdint.h:11
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition: vsprintf.c:464
Definition: pnic.c:39
unsigned long ioaddr
I/O address.
Definition: pci.h:200
#define PNIC_CMD_READ_MAC
Definition: pnic_api.h:40
static uint16_t pnic_command_quiet(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:55
unsigned short ioaddr
Definition: pnic.c:40
void adjust_pci_device(struct pci_device *pci)
Enable PCI device.
Definition: pci.c:149
struct device dev
Generic device.
Definition: pci.h:189
uint8_t status
Status.
Definition: ena.h:16
static void netdev_init(struct net_device *netdev, struct net_device_operations *op)
Initialise a network device.
Definition: netdevice.h:498
static void pci_set_drvdata(struct pci_device *pci, void *priv)
Set PCI driver-private data.
Definition: pci.h:338
#define ENOMEM
Not enough space.
Definition: errno.h:534
static void netdev_put(struct net_device *netdev)
Drop reference to network device.
Definition: netdevice.h:555
void * priv
Driver private data.
Definition: netdevice.h:425
static void netdev_link_up(struct net_device *netdev)
Mark network device as having link up.
Definition: netdevice.h:768
#define PNIC_STATUS_OK
Definition: pnic_api.h:54
static struct net_device * netdev
Definition: gdbudp.c:52
int register_netdev(struct net_device *netdev)
Register network device.
Definition: netdevice.c:667
A network device.
Definition: netdevice.h:348
static void netdev_nullify(struct net_device *netdev)
Stop using a network device.
Definition: netdevice.h:511
#define ETH_ALEN
Definition: if_ether.h:8
struct device * dev
Underlying hardware device.
Definition: netdevice.h:360
static int pnic_api_check(uint16_t api_version)
Definition: pnic.c:111
#define EIO
Input/output error.
Definition: errno.h:433
struct net_device * alloc_etherdev(size_t priv_size)
Allocate Ethernet device.
Definition: ethernet.c:264
static uint16_t pnic_command(struct pnic *pnic, uint16_t command, const void *input, uint16_t input_length, void *output, uint16_t output_max_length, uint16_t *output_length)
Definition: pnic.c:96
#define PNIC_CMD_API_VER
Definition: pnic_api.h:39
static struct net_device_operations pnic_operations
Definition: pnic.c:204
uint8_t hw_addr[MAX_HW_ADDR_LEN]
Hardware address.
Definition: netdevice.h:375
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References adjust_pci_device(), alloc_etherdev(), pci_device::dev, net_device::dev, EIO, ENOMEM, ETH_ALEN, net_device::hw_addr, pnic::ioaddr, pci_device::ioaddr, netdev, netdev_init(), netdev_link_up(), netdev_nullify(), netdev_put(), NULL, pci_set_drvdata(), pnic_api_check(), PNIC_CMD_API_VER, PNIC_CMD_READ_MAC, pnic_command(), pnic_command_quiet(), pnic_operations, PNIC_STATUS_OK, printf(), net_device::priv, rc, register_netdev(), and status.

Variable Documentation

◆ pnic_operations

struct net_device_operations pnic_operations
static
Initial value:
= {
.open = pnic_open,
.close = pnic_close,
.transmit = pnic_transmit,
.poll = pnic_poll,
.irq = pnic_irq,
}
static void pnic_poll(struct net_device *netdev)
Definition: pnic.c:127
static int pnic_transmit(struct net_device *netdev, struct io_buffer *iobuf)
Definition: pnic.c:161
static void pnic_close(struct net_device *netdev __unused)
Definition: pnic.c:186
static void pnic_irq(struct net_device *netdev, int enable)
Definition: pnic.c:193
static int pnic_open(struct net_device *netdev __unused)
Definition: pnic.c:178

Definition at line 204 of file pnic.c.

Referenced by pnic_probe().

◆ pnic_nics

struct pci_device_id pnic_nics[]
static
Initial value:
= {
PCI_ROM ( 0xfefe, 0xefef, "pnic", "Bochs Pseudo NIC Adaptor", 0 ),
}
#define PCI_ROM(_vendor, _device, _name, _description, _data)
Definition: pci.h:283

Definition at line 280 of file pnic.c.

◆ __pci_driver

struct pci_driver pnic_driver __pci_driver
Initial value:
= {
.ids = pnic_nics,
.id_count = ( sizeof ( pnic_nics ) / sizeof ( pnic_nics[0] ) ),
.probe = pnic_probe,
}
static void pnic_remove(struct pci_device *pci)
Definition: pnic.c:215
static struct pci_device_id pnic_nics[]
Definition: pnic.c:280
static struct xen_remove_from_physmap * remove
Definition: xenmem.h:39
static int pnic_probe(struct pci_device *pci)
Definition: pnic.c:228

Definition at line 285 of file pnic.c.