root / docs / specs / ivshmem_device_spec.txt @ b6828931
History | View | Annotate | Download (4.3 kB)
1 |
|
---|---|
2 |
Device Specification for Inter-VM shared memory device |
3 |
------------------------------------------------------ |
4 |
|
5 |
The Inter-VM shared memory device is designed to share a region of memory to |
6 |
userspace in multiple virtual guests. The memory region does not belong to any |
7 |
guest, but is a POSIX memory object on the host. Optionally, the device may |
8 |
support sending interrupts to other guests sharing the same memory region. |
9 |
|
10 |
|
11 |
The Inter-VM PCI device |
12 |
----------------------- |
13 |
|
14 |
*BARs* |
15 |
|
16 |
The device supports three BARs. BAR0 is a 1 Kbyte MMIO region to support |
17 |
registers. BAR1 is used for MSI-X when it is enabled in the device. BAR2 is |
18 |
used to map the shared memory object from the host. The size of BAR2 is |
19 |
specified when the guest is started and must be a power of 2 in size. |
20 |
|
21 |
*Registers* |
22 |
|
23 |
The device currently supports 4 registers of 32-bits each. Registers |
24 |
are used for synchronization between guests sharing the same memory object when |
25 |
interrupts are supported (this requires using the shared memory server). |
26 |
|
27 |
The server assigns each VM an ID number and sends this ID number to the Qemu |
28 |
process when the guest starts. |
29 |
|
30 |
enum ivshmem_registers { |
31 |
IntrMask = 0, |
32 |
IntrStatus = 4, |
33 |
IVPosition = 8, |
34 |
Doorbell = 12 |
35 |
}; |
36 |
|
37 |
The first two registers are the interrupt mask and status registers. Mask and |
38 |
status are only used with pin-based interrupts. They are unused with MSI |
39 |
interrupts. |
40 |
|
41 |
Status Register: The status register is set to 1 when an interrupt occurs. |
42 |
|
43 |
Mask Register: The mask register is bitwise ANDed with the interrupt status |
44 |
and the result will raise an interrupt if it is non-zero. However, since 1 is |
45 |
the only value the status will be set to, it is only the first bit of the mask |
46 |
that has any effect. Therefore interrupts can be masked by setting the first |
47 |
bit to 0 and unmasked by setting the first bit to 1. |
48 |
|
49 |
IVPosition Register: The IVPosition register is read-only and reports the |
50 |
guest's ID number. The guest IDs are non-negative integers. When using the |
51 |
server, since the server is a separate process, the VM ID will only be set when |
52 |
the device is ready (shared memory is received from the server and accessible via |
53 |
the device). If the device is not ready, the IVPosition will return -1. |
54 |
Applications should ensure that they have a valid VM ID before accessing the |
55 |
shared memory. |
56 |
|
57 |
Doorbell Register: To interrupt another guest, a guest must write to the |
58 |
Doorbell register. The doorbell register is 32-bits, logically divided into |
59 |
two 16-bit fields. The high 16-bits are the guest ID to interrupt and the low |
60 |
16-bits are the interrupt vector to trigger. The semantics of the value |
61 |
written to the doorbell depends on whether the device is using MSI or a regular |
62 |
pin-based interrupt. In short, MSI uses vectors while regular interrupts set the |
63 |
status register. |
64 |
|
65 |
Regular Interrupts |
66 |
|
67 |
If regular interrupts are used (due to either a guest not supporting MSI or the |
68 |
user specifying not to use them on startup) then the value written to the lower |
69 |
16-bits of the Doorbell register results is arbitrary and will trigger an |
70 |
interrupt in the destination guest. |
71 |
|
72 |
Message Signalled Interrupts |
73 |
|
74 |
A ivshmem device may support multiple MSI vectors. If so, the lower 16-bits |
75 |
written to the Doorbell register must be between 0 and the maximum number of |
76 |
vectors the guest supports. The lower 16 bits written to the doorbell is the |
77 |
MSI vector that will be raised in the destination guest. The number of MSI |
78 |
vectors is configurable but it is set when the VM is started. |
79 |
|
80 |
The important thing to remember with MSI is that it is only a signal, no status |
81 |
is set (since MSI interrupts are not shared). All information other than the |
82 |
interrupt itself should be communicated via the shared memory region. Devices |
83 |
supporting multiple MSI vectors can use different vectors to indicate different |
84 |
events have occurred. The semantics of interrupt vectors are left to the |
85 |
user's discretion. |
86 |
|
87 |
|
88 |
Usage in the Guest |
89 |
------------------ |
90 |
|
91 |
The shared memory device is intended to be used with the provided UIO driver. |
92 |
Very little configuration is needed. The guest should map BAR0 to access the |
93 |
registers (an array of 32-bit ints allows simple writing) and map BAR2 to |
94 |
access the shared memory region itself. The size of the shared memory region |
95 |
is specified when the guest (or shared memory server) is started. A guest may |
96 |
map the whole shared memory region or only part of it. |