]> rtime.felk.cvut.cz Git - jailhouse.git/blob - inmates/lib/x86/inmate.h
inmates: pci: include feature check in capability lookup
[jailhouse.git] / inmates / lib / x86 / inmate.h
1 /*
2  * Jailhouse, a Linux-based partitioning hypervisor
3  *
4  * Copyright (c) Siemens AG, 2013
5  *
6  * Authors:
7  *  Jan Kiszka <jan.kiszka@siemens.com>
8  *
9  * This work is licensed under the terms of the GNU GPL, version 2.  See
10  * the COPYING file in the top-level directory.
11  */
12
13 #define NULL                    ((void *)0)
14
15 #define HEAP_BASE               0x000000
16 #define FSEGMENT_BASE           0x0f0000
17 #define COMM_REGION_BASE        0x100000
18
19 #define INMATE_CS32             0x8
20 #define INMATE_CS64             0x10
21 #define INMATE_DS32             0x18
22
23 #define NS_PER_USEC             1000UL
24 #define NS_PER_MSEC             1000000UL
25 #define NS_PER_SEC              1000000000UL
26
27 #define PAGE_SIZE               (4 * 1024ULL)
28 #ifdef __x86_64__
29 #define HUGE_PAGE_SIZE          (2 * 1024 * 1024ULL)
30 #else
31 #define HUGE_PAGE_SIZE          (4 * 1024 * 1024ULL)
32 #endif
33 #define PAGE_MASK               (~(PAGE_SIZE - 1))
34 #define HUGE_PAGE_MASK          (~(HUGE_PAGE_SIZE - 1))
35
36 #define X2APIC_ID               0x802
37
38 #define PCI_CFG_VENDOR_ID       0x000
39 #define PCI_CFG_DEVICE_ID       0x002
40 #define PCI_CFG_COMMAND         0x004
41 # define PCI_CMD_IO             (1 << 0)
42 # define PCI_CMD_MEM            (1 << 1)
43 # define PCI_CMD_MASTER         (1 << 2)
44 # define PCI_CMD_INTX_OFF       (1 << 10)
45 #define PCI_CFG_STATUS          0x006
46 # define PCI_STS_INT            (1 << 3)
47 # define PCI_STS_CAPS           (1 << 4)
48 #define PCI_CFG_BAR             0x010
49 # define PCI_BAR_64BIT          0x4
50 #define PCI_CFG_CAP_PTR         0x034
51
52 #define PCI_ID_ANY              0xffff
53
54 #define PCI_CAP_MSI             0x05
55 #define PCI_CAP_MSIX            0x11
56
57 #define MSIX_CTRL_ENABLE        0x8000
58 #define MSIX_CTRL_FMASK         0x4000
59
60 #ifndef __ASSEMBLY__
61 typedef signed char s8;
62 typedef unsigned char u8;
63
64 typedef signed short s16;
65 typedef unsigned short u16;
66
67 typedef signed int s32;
68 typedef unsigned int u32;
69
70 typedef signed long long s64;
71 typedef unsigned long long u64;
72
73 typedef s8 __s8;
74 typedef u8 __u8;
75
76 typedef s16 __s16;
77 typedef u16 __u16;
78
79 typedef s32 __s32;
80 typedef u32 __u32;
81
82 typedef s64 __s64;
83 typedef u64 __u64;
84
85 typedef enum { true=1, false=0 } bool;
86
87 static inline void cpu_relax(void)
88 {
89         asm volatile("rep; nop" : : : "memory");
90 }
91
92 static inline void outb(u8 v, u16 port)
93 {
94         asm volatile("outb %0,%1" : : "a" (v), "dN" (port));
95 }
96
97 static inline void outw(u16 v, u16 port)
98 {
99         asm volatile("outw %0,%1" : : "a" (v), "dN" (port));
100 }
101
102 static inline void outl(u32 v, u16 port)
103 {
104         asm volatile("outl %0,%1" : : "a" (v), "dN" (port));
105 }
106
107 static inline u8 inb(u16 port)
108 {
109         u8 v;
110         asm volatile("inb %1,%0" : "=a" (v) : "dN" (port));
111         return v;
112 }
113
114 static inline u16 inw(u16 port)
115 {
116         u16 v;
117         asm volatile("inw %1,%0" : "=a" (v) : "dN" (port));
118         return v;
119 }
120
121 static inline u32 inl(u16 port)
122 {
123         u32 v;
124         asm volatile("inl %1,%0" : "=a" (v) : "dN" (port));
125         return v;
126 }
127
128 static inline u8 mmio_read8(void *address)
129 {
130         return *(volatile u8 *)address;
131 }
132
133 static inline u16 mmio_read16(void *address)
134 {
135         return *(volatile u16 *)address;
136 }
137
138 static inline u32 mmio_read32(void *address)
139 {
140         u32 value;
141
142         /* assembly-encoded to match the hypervisor MMIO parser support */
143         asm volatile("movl (%1),%0" : "=r" (value) : "r" (address));
144         return value;
145 }
146
147 static inline u64 mmio_read64(void *address)
148 {
149         return *(volatile u64 *)address;
150 }
151
152 static inline void mmio_write8(void *address, u8 value)
153 {
154         *(volatile u8 *)address = value;
155 }
156
157 static inline void mmio_write16(void *address, u16 value)
158 {
159         *(volatile u16 *)address = value;
160 }
161
162 static inline void mmio_write32(void *address, u32 value)
163 {
164         /* assembly-encoded to match the hypervisor MMIO parser support */
165         asm volatile("movl %0,(%1)" : : "r" (value), "r" (address));
166 }
167
168 static inline void mmio_write64(void *address, u64 value)
169 {
170         *(volatile u64 *)address = value;
171 }
172
173 static inline u64 read_msr(unsigned int msr)
174 {
175         u32 low, high;
176
177         asm volatile("rdmsr" : "=a" (low), "=d" (high) : "c" (msr));
178         return low | ((u64)high << 32);
179 }
180
181 static inline void write_msr(unsigned int msr, u64 val)
182 {
183         asm volatile("wrmsr"
184                 : /* no output */
185                 : "c" (msr), "a" (val), "d" (val >> 32)
186                 : "memory");
187 }
188
189 static inline unsigned int cpu_id(void)
190 {
191         return read_msr(X2APIC_ID);
192 }
193
194 #include <jailhouse/hypercall.h>
195
196 #define comm_region     ((struct jailhouse_comm_region *)COMM_REGION_BASE)
197
198 extern unsigned int printk_uart_base;
199 void printk(const char *fmt, ...);
200
201 void *memset(void *s, int c, unsigned long n);
202 void *memcpy(void *d, const void *s, unsigned long n);
203
204 typedef void(*int_handler_t)(void);
205
206 void int_init(void);
207 void int_set_handler(unsigned int vector, int_handler_t handler);
208
209 enum ioapic_trigger_mode {
210         TRIGGER_EDGE = 0,
211         TRIGGER_LEVEL_ACTIVE_HIGH = 1 << 15,
212         TRIGGER_LEVEL_ACTIVE_LOW = (1 << 15) | (1 << 13),
213 };
214
215 void ioapic_init(void);
216 void ioapic_pin_set_vector(unsigned int pin,
217                            enum ioapic_trigger_mode trigger_mode,
218                            unsigned int vector);
219
220 void inmate_main(void);
221
222 void hypercall_init(void);
223
224 void pm_timer_init(void);
225 unsigned long pm_timer_read(void);
226 void delay_us(unsigned long microsecs);
227 unsigned long apic_timer_init(unsigned int vector);
228 void apic_timer_set(unsigned long timeout_ns);
229
230 enum map_type { MAP_CACHED, MAP_UNCACHED };
231
232 void *alloc(unsigned long size, unsigned long align);
233 void map_range(void *start, unsigned long size, enum map_type map_type);
234
235 u32 pci_read_config(u16 bdf, unsigned int addr, unsigned int size);
236 void pci_write_config(u16 bdf, unsigned int addr, u32 value,
237                       unsigned int size);
238 int pci_find_device(u16 vendor, u16 device, u16 start_bdf);
239 int pci_find_cap(u16 bdf, u16 cap);
240 void pci_msi_set_vector(u16 bdf, unsigned int vector);
241 void pci_msix_set_vector(u16 bdf, unsigned int vector, u32 index);
242 #endif