include: import Xen public headers to hw/xen/interface

There's already a partial set here; update them and pull in a more
complete set.

To start with, define __XEN_TOOLS__ in hw/xen/xen.h to ensure that any
internal definitions needed by Xen toolstack libraries are present
regardless of the order in which the headers are included. A reckoning
will come later, once we make the PV backends work in emulation and
untangle the headers for Xen-native vs. generic parts.

Signed-off-by: Joao Martins <joao.m.martins@oracle.com>
[dwmw2: Update to Xen public headers from 4.16.2 release, add some in io/,
        define __XEN_TOOLS__ in hw/xen/xen.h, move to hw/xen/interface/]
Signed-off-by: David Woodhouse <dwmw@amazon.co.uk>
Reviewed-by: Paul Durrant <paul@xen.org>
This commit is contained in:
Joao Martins 2019-02-13 12:29:47 -05:00 committed by David Woodhouse
parent 6276340310
commit 50c88402ca
28 changed files with 7134 additions and 136 deletions

View file

@ -118,7 +118,7 @@
*
* The underlying storage is not affected by the direct IO memory
* lifetime bug. See:
* http://lists.xen.org/archives/html/xen-devel/2012-12/msg01154.html
* https://lists.xen.org/archives/html/xen-devel/2012-12/msg01154.html
*
* Therefore this option gives the backend permission to use
* O_DIRECT, notwithstanding that bug.
@ -341,7 +341,7 @@
* access (even when it should be read-only). If the frontend hits the
* maximum number of allowed persistently mapped grants, it can fallback
* to non persistent mode. This will cause a performance degradation,
* since the backend driver will still try to map those grants
* since the the backend driver will still try to map those grants
* persistently. Since the persistent grants protocol is compatible with
* the previous protocol, a frontend driver can choose to work in
* persistent mode even when the backend doesn't support it.
@ -710,3 +710,13 @@ DEFINE_RING_TYPES(blkif, struct blkif_request, struct blkif_response);
#define VDISK_READONLY 0x4
#endif /* __XEN_PUBLIC_IO_BLKIF_H__ */
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -44,3 +44,13 @@ DEFINE_XEN_FLEX_RING(xencons);
#endif
#endif /* __XEN_PUBLIC_IO_CONSOLE_H__ */
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -153,4 +153,24 @@ struct xenfb_page
unsigned long pd[256];
};
/*
* Wart: xenkbd needs to know default resolution. Put it here until a
* better solution is found, but don't leak it to the backend.
*/
#ifdef __KERNEL__
#define XENFB_WIDTH 800
#define XENFB_HEIGHT 600
#define XENFB_DEPTH 32
#endif
#endif
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -564,3 +564,13 @@ struct xenkbd_page
};
#endif /* __XEN_PUBLIC_IO_KBDIF_H__ */
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -171,7 +171,7 @@
* The ability of the backend to use a control ring is advertised by
* setting:
*
* /local/domain/X/backend/<domid>/<vif>/feature-ctrl-ring = "1"
* /local/domain/X/backend/vif/<domid>/<vif>/feature-ctrl-ring = "1"
*
* The frontend provides a control ring to the backend by setting:
*
@ -190,6 +190,32 @@
* order as requests.
*/
/*
* Link state
* ==========
*
* The backend can advertise its current link (carrier) state to the
* frontend using the /local/domain/X/backend/vif/<domid>/<vif>/carrier
* node. If this node is not present, then the frontend should assume that
* the link is up (for compatibility with backends that do not implement
* this feature). If this node is present, then a value of "0" should be
* interpreted by the frontend as the link being down (no carrier) and a
* value of "1" should be interpreted as the link being up (carrier
* present).
*/
/*
* MTU
* ===
*
* The toolstack may set a value of MTU for the frontend by setting the
* /local/domain/<domid>/device/vif/<vif>/mtu node with the MTU value in
* octets. If this node is absent the frontend should assume an MTU value
* of 1500 octets. A frontend is also at liberty to ignore this value so
* it is only suitable for informing the frontend that a packet payload
* >1500 octets is permitted.
*/
/*
* Hash types
* ==========
@ -267,6 +293,62 @@
#define XEN_NETIF_CTRL_HASH_ALGORITHM_TOEPLITZ 1
/*
* This algorithm uses a 'key' as well as the data buffer itself.
* (Buffer[] and Key[] are treated as shift-registers where the MSB of
* Buffer/Key[0] is considered 'left-most' and the LSB of Buffer/Key[N-1]
* is the 'right-most').
*
* Value = 0
* For number of bits in Buffer[]
* If (left-most bit of Buffer[] is 1)
* Value ^= left-most 32 bits of Key[]
* Key[] << 1
* Buffer[] << 1
*
* The code below is provided for convenience where an operating system
* does not already provide an implementation.
*/
#ifdef XEN_NETIF_DEFINE_TOEPLITZ
static uint32_t xen_netif_toeplitz_hash(const uint8_t *key,
unsigned int keylen,
const uint8_t *buf,
unsigned int buflen)
{
unsigned int keyi, bufi;
uint64_t prefix = 0;
uint64_t hash = 0;
/* Pre-load prefix with the first 8 bytes of the key */
for (keyi = 0; keyi < 8; keyi++) {
prefix <<= 8;
prefix |= (keyi < keylen) ? key[keyi] : 0;
}
for (bufi = 0; bufi < buflen; bufi++) {
uint8_t byte = buf[bufi];
unsigned int bit;
for (bit = 0; bit < 8; bit++) {
if (byte & 0x80)
hash ^= prefix;
prefix <<= 1;
byte <<=1;
}
/*
* 'prefix' has now been left-shifted by 8, so
* OR in the next byte.
*/
prefix |= (keyi < keylen) ? key[keyi] : 0;
keyi++;
}
/* The valid part of the hash is in the upper 32 bits. */
return hash >> 32;
}
#endif /* XEN_NETIF_DEFINE_TOEPLITZ */
/*
* Control requests (struct xen_netif_ctrl_request)
* ================================================
@ -1008,3 +1090,13 @@ DEFINE_RING_TYPES(netif_rx, struct netif_rx_request, struct netif_rx_response);
#define NETIF_RSP_NULL 1
#endif
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -1,6 +1,6 @@
/******************************************************************************
* ring.h
*
*
* Shared producer-consumer ring macros.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
@ -33,13 +33,6 @@
* - standard integers types (uint8_t, uint16_t, etc)
* They are provided by stdint.h of the standard headers.
*
* Before using the different macros, you need to provide the following
* macros:
* - xen_mb() a memory barrier
* - xen_rmb() a read memory barrier
* - xen_wmb() a write memory barrier
* Example of those can be found in xenctrl.h.
*
* In addition, if you intend to use the FLEX macros, you also need to
* provide the following, before invoking the FLEX macros:
* - size_t
@ -49,6 +42,14 @@
* and grant_table.h from the Xen public headers.
*/
#include "../xen-compat.h"
#if __XEN_INTERFACE_VERSION__ < 0x00030208
#define xen_mb() mb()
#define xen_rmb() rmb()
#define xen_wmb() wmb()
#endif
typedef unsigned int RING_IDX;
/* Round a 32-bit unsigned constant down to the nearest power of two. */
@ -61,12 +62,12 @@ typedef unsigned int RING_IDX;
/*
* Calculate size of a shared ring, given the total available space for the
* ring and indexes (_sz), and the name tag of the request/response structure.
* A ring contains as many entries as will fit, rounded down to the nearest
* A ring contains as many entries as will fit, rounded down to the nearest
* power of two (so we can mask with (size-1) to loop around).
*/
#define __CONST_RING_SIZE(_s, _sz) \
(__RD32(((_sz) - offsetof(struct _s##_sring, ring)) / \
sizeof_field(struct _s##_sring, ring[0])))
sizeof(((struct _s##_sring *)0)->ring[0])))
/*
* The same for passing in an actual pointer instead of a name tag.
*/
@ -75,7 +76,7 @@ typedef unsigned int RING_IDX;
/*
* Macros to make the correct C datatypes for a new kind of ring.
*
*
* To make a new ring datatype, you need to have two message structures,
* let's say request_t, and response_t already defined.
*
@ -85,7 +86,7 @@ typedef unsigned int RING_IDX;
*
* These expand out to give you a set of types, as you can see below.
* The most important of these are:
*
*
* mytag_sring_t - The shared ring.
* mytag_front_ring_t - The 'front' half of the ring.
* mytag_back_ring_t - The 'back' half of the ring.
@ -153,15 +154,15 @@ typedef struct __name##_back_ring __name##_back_ring_t
/*
* Macros for manipulating rings.
*
* FRONT_RING_whatever works on the "front end" of a ring: here
*
* FRONT_RING_whatever works on the "front end" of a ring: here
* requests are pushed on to the ring and responses taken off it.
*
* BACK_RING_whatever works on the "back end" of a ring: here
*
* BACK_RING_whatever works on the "back end" of a ring: here
* requests are taken off the ring and responses put on.
*
* N.B. these macros do NO INTERLOCKS OR FLOW CONTROL.
* This is OK in 1-for-1 request-response situations where the
*
* N.B. these macros do NO INTERLOCKS OR FLOW CONTROL.
* This is OK in 1-for-1 request-response situations where the
* requestor (front end) never has more than RING_SIZE()-1
* outstanding requests.
*/
@ -174,20 +175,24 @@ typedef struct __name##_back_ring __name##_back_ring_t
(void)memset((_s)->__pad, 0, sizeof((_s)->__pad)); \
} while(0)
#define FRONT_RING_INIT(_r, _s, __size) do { \
(_r)->req_prod_pvt = 0; \
(_r)->rsp_cons = 0; \
#define FRONT_RING_ATTACH(_r, _s, _i, __size) do { \
(_r)->req_prod_pvt = (_i); \
(_r)->rsp_cons = (_i); \
(_r)->nr_ents = __RING_SIZE(_s, __size); \
(_r)->sring = (_s); \
} while (0)
#define BACK_RING_INIT(_r, _s, __size) do { \
(_r)->rsp_prod_pvt = 0; \
(_r)->req_cons = 0; \
#define FRONT_RING_INIT(_r, _s, __size) FRONT_RING_ATTACH(_r, _s, 0, __size)
#define BACK_RING_ATTACH(_r, _s, _i, __size) do { \
(_r)->rsp_prod_pvt = (_i); \
(_r)->req_cons = (_i); \
(_r)->nr_ents = __RING_SIZE(_s, __size); \
(_r)->sring = (_s); \
} while (0)
#define BACK_RING_INIT(_r, _s, __size) BACK_RING_ATTACH(_r, _s, 0, __size)
/* How big is this ring? */
#define RING_SIZE(_r) \
((_r)->nr_ents)
@ -206,33 +211,45 @@ typedef struct __name##_back_ring __name##_back_ring_t
#define RING_HAS_UNCONSUMED_RESPONSES(_r) \
((_r)->sring->rsp_prod - (_r)->rsp_cons)
#ifdef __GNUC__
#define RING_HAS_UNCONSUMED_REQUESTS(_r) ({ \
unsigned int req = (_r)->sring->req_prod - (_r)->req_cons; \
unsigned int rsp = RING_SIZE(_r) - \
((_r)->req_cons - (_r)->rsp_prod_pvt); \
req < rsp ? req : rsp; \
})
#else
/* Same as above, but without the nice GCC ({ ... }) syntax. */
#define RING_HAS_UNCONSUMED_REQUESTS(_r) \
((((_r)->sring->req_prod - (_r)->req_cons) < \
(RING_SIZE(_r) - ((_r)->req_cons - (_r)->rsp_prod_pvt))) ? \
((_r)->sring->req_prod - (_r)->req_cons) : \
(RING_SIZE(_r) - ((_r)->req_cons - (_r)->rsp_prod_pvt)))
#endif
/* Direct access to individual ring elements, by index. */
#define RING_GET_REQUEST(_r, _idx) \
(&((_r)->sring->ring[((_idx) & (RING_SIZE(_r) - 1))].req))
#define RING_GET_RESPONSE(_r, _idx) \
(&((_r)->sring->ring[((_idx) & (RING_SIZE(_r) - 1))].rsp))
/*
* Get a local copy of a request.
* Get a local copy of a request/response.
*
* Use this in preference to RING_GET_REQUEST() so all processing is
* Use this in preference to RING_GET_{REQUEST,RESPONSE}() so all processing is
* done on a local copy that cannot be modified by the other end.
*
* Note that https://gcc.gnu.org/bugzilla/show_bug.cgi?id=58145 may cause this
* to be ineffective where _req is a struct which consists of only bitfields.
* to be ineffective where dest is a struct which consists of only bitfields.
*/
#define RING_COPY_REQUEST(_r, _idx, _req) do { \
/* Use volatile to force the copy into _req. */ \
*(_req) = *(volatile typeof(_req))RING_GET_REQUEST(_r, _idx); \
#define RING_COPY_(type, r, idx, dest) do { \
/* Use volatile to force the copy into dest. */ \
*(dest) = *(volatile __typeof__(dest))RING_GET_##type(r, idx); \
} while (0)
#define RING_GET_RESPONSE(_r, _idx) \
(&((_r)->sring->ring[((_idx) & (RING_SIZE(_r) - 1))].rsp))
#define RING_COPY_REQUEST(r, idx, req) RING_COPY_(REQUEST, r, idx, req)
#define RING_COPY_RESPONSE(r, idx, rsp) RING_COPY_(RESPONSE, r, idx, rsp)
/* Loop termination condition: Would the specified index overflow the ring? */
#define RING_REQUEST_CONS_OVERFLOW(_r, _cons) \
@ -242,6 +259,10 @@ typedef struct __name##_back_ring __name##_back_ring_t
#define RING_REQUEST_PROD_OVERFLOW(_r, _prod) \
(((_prod) - (_r)->rsp_prod_pvt) > RING_SIZE(_r))
/* Ill-behaved backend determination: Can there be this many responses? */
#define RING_RESPONSE_PROD_OVERFLOW(_r, _prod) \
(((_prod) - (_r)->rsp_cons) > RING_SIZE(_r))
#define RING_PUSH_REQUESTS(_r) do { \
xen_wmb(); /* back sees requests /before/ updated producer index */ \
(_r)->sring->req_prod = (_r)->req_prod_pvt; \
@ -254,26 +275,26 @@ typedef struct __name##_back_ring __name##_back_ring_t
/*
* Notification hold-off (req_event and rsp_event):
*
*
* When queueing requests or responses on a shared ring, it may not always be
* necessary to notify the remote end. For example, if requests are in flight
* in a backend, the front may be able to queue further requests without
* notifying the back (if the back checks for new requests when it queues
* responses).
*
*
* When enqueuing requests or responses:
*
*
* Use RING_PUSH_{REQUESTS,RESPONSES}_AND_CHECK_NOTIFY(). The second argument
* is a boolean return value. True indicates that the receiver requires an
* asynchronous notification.
*
*
* After dequeuing requests or responses (before sleeping the connection):
*
*
* Use RING_FINAL_CHECK_FOR_REQUESTS() or RING_FINAL_CHECK_FOR_RESPONSES().
* The second argument is a boolean return value. True indicates that there
* are pending messages on the ring (i.e., the connection should not be put
* to sleep).
*
*
* These macros will set the req_event/rsp_event field to trigger a
* notification on the very next message that is enqueued. If you want to
* create batches of work (i.e., only receive a notification after several

View file

@ -32,6 +32,34 @@
#include "../grant_table.h"
/*
* Detailed Interface Description
* ==============================
* The pvUSB interface is using a split driver design: a frontend driver in
* the guest and a backend driver in a driver domain (normally dom0) having
* access to the physical USB device(s) being passed to the guest.
*
* The frontend and backend drivers use XenStore to initiate the connection
* between them, the I/O activity is handled via two shared ring pages and an
* event channel. As the interface between frontend and backend is at the USB
* host connector level, multiple (up to 31) physical USB devices can be
* handled by a single connection.
*
* The Xen pvUSB device name is "qusb", so the frontend's XenStore entries are
* to be found under "device/qusb", while the backend's XenStore entries are
* under "backend/<guest-dom-id>/qusb".
*
* When a new pvUSB connection is established, the frontend needs to setup the
* two shared ring pages for communication and the event channel. The ring
* pages need to be made available to the backend via the grant table
* interface.
*
* One of the shared ring pages is used by the backend to inform the frontend
* about USB device plug events (device to be added or removed). This is the
* "conn-ring".
*
* The other ring page is used for USB I/O communication (requests and
* responses). This is the "urb-ring".
*
* Feature and Parameter Negotiation
* =================================
* The two halves of a Xen pvUSB driver utilize nodes within the XenStore to
@ -99,130 +127,273 @@
* The machine ABI rules governing the format of all ring request and
* response structures.
*
* Protocol Description
* ====================
*
*-------------------------- USB device plug events --------------------------
*
* USB device plug events are send via the "conn-ring" shared page. As only
* events are being sent, the respective requests from the frontend to the
* backend are just dummy ones.
* The events sent to the frontend have the following layout:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | id | portnum | speed | 4
* +----------------+----------------+----------------+----------------+
* id - uint16_t, event id (taken from the actual frontend dummy request)
* portnum - uint8_t, port number (1 ... 31)
* speed - uint8_t, device USBIF_SPEED_*, USBIF_SPEED_NONE == unplug
*
* The dummy request:
* 0 1 octet
* +----------------+----------------+
* | id | 2
* +----------------+----------------+
* id - uint16_t, guest supplied value (no need for being unique)
*
*-------------------------- USB I/O request ---------------------------------
*
* A single USB I/O request on the "urb-ring" has the following layout:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | id | nr_buffer_segs | 4
* +----------------+----------------+----------------+----------------+
* | pipe | 8
* +----------------+----------------+----------------+----------------+
* | transfer_flags | buffer_length | 12
* +----------------+----------------+----------------+----------------+
* | request type specific | 16
* | data | 20
* +----------------+----------------+----------------+----------------+
* | seg[0] | 24
* | data | 28
* +----------------+----------------+----------------+----------------+
* |/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/|
* +----------------+----------------+----------------+----------------+
* | seg[USBIF_MAX_SEGMENTS_PER_REQUEST - 1] | 144
* | data | 148
* +----------------+----------------+----------------+----------------+
* Bit field bit number 0 is always least significant bit, undefined bits must
* be zero.
* id - uint16_t, guest supplied value
* nr_buffer_segs - uint16_t, number of segment entries in seg[] array
* pipe - uint32_t, bit field with multiple information:
* bits 0-4: port request to send to
* bit 5: unlink request with specified id (cancel I/O) if set (see below)
* bit 7: direction (1 = read from device)
* bits 8-14: device number on port
* bits 15-18: endpoint of device
* bits 30-31: request type: 00 = isochronous, 01 = interrupt,
* 10 = control, 11 = bulk
* transfer_flags - uint16_t, bit field with processing flags:
* bit 0: less data than specified allowed
* buffer_length - uint16_t, total length of data
* request type specific data - 8 bytes, see below
* seg[] - array with 8 byte elements, see below
*
* Request type specific data for isochronous request:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | interval | start_frame | 4
* +----------------+----------------+----------------+----------------+
* | number_of_packets | nr_frame_desc_segs | 8
* +----------------+----------------+----------------+----------------+
* interval - uint16_t, time interval in msecs between frames
* start_frame - uint16_t, start frame number
* number_of_packets - uint16_t, number of packets to transfer
* nr_frame_desc_segs - uint16_t number of seg[] frame descriptors elements
*
* Request type specific data for interrupt request:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | interval | 0 | 4
* +----------------+----------------+----------------+----------------+
* | 0 | 8
* +----------------+----------------+----------------+----------------+
* interval - uint16_t, time in msecs until interruption
*
* Request type specific data for control request:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | data of setup packet | 4
* | | 8
* +----------------+----------------+----------------+----------------+
*
* Request type specific data for bulk request:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | 0 | 4
* | 0 | 8
* +----------------+----------------+----------------+----------------+
*
* Request type specific data for unlink request:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | unlink_id | 0 | 4
* +----------------+----------------+----------------+----------------+
* | 0 | 8
* +----------------+----------------+----------------+----------------+
* unlink_id - uint16_t, request id of request to terminate
*
* seg[] array element layout:
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | gref | 4
* +----------------+----------------+----------------+----------------+
* | offset | length | 8
* +----------------+----------------+----------------+----------------+
* gref - uint32_t, grant reference of buffer page
* offset - uint16_t, offset of buffer start in page
* length - uint16_t, length of buffer in page
*
*-------------------------- USB I/O response --------------------------------
*
* 0 1 2 3 octet
* +----------------+----------------+----------------+----------------+
* | id | start_frame | 4
* +----------------+----------------+----------------+----------------+
* | status | 8
* +----------------+----------------+----------------+----------------+
* | actual_length | 12
* +----------------+----------------+----------------+----------------+
* | error_count | 16
* +----------------+----------------+----------------+----------------+
* id - uint16_t, id of the request this response belongs to
* start_frame - uint16_t, start_frame this response (iso requests only)
* status - int32_t, USBIF_STATUS_* (non-iso requests)
* actual_length - uint32_t, actual size of data transferred
* error_count - uint32_t, number of errors (iso requests)
*/
enum usb_spec_version {
USB_VER_UNKNOWN = 0,
USB_VER_USB11,
USB_VER_USB20,
USB_VER_USB30, /* not supported yet */
USB_VER_UNKNOWN = 0,
USB_VER_USB11,
USB_VER_USB20,
USB_VER_USB30, /* not supported yet */
};
/*
* USB pipe in usbif_request
*
* - port number: bits 0-4
* (USB_MAXCHILDREN is 31)
* - port number: bits 0-4
* (USB_MAXCHILDREN is 31)
*
* - operation flag: bit 5
* (0 = submit urb,
* 1 = unlink urb)
* - operation flag: bit 5
* (0 = submit urb,
* 1 = unlink urb)
*
* - direction: bit 7
* (0 = Host-to-Device [Out]
* 1 = Device-to-Host [In])
* - direction: bit 7
* (0 = Host-to-Device [Out]
* 1 = Device-to-Host [In])
*
* - device address: bits 8-14
* - device address: bits 8-14
*
* - endpoint: bits 15-18
* - endpoint: bits 15-18
*
* - pipe type: bits 30-31
* (00 = isochronous, 01 = interrupt,
* 10 = control, 11 = bulk)
* - pipe type: bits 30-31
* (00 = isochronous, 01 = interrupt,
* 10 = control, 11 = bulk)
*/
#define USBIF_PIPE_PORT_MASK 0x0000001f
#define USBIF_PIPE_UNLINK 0x00000020
#define USBIF_PIPE_DIR 0x00000080
#define USBIF_PIPE_DEV_MASK 0x0000007f
#define USBIF_PIPE_DEV_SHIFT 8
#define USBIF_PIPE_EP_MASK 0x0000000f
#define USBIF_PIPE_EP_SHIFT 15
#define USBIF_PIPE_TYPE_MASK 0x00000003
#define USBIF_PIPE_TYPE_SHIFT 30
#define USBIF_PIPE_TYPE_ISOC 0
#define USBIF_PIPE_TYPE_INT 1
#define USBIF_PIPE_TYPE_CTRL 2
#define USBIF_PIPE_TYPE_BULK 3
#define USBIF_PIPE_PORT_MASK 0x0000001f
#define USBIF_PIPE_UNLINK 0x00000020
#define USBIF_PIPE_DIR 0x00000080
#define USBIF_PIPE_DEV_MASK 0x0000007f
#define USBIF_PIPE_DEV_SHIFT 8
#define USBIF_PIPE_EP_MASK 0x0000000f
#define USBIF_PIPE_EP_SHIFT 15
#define USBIF_PIPE_TYPE_MASK 0x00000003
#define USBIF_PIPE_TYPE_SHIFT 30
#define USBIF_PIPE_TYPE_ISOC 0
#define USBIF_PIPE_TYPE_INT 1
#define USBIF_PIPE_TYPE_CTRL 2
#define USBIF_PIPE_TYPE_BULK 3
#define usbif_pipeportnum(pipe) ((pipe) & USBIF_PIPE_PORT_MASK)
#define usbif_setportnum_pipe(pipe, portnum) ((pipe) | (portnum))
#define usbif_pipeportnum(pipe) ((pipe) & USBIF_PIPE_PORT_MASK)
#define usbif_setportnum_pipe(pipe, portnum) ((pipe) | (portnum))
#define usbif_pipeunlink(pipe) ((pipe) & USBIF_PIPE_UNLINK)
#define usbif_pipesubmit(pipe) (!usbif_pipeunlink(pipe))
#define usbif_setunlink_pipe(pipe) ((pipe) | USBIF_PIPE_UNLINK)
#define usbif_pipeunlink(pipe) ((pipe) & USBIF_PIPE_UNLINK)
#define usbif_pipesubmit(pipe) (!usbif_pipeunlink(pipe))
#define usbif_setunlink_pipe(pipe) ((pipe) | USBIF_PIPE_UNLINK)
#define usbif_pipein(pipe) ((pipe) & USBIF_PIPE_DIR)
#define usbif_pipeout(pipe) (!usbif_pipein(pipe))
#define usbif_pipein(pipe) ((pipe) & USBIF_PIPE_DIR)
#define usbif_pipeout(pipe) (!usbif_pipein(pipe))
#define usbif_pipedevice(pipe) \
(((pipe) >> USBIF_PIPE_DEV_SHIFT) & USBIF_PIPE_DEV_MASK)
#define usbif_pipedevice(pipe) \
(((pipe) >> USBIF_PIPE_DEV_SHIFT) & USBIF_PIPE_DEV_MASK)
#define usbif_pipeendpoint(pipe) \
(((pipe) >> USBIF_PIPE_EP_SHIFT) & USBIF_PIPE_EP_MASK)
#define usbif_pipeendpoint(pipe) \
(((pipe) >> USBIF_PIPE_EP_SHIFT) & USBIF_PIPE_EP_MASK)
#define usbif_pipetype(pipe) \
(((pipe) >> USBIF_PIPE_TYPE_SHIFT) & USBIF_PIPE_TYPE_MASK)
#define usbif_pipeisoc(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_ISOC)
#define usbif_pipeint(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_INT)
#define usbif_pipectrl(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_CTRL)
#define usbif_pipebulk(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_BULK)
#define usbif_pipetype(pipe) \
(((pipe) >> USBIF_PIPE_TYPE_SHIFT) & USBIF_PIPE_TYPE_MASK)
#define usbif_pipeisoc(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_ISOC)
#define usbif_pipeint(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_INT)
#define usbif_pipectrl(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_CTRL)
#define usbif_pipebulk(pipe) (usbif_pipetype(pipe) == USBIF_PIPE_TYPE_BULK)
#define USBIF_MAX_SEGMENTS_PER_REQUEST (16)
#define USBIF_MAX_PORTNR 31
#define USBIF_RING_SIZE 4096
#define USBIF_MAX_PORTNR 31
#define USBIF_RING_SIZE 4096
/*
* RING for transferring urbs.
*/
struct usbif_request_segment {
grant_ref_t gref;
uint16_t offset;
uint16_t length;
grant_ref_t gref;
uint16_t offset;
uint16_t length;
};
struct usbif_urb_request {
uint16_t id; /* request id */
uint16_t nr_buffer_segs; /* number of urb->transfer_buffer segments */
uint16_t id; /* request id */
uint16_t nr_buffer_segs; /* number of urb->transfer_buffer segments */
/* basic urb parameter */
uint32_t pipe;
uint16_t transfer_flags;
#define USBIF_SHORT_NOT_OK 0x0001
uint16_t buffer_length;
union {
uint8_t ctrl[8]; /* setup_packet (Ctrl) */
/* basic urb parameter */
uint32_t pipe;
uint16_t transfer_flags;
#define USBIF_SHORT_NOT_OK 0x0001
uint16_t buffer_length;
union {
uint8_t ctrl[8]; /* setup_packet (Ctrl) */
struct {
uint16_t interval; /* maximum (1024*8) in usb core */
uint16_t start_frame; /* start frame */
uint16_t number_of_packets; /* number of ISO packet */
uint16_t nr_frame_desc_segs; /* number of iso_frame_desc segments */
} isoc;
struct {
uint16_t interval; /* maximum (1024*8) in usb core */
uint16_t start_frame; /* start frame */
uint16_t number_of_packets; /* number of ISO packet */
uint16_t nr_frame_desc_segs; /* number of iso_frame_desc segments */
} isoc;
struct {
uint16_t interval; /* maximum (1024*8) in usb core */
uint16_t pad[3];
} intr;
struct {
uint16_t interval; /* maximum (1024*8) in usb core */
uint16_t pad[3];
} intr;
struct {
uint16_t unlink_id; /* unlink request id */
uint16_t pad[3];
} unlink;
struct {
uint16_t unlink_id; /* unlink request id */
uint16_t pad[3];
} unlink;
} u;
} u;
/* urb data segments */
struct usbif_request_segment seg[USBIF_MAX_SEGMENTS_PER_REQUEST];
/* urb data segments */
struct usbif_request_segment seg[USBIF_MAX_SEGMENTS_PER_REQUEST];
};
typedef struct usbif_urb_request usbif_urb_request_t;
struct usbif_urb_response {
uint16_t id; /* request id */
uint16_t start_frame; /* start frame (ISO) */
int32_t status; /* status (non-ISO) */
int32_t actual_length; /* actual transfer length */
int32_t error_count; /* number of ISO errors */
uint16_t id; /* request id */
uint16_t start_frame; /* start frame (ISO) */
int32_t status; /* status (non-ISO) */
#define USBIF_STATUS_OK 0
#define USBIF_STATUS_NODEV (-19)
#define USBIF_STATUS_INVAL (-22)
#define USBIF_STATUS_STALL (-32)
#define USBIF_STATUS_IOERROR (-71)
#define USBIF_STATUS_BABBLE (-75)
#define USBIF_STATUS_SHUTDOWN (-108)
int32_t actual_length; /* actual transfer length */
int32_t error_count; /* number of ISO errors */
};
typedef struct usbif_urb_response usbif_urb_response_t;
@ -233,18 +404,18 @@ DEFINE_RING_TYPES(usbif_urb, struct usbif_urb_request, struct usbif_urb_response
* RING for notifying connect/disconnect events to frontend
*/
struct usbif_conn_request {
uint16_t id;
uint16_t id;
};
typedef struct usbif_conn_request usbif_conn_request_t;
struct usbif_conn_response {
uint16_t id; /* request id */
uint8_t portnum; /* port number */
uint8_t speed; /* usb_device_speed */
#define USBIF_SPEED_NONE 0
#define USBIF_SPEED_LOW 1
#define USBIF_SPEED_FULL 2
#define USBIF_SPEED_HIGH 3
uint16_t id; /* request id */
uint8_t portnum; /* port number */
uint8_t speed; /* usb_device_speed */
#define USBIF_SPEED_NONE 0
#define USBIF_SPEED_LOW 1
#define USBIF_SPEED_FULL 2
#define USBIF_SPEED_HIGH 3
};
typedef struct usbif_conn_response usbif_conn_response_t;

View file

@ -68,3 +68,13 @@ enum xenbus_state {
typedef enum xenbus_state XenbusState;
#endif /* _XEN_PUBLIC_IO_XENBUS_H */
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/

View file

@ -0,0 +1,153 @@
/*
* Details of the "wire" protocol between Xen Store Daemon and client
* library or guest kernel.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to
* deal in the Software without restriction, including without limitation the
* rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
* sell copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*
* Copyright (C) 2005 Rusty Russell IBM Corporation
*/
#ifndef _XS_WIRE_H
#define _XS_WIRE_H
enum xsd_sockmsg_type
{
XS_CONTROL,
#define XS_DEBUG XS_CONTROL
XS_DIRECTORY,
XS_READ,
XS_GET_PERMS,
XS_WATCH,
XS_UNWATCH,
XS_TRANSACTION_START,
XS_TRANSACTION_END,
XS_INTRODUCE,
XS_RELEASE,
XS_GET_DOMAIN_PATH,
XS_WRITE,
XS_MKDIR,
XS_RM,
XS_SET_PERMS,
XS_WATCH_EVENT,
XS_ERROR,
XS_IS_DOMAIN_INTRODUCED,
XS_RESUME,
XS_SET_TARGET,
/* XS_RESTRICT has been removed */
XS_RESET_WATCHES = XS_SET_TARGET + 2,
XS_DIRECTORY_PART,
XS_TYPE_COUNT, /* Number of valid types. */
XS_INVALID = 0xffff /* Guaranteed to remain an invalid type */
};
#define XS_WRITE_NONE "NONE"
#define XS_WRITE_CREATE "CREATE"
#define XS_WRITE_CREATE_EXCL "CREATE|EXCL"
/* We hand errors as strings, for portability. */
struct xsd_errors
{
int errnum;
const char *errstring;
};
#ifdef EINVAL
#define XSD_ERROR(x) { x, #x }
/* LINTED: static unused */
static struct xsd_errors xsd_errors[]
#if defined(__GNUC__)
__attribute__((unused))
#endif
= {
XSD_ERROR(EINVAL),
XSD_ERROR(EACCES),
XSD_ERROR(EEXIST),
XSD_ERROR(EISDIR),
XSD_ERROR(ENOENT),
XSD_ERROR(ENOMEM),
XSD_ERROR(ENOSPC),
XSD_ERROR(EIO),
XSD_ERROR(ENOTEMPTY),
XSD_ERROR(ENOSYS),
XSD_ERROR(EROFS),
XSD_ERROR(EBUSY),
XSD_ERROR(EAGAIN),
XSD_ERROR(EISCONN),
XSD_ERROR(E2BIG)
};
#endif
struct xsd_sockmsg
{
uint32_t type; /* XS_??? */
uint32_t req_id;/* Request identifier, echoed in daemon's response. */
uint32_t tx_id; /* Transaction id (0 if not related to a transaction). */
uint32_t len; /* Length of data following this. */
/* Generally followed by nul-terminated string(s). */
};
enum xs_watch_type
{
XS_WATCH_PATH = 0,
XS_WATCH_TOKEN
};
/*
* `incontents 150 xenstore_struct XenStore wire protocol.
*
* Inter-domain shared memory communications. */
#define XENSTORE_RING_SIZE 1024
typedef uint32_t XENSTORE_RING_IDX;
#define MASK_XENSTORE_IDX(idx) ((idx) & (XENSTORE_RING_SIZE-1))
struct xenstore_domain_interface {
char req[XENSTORE_RING_SIZE]; /* Requests to xenstore daemon. */
char rsp[XENSTORE_RING_SIZE]; /* Replies and async watch events. */
XENSTORE_RING_IDX req_cons, req_prod;
XENSTORE_RING_IDX rsp_cons, rsp_prod;
uint32_t server_features; /* Bitmap of features supported by the server */
uint32_t connection;
};
/* Violating this is very bad. See docs/misc/xenstore.txt. */
#define XENSTORE_PAYLOAD_MAX 4096
/* Violating these just gets you an error back */
#define XENSTORE_ABS_PATH_MAX 3072
#define XENSTORE_REL_PATH_MAX 2048
/* The ability to reconnect a ring */
#define XENSTORE_SERVER_FEATURE_RECONNECTION 1
/* Valid values for the connection field */
#define XENSTORE_CONNECTED 0 /* the steady-state */
#define XENSTORE_RECONNECT 1 /* guest has initiated a reconnect */
#endif /* _XS_WIRE_H */
/*
* Local variables:
* mode: C
* c-file-style: "BSD"
* c-basic-offset: 4
* tab-width: 4
* indent-tabs-mode: nil
* End:
*/