49#define EIO_NETIF_RSP_ERROR \
50 __einfo_error ( EINFO_EIO_NETIF_RSP_ERROR )
51#define EINFO_EIO_NETIF_RSP_ERROR \
52 __einfo_uniqify ( EINFO_EIO, -NETIF_RSP_ERROR, \
53 "Unspecified network error" )
54#define EIO_NETIF_RSP_DROPPED \
55 __einfo_error ( EINFO_EIO_NETIF_RSP_DROPPED )
56#define EINFO_EIO_NETIF_RSP_DROPPED \
57 __einfo_uniqify ( EINFO_EIO, -NETIF_RSP_DROPPED, \
59#define EIO_NETIF_RSP( status ) \
60 EUNIQ ( EINFO_EIO, ( -(status) & 0x1f ), \
61 EIO_NETIF_RSP_ERROR, EIO_NETIF_RSP_DROPPED )
87 DBGC ( netfront,
"NETFRONT %s could not read backend state: "
103 DBGC ( netfront,
"NETFRONT %s backend did not reach "
114 DBGC ( netfront,
"NETFRONT %s backend did not reach InitWait: "
138 DBGC ( netfront,
"NETFRONT %s could not read MAC address: %s\n",
140 goto err_xenstore_read;
142 DBGC2 ( netfront,
"NETFRONT %s has MAC address \"%s\"\n",
149 DBGC ( netfront,
"NETFRONT %s could not decode MAC address "
172 const char *subkey,
unsigned long num ) {
180 DBGC ( netfront,
"NETFRONT %s could not set %s=\"%ld\": %s\n",
197 const char *subkey ) {
216 DBGC ( netfront,
"NETFRONT %s could not delete %s: %s\n",
248 if ( ( xenrc = xenevent_alloc_unbound ( xen, &
alloc_unbound ) ) != 0 ) {
250 DBGC ( netfront,
"NETFRONT %s could not allocate event: %s\n",
252 goto err_alloc_unbound;
261 DBGC ( netfront,
"NETFRONT %s event-channel=\"%d\"\n",
268 xenevent_close ( xen, &
close );
287 if ( ( xenrc = xenevent_send ( xen, &netfront->
event ) ) != 0 ) {
289 DBGC ( netfront,
"NETFRONT %s could not send event: %s\n",
312 xenevent_close ( xen, &
close );
338 for ( i = 0 ; i < ring->
count ; i++ ) {
354 if ( (
rc = xengrant_permit_access ( xen, ring->
ref, xendev->
backend_id,
356 DBGC ( netfront,
"NETFRONT %s could not permit access to "
358 goto err_permit_access;
366 DBGC ( netfront,
"NETFRONT %s %s=\"%d\" [%08lx,%08lx)\n", xendev->
key,
372 xengrant_invalidate ( xen, ring->
ref );
399 unsigned int next_id;
400 unsigned int next_ref;
404 assert ( ! netfront_ring_is_full ( ring ) );
408 next_ref = ring->
refs[next_id];
411 if ( (
rc = xengrant_permit_access ( xen, next_ref, xendev->
backend_id,
413 DBGC ( netfront,
"NETFRONT %s could not permit access to "
420 ring->
iobufs[next_id] = iobuf;
451 xengrant_invalidate ( xen, ring->
refs[
id] );
472 void ( * discard ) (
struct io_buffer * ) ){
479 while ( ! netfront_ring_is_empty ( ring ) ) {
490 xengrant_invalidate ( xen, ring->
ref );
530 unsigned int refilled = 0;
544 addr = virt_to_phys ( iobuf->
data );
555 DBGC2 ( netfront,
"NETFRONT %s RX id %d ref %d is %#08lx+%zx\n",
604 goto err_create_event;
611 goto err_request_rx_copy;
619 "feature-no-csum-offload" ) ) != 0 )
620 goto err_feature_no_csum_offload;
624 "feature-rx-notify" ) ) != 0 )
625 goto err_feature_rx_notify;
629 DBGC ( netfront,
"NETFRONT %s could not set state=\"%d\": %s\n",
636 DBGC ( netfront,
"NETFRONT %s could not connect to backend: "
638 goto err_backend_wait;
653 err_feature_rx_notify:
654 netfront_rm ( netfront,
"feature-no-csum-offload" );
655 err_feature_no_csum_offload:
684 DBGC ( netfront,
"NETFRONT %s could not disconnect from "
700 netfront_rm ( netfront,
"feature-no-csum-offload" );
744 addr = virt_to_phys ( iobuf->
data );
750 if ( netfront_ring_space ( &netfront->
tx ) <
count ) {
751 DBGC ( netfront,
"NETFRONT %s out of transmit descriptors\n",
758 while ( remaining ) {
762 if ( frag_len >= remaining ) {
763 frag_len = remaining;
773 ( more ?
NULL : iobuf ),
781 DBGC2 ( netfront,
"NETFRONT %s TX id %d ref %d is "
783 request->gref,
addr, frag_len, ( more ?
"..." :
"" ) );
788 remaining -= frag_len;
824 DBGC2 ( netfront,
"NETFRONT %s TX id %d complete\n",
825 xendev->
key, response->
id );
830 DBGC2 ( netfront,
"NETFRONT %s TX id %d error %d: %s\n",
868 DBGC2 ( netfront,
"NETFRONT %s RX id %d error %d: %s\n",
880 DBGC2 ( netfront,
"NETFRONT %s RX id %d complete "
881 "%#08lx+%zx%s\n", xendev->
key, response->
id,
882 virt_to_phys ( iobuf->
data ),
len,
883 ( more ?
"..." :
"" ) );
893 DBGC2 ( netfront,
"NETFRONT %s RX reassembly failed\n",
961 DBGC ( netfront,
"NETFRONT %s backend=\"%s\" in domain %ld\n",
967 DBGC ( netfront,
"NETFRONT %s could not allocate grant "
969 goto err_grant_alloc;
971 netfront_init_ring ( &netfront->
tx,
"tx-ring-ref",
976 netfront_init_ring ( &netfront->
rx,
"rx-ring-ref",
994 goto err_register_netdev;
1007 err_register_netdev:
1050XEN_ROM (
"netfront",
"Xen netfront virtual NIC" );
1076 DBGC ( netfront,
"NETFRONT %s inhibiting emulated %s "
#define NULL
NULL pointer (VOID *)
struct arbelprm_rc_send_wqe rc
#define assert(condition)
Assert a condition at run-time.
int hex_decode(char separator, const char *encoded, void *data, size_t len)
Decode hexadecimal string (with optional byte separator character)
uint16_t offset
Offset to command line.
uint32_t addr
Buffer address.
uint8_t id
Request identifier.
uint8_t mac[ETH_ALEN]
MAC address.
struct net_device * alloc_etherdev(size_t priv_size)
Allocate Ethernet device.
static struct net_device * netdev
#define __unused
Declare a variable or data structure as unused.
static unsigned int count
Number of entries.
#define FILE_LICENCE(_licence)
Declare a particular licence as applying to a file.
#define EEXIST
File exists.
#define ENOMEM
Not enough space.
#define ENOBUFS
No buffer space available.
#define FILE_SECBOOT(_status)
Declare a file's UEFI Secure Boot permission status.
u8 request[0]
List of IEs requested.
#define PAGE_SIZE
Page size.
#define EXEN(xenrc)
Convert a Xen status code to an iPXE status code.
void free_iob(struct io_buffer *iobuf)
Free I/O buffer.
struct io_buffer * iob_concatenate(struct list_head *list)
Concatenate I/O buffers into a single buffer.
struct io_buffer * alloc_iob(size_t len)
Allocate I/O buffer.
#define iob_put(iobuf, len)
static size_t iob_len(struct io_buffer *iobuf)
Calculate length of data in an I/O buffer.
#define iob_reserve(iobuf, len)
static size_t iob_tailroom(struct io_buffer *iobuf)
Calculate available space at end of an I/O buffer.
static void * xen_get_drvdata(struct xen_device *xendev)
Get Xen device driver-private data.
#define XEN_ROM(_name, _desc)
Define build rules for a Xen device driver.
static void xen_set_drvdata(struct xen_device *xendev, void *priv)
Set Xen device driver-private data.
#define __xen_driver
Declare a Xen device driver.
#define list_for_each_entry_safe(pos, tmp, head, member)
Iterate over entries in a list, safe against deletion of the current entry.
#define list_add_tail(new, head)
Add a new entry to the tail of a list.
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
#define list_del(list)
Delete an entry from a list.
#define INIT_LIST_HEAD(list)
Initialise a list head.
#define LIST_HEAD(list)
Declare a static list head.
void * malloc_phys(size_t size, size_t phys_align)
Allocate memory with specified physical alignment.
void free_phys(void *ptr, size_t size)
Free memory allocated with malloc_phys()
Dynamic memory allocation.
void netdev_link_err(struct net_device *netdev, int rc)
Mark network device as having a specific link state.
void netdev_link_down(struct net_device *netdev)
Mark network device as having link down.
void netdev_rx(struct net_device *netdev, struct io_buffer *iobuf)
Add packet to receive queue.
void unregister_netdev(struct net_device *netdev)
Unregister network device.
void netdev_tx_complete_err(struct net_device *netdev, struct io_buffer *iobuf, int rc)
Complete network transmission.
void netdev_rx_err(struct net_device *netdev, struct io_buffer *iobuf, int rc)
Discard received packet.
int register_netdev(struct net_device *netdev)
Register network device.
Network device management.
static void netdev_link_up(struct net_device *netdev)
Mark network device as having link up.
static void netdev_init(struct net_device *netdev, struct net_device_operations *op)
Initialise a network device.
static void netdev_nullify(struct net_device *netdev)
Stop using a network device.
static void netdev_put(struct net_device *netdev)
Drop reference to network device.
#define __net_driver
Declare a network driver.
static void netdev_tx_complete(struct net_device *netdev, struct io_buffer *iobuf)
Complete network transmission.
static int netfront_transmit(struct net_device *netdev, struct io_buffer *iobuf)
Transmit packet.
static void netfront_refill_rx(struct net_device *netdev)
Refill receive descriptor ring.
static void netfront_destroy_event(struct netfront_nic *netfront)
Destroy event channel.
static struct net_device_operations netfront_operations
Network device operations.
static int netfront_net_probe(struct net_device *netdev, void *priv __unused)
Inhibit emulated PCI devices.
static int netfront_create_ring(struct netfront_nic *netfront, struct netfront_ring *ring)
Create descriptor ring.
static int netfront_write_num(struct netfront_nic *netfront, const char *subkey, unsigned long num)
Write XenStore numeric value.
static void netfront_poll(struct net_device *netdev)
Poll for completed and received packets.
static int netfront_reset(struct netfront_nic *netfront)
Reset device.
static int netfront_rm(struct netfront_nic *netfront, const char *subkey)
Delete XenStore value.
static void netfront_poll_rx(struct net_device *netdev)
Poll for received packets.
static struct io_buffer * netfront_pull(struct netfront_nic *netfront, struct netfront_ring *ring, unsigned int id)
Remove buffer from descriptor ring.
static int netfront_push(struct netfront_nic *netfront, struct netfront_ring *ring, physaddr_t addr, struct io_buffer *iobuf, uint16_t *id, grant_ref_t *ref)
Add buffer to descriptor ring.
static int netfront_open(struct net_device *netdev)
Open network device.
static void netfront_discard(struct netfront_nic *netfront)
Discard partially received I/O buffers.
static int netfront_read_mac(struct netfront_nic *netfront, void *hw_addr)
Fetch MAC address.
static int netfront_probe(struct xen_device *xendev)
Probe Xen device.
static int netfront_send_event(struct netfront_nic *netfront)
Send event.
static void netfront_destroy_ring(struct netfront_nic *netfront, struct netfront_ring *ring, void(*discard)(struct io_buffer *))
Destroy descriptor ring.
static void netfront_remove(struct xen_device *xendev)
Remove Xen device.
static int netfront_write_flag(struct netfront_nic *netfront, const char *subkey)
Write XenStore flag value.
static void netfront_poll_tx(struct net_device *netdev)
Poll for completed packets.
static int netfront_create_event(struct netfront_nic *netfront)
Create event channel.
#define EIO_NETIF_RSP(status)
static void netfront_close(struct net_device *netdev)
Close network device.
static const char grant_ref_t ref
#define NETFRONT_RX_FILL
Receive ring fill level.
#define NETFRONT_NUM_RX_DESC
Number of receive ring entries.
@ NETFRONT_REF_TX_RING
Transmit ring grant reference index.
@ NETFRONT_REF_COUNT
Total number of grant references required.
@ NETFRONT_REF_TX_BASE
Transmit descriptor grant reference base index.
@ NETFRONT_REF_RX_RING
Receive ring grant reference index.
@ NETFRONT_REF_RX_BASE
Receive descriptor grant reference base index.
#define NETFRONT_NUM_TX_DESC
Number of transmit ring entries.
#define NETTXF_data_validated
static void(* free)(struct refcnt *refcnt))
#define RING_PUSH_REQUESTS_AND_CHECK_NOTIFY(_r, _notify)
#define SHARED_RING_INIT(_s)
#define RING_GET_REQUEST(_r, _idx)
#define RING_GET_RESPONSE(_r, _idx)
#define FRONT_RING_INIT(_r, _s, __size)
#define RING_HAS_UNCONSUMED_RESPONSES(_r)
char * strerror(int errno)
Retrieve string representation of error number.
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
void * data
Start of data.
struct list_head list
List of which this buffer is a member.
Network device operations.
uint8_t hw_addr[MAX_HW_ADDR_LEN]
Hardware address.
struct device * dev
Underlying hardware device.
A network upper-layer driver.
grant_ref_t refs[NETFRONT_REF_COUNT]
Grant references.
uint8_t rx_ids[NETFRONT_NUM_RX_DESC]
Receive I/O buffer IDs.
struct io_buffer * tx_iobufs[NETFRONT_NUM_TX_DESC]
Transmit I/O buffers.
netif_tx_front_ring_t tx_fring
Transmit front ring.
struct xen_device * xendev
Xen device.
struct list_head rx_partial
Partial receive I/O buffer list.
struct net_device * netdev
Network device.
struct io_buffer * rx_iobufs[NETFRONT_NUM_RX_DESC]
Receive I/O buffers.
struct evtchn_send event
Event channel.
struct netfront_ring rx
Receive ring.
netif_rx_front_ring_t rx_fring
Receive front ring.
uint8_t tx_ids[NETFRONT_NUM_TX_DESC]
Transmit I/O buffer IDs.
struct list_head list
List of netfront NICs.
struct netfront_ring tx
Transmit ring.
A netfront descriptor ring.
grant_ref_t * refs
Grant references, indexed by buffer ID.
size_t count
Maximum number of used descriptors.
uint8_t * ids
Buffer ID ring.
struct io_buffer ** iobufs
I/O buffers, indexed by buffer ID.
unsigned int id_prod
Buffer ID ring producer counter.
const char * ref_key
Shared ring grant reference key.
unsigned int id_cons
Buffer ID ring consumer counter.
grant_ref_t ref
Shared ring grant reference.
union netfront_ring::@235351263275146342264217234007371176021305365026 sring
Shared ring.
unsigned long backend_id
Backend domain ID.
struct device dev
Generic iPXE device.
struct xen_hypervisor * xen
Xen hypervisor.
char * backend
Backend XenStore key.
static struct tlan_private * priv
@ XenbusStateInitialising
int xenbus_backend_state(struct xen_device *xendev)
Get backend state.
int xenbus_set_state(struct xen_device *xendev, int state)
Set device state.
int xenbus_backend_wait(struct xen_device *xendev, int state)
Wait for backend to reach a given state.
static struct evtchn_close * close
static struct evtchn_alloc_unbound * alloc_unbound
int xengrant_alloc(struct xen_hypervisor *xen, grant_ref_t *refs, unsigned int count)
Allocate grant references.
void xengrant_free(struct xen_hypervisor *xen, grant_ref_t *refs, unsigned int count)
Free grant references.
int xenstore_rm(struct xen_hypervisor *xen,...)
Delete XenStore value.
int xenstore_read(struct xen_hypervisor *xen, char **value,...)
Read XenStore value.
int xenstore_write_num(struct xen_hypervisor *xen, unsigned long num,...)
Write XenStore numeric value.