iPXE
hvm.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2014 Michael Brown <mbrown@fensystems.co.uk>.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License as
6  * published by the Free Software Foundation; either version 2 of the
7  * License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but
10  * WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  * General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17  * 02110-1301, USA.
18  *
19  * You can also choose to distribute this program under the terms of
20  * the Unmodified Binary Distribution Licence (as given in the file
21  * COPYING.UBDL), provided that you have satisfied its requirements.
22  */
23 
24 FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
25 
26 #include <stdint.h>
27 #include <stdio.h>
28 #include <string.h>
29 #include <errno.h>
30 #include <ipxe/malloc.h>
31 #include <ipxe/pci.h>
32 #include <ipxe/cpuid.h>
33 #include <ipxe/msr.h>
34 #include <ipxe/xen.h>
35 #include <ipxe/xenver.h>
36 #include <ipxe/xenmem.h>
37 #include <ipxe/xenstore.h>
38 #include <ipxe/xenbus.h>
39 #include <ipxe/xengrant.h>
40 #include "hvm.h"
41 
42 /** @file
43  *
44  * Xen HVM driver
45  *
46  */
47 
48 /**
49  * Get CPUID base
50  *
51  * @v hvm HVM device
52  * @ret rc Return status code
53  */
54 static int hvm_cpuid_base ( struct hvm_device *hvm ) {
55  struct {
56  uint32_t ebx;
57  uint32_t ecx;
58  uint32_t edx;
59  } __attribute__ (( packed )) signature;
60  uint32_t base;
62  uint32_t discard_eax;
63  uint32_t discard_ebx;
66 
67  /* Scan for magic signature */
68  for ( base = HVM_CPUID_MIN ; base <= HVM_CPUID_MAX ;
69  base += HVM_CPUID_STEP ) {
70  cpuid ( base, 0, &discard_eax, &signature.ebx, &signature.ecx,
71  &signature.edx );
73  sizeof ( signature ) ) == 0 ) {
74  hvm->cpuid_base = base;
75  cpuid ( ( base + HVM_CPUID_VERSION ), 0, &version,
76  &discard_ebx, &discard_ecx, &discard_edx );
77  DBGC2 ( hvm, "HVM using CPUID base %#08x (v%d.%d)\n",
78  base, ( version >> 16 ), ( version & 0xffff ) );
79  return 0;
80  }
81  }
82 
83  DBGC ( hvm, "HVM could not find hypervisor\n" );
84  return -ENODEV;
85 }
86 
87 /**
88  * Map hypercall page(s)
89  *
90  * @v hvm HVM device
91  * @ret rc Return status code
92  */
93 static int hvm_map_hypercall ( struct hvm_device *hvm ) {
94  uint32_t pages;
95  uint32_t msr;
98  physaddr_t hypercall_phys;
101  int xenrc;
102  int rc;
103 
104  /* Get number of hypercall pages and MSR to use */
105  cpuid ( ( hvm->cpuid_base + HVM_CPUID_PAGES ), 0, &pages, &msr,
107 
108  /* Allocate pages */
109  hvm->hypercall_len = ( pages * PAGE_SIZE );
111  if ( ! hvm->xen.hypercall ) {
112  DBGC ( hvm, "HVM could not allocate %d hypercall page(s)\n",
113  pages );
114  return -ENOMEM;
115  }
116  hypercall_phys = virt_to_phys ( hvm->xen.hypercall );
117  DBGC2 ( hvm, "HVM hypercall page(s) at [%#08lx,%#08lx) via MSR %#08x\n",
118  hypercall_phys, ( hypercall_phys + hvm->hypercall_len ), msr );
119 
120  /* Write to MSR */
121  wrmsr ( msr, hypercall_phys );
122 
123  /* Check that hypercall mechanism is working */
124  version = xenver_version ( &hvm->xen );
125  if ( ( xenrc = xenver_extraversion ( &hvm->xen, &extraversion ) ) != 0){
126  rc = -EXEN ( xenrc );
127  DBGC ( hvm, "HVM could not get extraversion: %s\n",
128  strerror ( rc ) );
129  return rc;
130  }
131  DBGC2 ( hvm, "HVM found Xen version %d.%d%s\n",
132  ( version >> 16 ), ( version & 0xffff ) , extraversion );
133 
134  return 0;
135 }
136 
137 /**
138  * Unmap hypercall page(s)
139  *
140  * @v hvm HVM device
141  */
142 static void hvm_unmap_hypercall ( struct hvm_device *hvm ) {
143 
144  /* Free pages */
145  free_phys ( hvm->xen.hypercall, hvm->hypercall_len );
146 }
147 
148 /**
149  * Allocate and map MMIO space
150  *
151  * @v hvm HVM device
152  * @v space Source mapping space
153  * @v len Length (must be a multiple of PAGE_SIZE)
154  * @ret mmio MMIO space address, or NULL on error
155  */
156 static void * hvm_ioremap ( struct hvm_device *hvm, unsigned int space,
157  size_t len ) {
158  struct xen_add_to_physmap add;
160  unsigned int pages = ( len / PAGE_SIZE );
161  physaddr_t mmio_phys;
162  unsigned int i;
163  void *mmio;
164  int xenrc;
165  int rc;
166 
167  /* Sanity check */
168  assert ( ( len % PAGE_SIZE ) == 0 );
169 
170  /* Check for available space */
171  if ( ( hvm->mmio_offset + len ) > hvm->mmio_len ) {
172  DBGC ( hvm, "HVM could not allocate %zd bytes of MMIO space "
173  "(%zd of %zd remaining)\n", len,
174  ( hvm->mmio_len - hvm->mmio_offset ), hvm->mmio_len );
175  goto err_no_space;
176  }
177 
178  /* Map this space */
179  mmio = pci_ioremap ( hvm->pci, ( hvm->mmio + hvm->mmio_offset ), len );
180  if ( ! mmio ) {
181  DBGC ( hvm, "HVM could not map MMIO space [%08lx,%08lx)\n",
182  ( hvm->mmio + hvm->mmio_offset ),
183  ( hvm->mmio + hvm->mmio_offset + len ) );
184  goto err_ioremap;
185  }
186  mmio_phys = virt_to_phys ( mmio );
187 
188  /* Add to physical address space */
189  for ( i = 0 ; i < pages ; i++ ) {
190  add.domid = DOMID_SELF;
191  add.idx = i;
192  add.space = space;
193  add.gpfn = ( ( mmio_phys / PAGE_SIZE ) + i );
194  if ( ( xenrc = xenmem_add_to_physmap ( &hvm->xen, &add ) ) !=0){
195  rc = -EXEN ( xenrc );
196  DBGC ( hvm, "HVM could not add space %d idx %d at "
197  "[%08lx,%08lx): %s\n", space, i,
198  ( mmio_phys + ( i * PAGE_SIZE ) ),
199  ( mmio_phys + ( ( i + 1 ) * PAGE_SIZE ) ),
200  strerror ( rc ) );
201  goto err_add_to_physmap;
202  }
203  }
204 
205  /* Update offset */
206  hvm->mmio_offset += len;
207 
208  return mmio;
209 
210  i = pages;
211  err_add_to_physmap:
212  for ( i-- ; ( signed int ) i >= 0 ; i-- ) {
214  add.gpfn = ( ( mmio_phys / PAGE_SIZE ) + i );
215  xenmem_remove_from_physmap ( &hvm->xen, &remove );
216  }
217  iounmap ( mmio );
218  err_ioremap:
219  err_no_space:
220  return NULL;
221 }
222 
223 /**
224  * Unmap MMIO space
225  *
226  * @v hvm HVM device
227  * @v mmio MMIO space address
228  * @v len Length (must be a multiple of PAGE_SIZE)
229  */
230 static void hvm_iounmap ( struct hvm_device *hvm, void *mmio, size_t len ) {
232  physaddr_t mmio_phys = virt_to_phys ( mmio );
233  unsigned int pages = ( len / PAGE_SIZE );
234  unsigned int i;
235  int xenrc;
236  int rc;
237 
238  /* Unmap this space */
239  iounmap ( mmio );
240 
241  /* Remove from physical address space */
242  for ( i = 0 ; i < pages ; i++ ) {
244  remove.gpfn = ( ( mmio_phys / PAGE_SIZE ) + i );
245  if ( ( xenrc = xenmem_remove_from_physmap ( &hvm->xen,
246  &remove ) ) != 0 ) {
247  rc = -EXEN ( xenrc );
248  DBGC ( hvm, "HVM could not remove space [%08lx,%08lx): "
249  "%s\n", ( mmio_phys + ( i * PAGE_SIZE ) ),
250  ( mmio_phys + ( ( i + 1 ) * PAGE_SIZE ) ),
251  strerror ( rc ) );
252  /* Nothing we can do about this */
253  }
254  }
255 }
256 
257 /**
258  * Map shared info page
259  *
260  * @v hvm HVM device
261  * @ret rc Return status code
262  */
263 static int hvm_map_shared_info ( struct hvm_device *hvm ) {
264  physaddr_t shared_info_phys;
265  int rc;
266 
267  /* Map shared info page */
269  PAGE_SIZE );
270  if ( ! hvm->xen.shared ) {
271  rc = -ENOMEM;
272  goto err_alloc;
273  }
274  shared_info_phys = virt_to_phys ( hvm->xen.shared );
275  DBGC2 ( hvm, "HVM shared info page at [%#08lx,%#08lx)\n",
276  shared_info_phys, ( shared_info_phys + PAGE_SIZE ) );
277 
278  /* Sanity check */
279  DBGC2 ( hvm, "HVM wallclock time is %d\n",
280  readl ( &hvm->xen.shared->wc_sec ) );
281 
282  return 0;
283 
284  hvm_iounmap ( hvm, hvm->xen.shared, PAGE_SIZE );
285  err_alloc:
286  return rc;
287 }
288 
289 /**
290  * Unmap shared info page
291  *
292  * @v hvm HVM device
293  */
294 static void hvm_unmap_shared_info ( struct hvm_device *hvm ) {
295 
296  /* Unmap shared info page */
297  hvm_iounmap ( hvm, hvm->xen.shared, PAGE_SIZE );
298 }
299 
300 /**
301  * Map grant table
302  *
303  * @v hvm HVM device
304  * @ret rc Return status code
305  */
306 static int hvm_map_grant ( struct hvm_device *hvm ) {
307  physaddr_t grant_phys;
308  int rc;
309 
310  /* Initialise grant table */
311  if ( ( rc = xengrant_init ( &hvm->xen ) ) != 0 ) {
312  DBGC ( hvm, "HVM could not initialise grant table: %s\n",
313  strerror ( rc ) );
314  return rc;
315  }
316 
317  /* Map grant table */
319  hvm->xen.grant.len );
320  if ( ! hvm->xen.grant.table )
321  return -ENODEV;
322 
323  grant_phys = virt_to_phys ( hvm->xen.grant.table );
324  DBGC2 ( hvm, "HVM mapped grant table at [%08lx,%08lx)\n",
325  grant_phys, ( grant_phys + hvm->xen.grant.len ) );
326  return 0;
327 }
328 
329 /**
330  * Unmap grant table
331  *
332  * @v hvm HVM device
333  */
334 static void hvm_unmap_grant ( struct hvm_device *hvm ) {
335 
336  /* Unmap grant table */
337  hvm_iounmap ( hvm, hvm->xen.grant.table, hvm->xen.grant.len );
338 }
339 
340 /**
341  * Map XenStore
342  *
343  * @v hvm HVM device
344  * @ret rc Return status code
345  */
346 static int hvm_map_xenstore ( struct hvm_device *hvm ) {
347  uint64_t xenstore_evtchn;
348  uint64_t xenstore_pfn;
349  physaddr_t xenstore_phys;
350  char *name;
351  int xenrc;
352  int rc;
353 
354  /* Get XenStore event channel */
355  if ( ( xenrc = xen_hvm_get_param ( &hvm->xen, HVM_PARAM_STORE_EVTCHN,
356  &xenstore_evtchn ) ) != 0 ) {
357  rc = -EXEN ( xenrc );
358  DBGC ( hvm, "HVM could not get XenStore event channel: %s\n",
359  strerror ( rc ) );
360  return rc;
361  }
362  hvm->xen.store.port = xenstore_evtchn;
363 
364  /* Get XenStore PFN */
365  if ( ( xenrc = xen_hvm_get_param ( &hvm->xen, HVM_PARAM_STORE_PFN,
366  &xenstore_pfn ) ) != 0 ) {
367  rc = -EXEN ( xenrc );
368  DBGC ( hvm, "HVM could not get XenStore PFN: %s\n",
369  strerror ( rc ) );
370  return rc;
371  }
372  xenstore_phys = ( xenstore_pfn * PAGE_SIZE );
373 
374  /* Map XenStore */
375  hvm->xen.store.intf = pci_ioremap ( hvm->pci, xenstore_phys,
376  PAGE_SIZE );
377  if ( ! hvm->xen.store.intf ) {
378  DBGC ( hvm, "HVM could not map XenStore at [%08lx,%08lx)\n",
379  xenstore_phys, ( xenstore_phys + PAGE_SIZE ) );
380  return -ENODEV;
381  }
382  DBGC2 ( hvm, "HVM mapped XenStore at [%08lx,%08lx) with event port "
383  "%d\n", xenstore_phys, ( xenstore_phys + PAGE_SIZE ),
384  hvm->xen.store.port );
385 
386  /* Check that XenStore is working */
387  if ( ( rc = xenstore_read ( &hvm->xen, &name, "name", NULL ) ) != 0 ) {
388  DBGC ( hvm, "HVM could not read domain name: %s\n",
389  strerror ( rc ) );
390  return rc;
391  }
392  DBGC2 ( hvm, "HVM running in domain \"%s\"\n", name );
393  free ( name );
394 
395  return 0;
396 }
397 
398 /**
399  * Unmap XenStore
400  *
401  * @v hvm HVM device
402  */
403 static void hvm_unmap_xenstore ( struct hvm_device *hvm ) {
404 
405  /* Unmap XenStore */
406  iounmap ( hvm->xen.store.intf );
407 }
408 
409 /**
410  * Probe PCI device
411  *
412  * @v pci PCI device
413  * @ret rc Return status code
414  */
415 static int hvm_probe ( struct pci_device *pci ) {
416  struct hvm_device *hvm;
417  int rc;
418 
419  /* Allocate and initialise structure */
420  hvm = zalloc ( sizeof ( *hvm ) );
421  if ( ! hvm ) {
422  rc = -ENOMEM;
423  goto err_alloc;
424  }
425  hvm->pci = pci;
426  hvm->mmio = pci_bar_start ( pci, HVM_MMIO_BAR );
428  DBGC2 ( hvm, "HVM has MMIO space [%08lx,%08lx)\n",
429  hvm->mmio, ( hvm->mmio + hvm->mmio_len ) );
430 
431  /* Fix up PCI device */
433 
434  /* Attach to hypervisor */
435  if ( ( rc = hvm_cpuid_base ( hvm ) ) != 0 )
436  goto err_cpuid_base;
437  if ( ( rc = hvm_map_hypercall ( hvm ) ) != 0 )
438  goto err_map_hypercall;
439  if ( ( rc = hvm_map_shared_info ( hvm ) ) != 0 )
440  goto err_map_shared_info;
441  if ( ( rc = hvm_map_grant ( hvm ) ) != 0 )
442  goto err_map_grant;
443  if ( ( rc = hvm_map_xenstore ( hvm ) ) != 0 )
444  goto err_map_xenstore;
445 
446  /* Probe Xen devices */
447  if ( ( rc = xenbus_probe ( &hvm->xen, &pci->dev ) ) != 0 ) {
448  DBGC ( hvm, "HVM could not probe Xen bus: %s\n",
449  strerror ( rc ) );
450  goto err_xenbus_probe;
451  }
452 
453  pci_set_drvdata ( pci, hvm );
454  return 0;
455 
456  xenbus_remove ( &hvm->xen, &pci->dev );
457  err_xenbus_probe:
458  hvm_unmap_xenstore ( hvm );
459  err_map_xenstore:
460  hvm_unmap_grant ( hvm );
461  err_map_grant:
462  hvm_unmap_shared_info ( hvm );
463  err_map_shared_info:
464  hvm_unmap_hypercall ( hvm );
465  err_map_hypercall:
466  err_cpuid_base:
467  free ( hvm );
468  err_alloc:
469  return rc;
470 }
471 
472 /**
473  * Remove PCI device
474  *
475  * @v pci PCI device
476  */
477 static void hvm_remove ( struct pci_device *pci ) {
478  struct hvm_device *hvm = pci_get_drvdata ( pci );
479 
480  xenbus_remove ( &hvm->xen, &pci->dev );
481  hvm_unmap_xenstore ( hvm );
482  hvm_unmap_grant ( hvm );
483  hvm_unmap_shared_info ( hvm );
484  hvm_unmap_hypercall ( hvm );
485  free ( hvm );
486 }
487 
488 /** PCI device IDs */
489 static struct pci_device_id hvm_ids[] = {
490  PCI_ROM ( 0x5853, 0x0001, "hvm", "hvm", 0 ),
491  PCI_ROM ( 0x5853, 0x0002, "hvm2", "hvm2", 0 ),
492 };
493 
494 /** PCI driver */
495 struct pci_driver hvm_driver __pci_driver = {
496  .ids = hvm_ids,
497  .id_count = ( sizeof ( hvm_ids ) / sizeof ( hvm_ids[0] ) ),
498  .probe = hvm_probe,
499  .remove = hvm_remove,
500 };
501 
502 /* Drag in objects via hvm_driver */
503 REQUIRING_SYMBOL ( hvm_driver );
504 
505 /* Drag in netfront driver */
506 REQUIRE_OBJECT ( netfront );
int xengrant_init(struct xen_hypervisor *xen)
Initialise grant table.
Definition: xengrant.c:70
size_t mmio_offset
Current offset within MMIO address space.
Definition: hvm.h:51
#define __attribute__(x)
Definition: compiler.h:10
uint32_t base
Base.
Definition: librm.h:138
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
const char * name
Definition: ath9k_hw.c:1984
Xen memory operations.
static xen_extraversion_t * extraversion
Definition: xenver.h:37
#define HVM_CPUID_VERSION
Get Xen version.
Definition: hvm.h:30
uint32_t wc_sec
Definition: xen.h:776
static struct xen_add_to_physmap * add
Definition: xenmem.h:24
A PCI driver.
Definition: pci.h:251
static int xen_hvm_get_param(struct xen_hypervisor *xen, unsigned int index, uint64_t *value)
Get HVM parameter value.
Definition: hvm.h:64
static void hvm_unmap_hypercall(struct hvm_device *hvm)
Unmap hypercall page(s)
Definition: hvm.c:142
xen_ulong_t idx
Definition: memory.h:242
Error codes.
static void hvm_remove(struct pci_device *pci)
Remove PCI device.
Definition: hvm.c:477
static struct pci_device_id hvm_ids[]
PCI device IDs.
Definition: hvm.c:489
struct pci_device_id * ids
PCI ID table.
Definition: pci.h:253
struct xen_hypervisor xen
Xen hypervisor.
Definition: hvm.h:41
#define HVM_PARAM_STORE_EVTCHN
Definition: params.h:80
#define HVM_PARAM_STORE_PFN
Definition: params.h:79
uint32_t readl(volatile uint32_t *io_addr)
Read 32-bit dword from memory-mapped device.
#define DBGC(...)
Definition: compiler.h:505
unsigned long pci_bar_size(struct pci_device *pci, unsigned int reg)
Get the size of a PCI BAR.
Definition: pci.c:163
#define HVM_CPUID_MAGIC
Magic signature.
Definition: hvm.h:27
#define HVM_CPUID_MIN
Minimum CPUID base.
Definition: hvm.h:18
unsigned long long uint64_t
Definition: stdint.h:13
int xenstore_read(struct xen_hypervisor *xen, char **value,...)
Read XenStore value.
Definition: xenstore.c:371
#define PAGE_SIZE
Page size.
Definition: io.h:27
void adjust_pci_device(struct pci_device *pci)
Enable PCI device.
Definition: pci.c:240
struct device dev
Generic device.
Definition: pci.h:212
#define HVM_MMIO_BAR
PCI MMIO BAR.
Definition: hvm.h:36
#define EXEN(xenrc)
Convert a Xen status code to an iPXE status code.
Definition: xen.h:86
Dynamic memory allocation.
int xenbus_probe(struct xen_hypervisor *xen, struct device *parent)
Probe Xen bus.
Definition: xenbus.c:354
Xen interface.
xen_pfn_t gpfn
Definition: memory.h:245
REQUIRE_OBJECT(netfront)
static void pci_set_drvdata(struct pci_device *pci, void *priv)
Set PCI driver-private data.
Definition: pci.h:365
#define ENOMEM
Not enough space.
Definition: errno.h:534
u32 version
Driver version.
Definition: ath9k_hw.c:1983
static uint32_t uint32_t uint32_t * ebx
Definition: cpuid.h:89
struct shared_info * shared
Shared info page.
Definition: xen.h:54
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
ring len
Length.
Definition: dwmac.h:231
struct pci_driver hvm_driver __pci_driver
PCI driver.
Definition: hvm.c:495
unsigned long pci_bar_start(struct pci_device *pci, unsigned int reg)
Find the start of a PCI BAR.
Definition: pci.c:96
static void hvm_unmap_xenstore(struct hvm_device *hvm)
Unmap XenStore.
Definition: hvm.c:403
static int hvm_map_shared_info(struct hvm_device *hvm)
Map shared info page.
Definition: hvm.c:263
struct grant_entry_v1 * table
Grant table entries.
Definition: xen.h:30
uint32_t discard_edx
Definition: hyperv.h:32
struct xen_hypercall * hypercall
Hypercall table.
Definition: xen.h:52
FILE_LICENCE(GPL2_OR_LATER_OR_UBDL)
static int hvm_cpuid_base(struct hvm_device *hvm)
Get CPUID base.
Definition: hvm.c:54
unsigned int space
Definition: memory.h:237
static int hvm_probe(struct pci_device *pci)
Probe PCI device.
Definition: hvm.c:415
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
static uint32_t uint32_t uint32_t uint32_t * ecx
Definition: cpuid.h:89
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:54
x86 CPU feature detection
void * zalloc(size_t size)
Allocate cleared memory.
Definition: malloc.c:661
static int hvm_map_hypercall(struct hvm_device *hvm)
Map hypercall page(s)
Definition: hvm.c:93
size_t hypercall_len
Length of hypercall table.
Definition: hvm.h:47
Xen device bus.
PCI bus.
unsigned long mmio
MMIO base address.
Definition: hvm.h:49
A PCI device.
Definition: pci.h:210
A Xen HVM device.
Definition: hvm.h:39
evtchn_port_t port
Event channel.
Definition: xen.h:46
static uint32_t uint32_t uint32_t uint32_t uint32_t * edx
Definition: cpuid.h:90
#define ENODEV
No such device.
Definition: errno.h:509
#define XENMAPSPACE_grant_table
Definition: memory.h:212
static int hvm_map_xenstore(struct hvm_device *hvm)
Map XenStore.
Definition: hvm.c:346
#define HVM_CPUID_STEP
Increment between CPUID bases.
Definition: hvm.h:24
uint32_t discard_ecx
Definition: hyperv.h:31
domid_t domid
Definition: memory.h:232
static void hvm_iounmap(struct hvm_device *hvm, void *mmio, size_t len)
Unmap MMIO space.
Definition: hvm.c:230
A PCI device ID list entry.
Definition: pci.h:174
unsigned int uint32_t
Definition: stdint.h:12
size_t mmio_len
Length of MMIO address space.
Definition: hvm.h:53
static void hvm_unmap_grant(struct hvm_device *hvm)
Unmap grant table.
Definition: hvm.c:334
Xen HVM driver.
char xen_extraversion_t[16]
Definition: version.h:26
Xen version.
static struct xen_remove_from_physmap * remove
Definition: xenmem.h:39
unsigned long physaddr_t
Definition: stdint.h:20
static void * hvm_ioremap(struct hvm_device *hvm, unsigned int space, size_t len)
Allocate and map MMIO space.
Definition: hvm.c:156
static void * pci_get_drvdata(struct pci_device *pci)
Get PCI driver-private data.
Definition: pci.h:375
#define XENMAPSPACE_shared_info
Definition: memory.h:211
struct xenstore_domain_interface * intf
XenStore domain interface.
Definition: xen.h:44
#define DBGC2(...)
Definition: compiler.h:522
int(* probe)(struct pci_device *pci)
Probe device.
Definition: pci.h:264
struct xen_grant grant
Grant table.
Definition: xen.h:56
void free_phys(void *ptr, size_t size)
Free memory allocated with malloc_phys()
Definition: malloc.c:722
#define DOMID_SELF
Definition: xen.h:567
void iounmap(volatile const void *io_addr)
Unmap I/O address.
struct xen_store store
XenStore.
Definition: xen.h:58
void xenbus_remove(struct xen_hypervisor *xen __unused, struct device *parent)
Remove Xen bus.
Definition: xenbus.c:391
static int hvm_map_grant(struct hvm_device *hvm)
Map grant table.
Definition: hvm.c:306
size_t len
Total grant table length.
Definition: xen.h:32
#define HVM_CPUID_MAX
Maximum CPUID base.
Definition: hvm.h:21
Xen grant tables.
void * pci_ioremap(struct pci_device *pci, unsigned long bus_addr, size_t len)
Map PCI bus address as an I/O address.
static void hvm_unmap_shared_info(struct hvm_device *hvm)
Unmap shared info page.
Definition: hvm.c:294
u8 signature
CPU signature.
Definition: CIB_PRM.h:35
#define HVM_CPUID_PAGES
Get number of hypercall pages.
Definition: hvm.h:33
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
Definition: string.c:114
XenStore interface.
#define NULL
NULL pointer (VOID *)
Definition: Base.h:321
String functions.
#define PCI_ROM(_vendor, _device, _name, _description, _data)
Definition: pci.h:307
REQUIRING_SYMBOL(hvm_driver)
struct pci_device * pci
PCI device.
Definition: hvm.h:43
uint32_t cpuid_base
CPUID base.
Definition: hvm.h:45
Model-specific registers.
void * malloc_phys(size_t size, size_t phys_align)
Allocate memory with specified physical alignment.
Definition: malloc.c:706