summaryrefslogtreecommitdiffstats
path: root/sys/amd64/vmm/vmm.c
diff options
context:
space:
mode:
authorneel <neel@FreeBSD.org>2013-11-25 19:04:51 +0000
committerneel <neel@FreeBSD.org>2013-11-25 19:04:51 +0000
commit89dbc92028f9ab8548675d88e47f08f520ecde12 (patch)
tree5d29fe534d31ddc45fa2bf63ae3f535aec050003 /sys/amd64/vmm/vmm.c
parent2f61636cf871204be51aed93531356162b74c261 (diff)
downloadFreeBSD-src-89dbc92028f9ab8548675d88e47f08f520ecde12.zip
FreeBSD-src-89dbc92028f9ab8548675d88e47f08f520ecde12.tar.gz
Add HPET device emulation to bhyve.
bhyve supports a single timer block with 8 timers. The timers are all 32-bit and capable of being operated in periodic mode. All timers support interrupt delivery using MSI. Timers 0 and 1 also support legacy interrupt routing. At the moment the timers are not connected to any ioapic pins but that will be addressed in a subsequent commit. This change is based on a patch from Tycho Nightingale (tycho.nightingale@pluribusnetworks.com).
Diffstat (limited to 'sys/amd64/vmm/vmm.c')
-rw-r--r--sys/amd64/vmm/vmm.c20
1 files changed, 17 insertions, 3 deletions
diff --git a/sys/amd64/vmm/vmm.c b/sys/amd64/vmm/vmm.c
index 40254c6..3e52a8e 100644
--- a/sys/amd64/vmm/vmm.c
+++ b/sys/amd64/vmm/vmm.c
@@ -65,6 +65,7 @@ __FBSDID("$FreeBSD$");
#include "vmm_host.h"
#include "vmm_mem.h"
#include "vmm_util.h"
+#include "vhpet.h"
#include "vioapic.h"
#include "vlapic.h"
#include "vmm_msr.h"
@@ -108,6 +109,7 @@ struct mem_seg {
struct vm {
void *cookie; /* processor-specific data */
void *iommu; /* iommu-specific data */
+ struct vhpet *vhpet; /* virtual HPET */
struct vioapic *vioapic; /* virtual ioapic */
struct vmspace *vmspace; /* guest's address space */
struct vcpu vcpu[VM_MAXCPU];
@@ -304,6 +306,7 @@ vm_create(const char *name, struct vm **retvm)
strcpy(vm->name, name);
vm->cookie = VMINIT(vm, vmspace_pmap(vmspace));
vm->vioapic = vioapic_init(vm);
+ vm->vhpet = vhpet_init(vm);
for (i = 0; i < VM_MAXCPU; i++) {
vcpu_init(vm, i);
@@ -337,6 +340,9 @@ vm_destroy(struct vm *vm)
if (vm->iommu != NULL)
iommu_destroy_domain(vm->iommu);
+ vhpet_cleanup(vm->vhpet);
+ vioapic_cleanup(vm->vioapic);
+
for (i = 0; i < vm->num_mem_segs; i++)
vm_free_mem_seg(vm, &vm->mem_segs[i]);
@@ -345,8 +351,6 @@ vm_destroy(struct vm *vm)
for (i = 0; i < VM_MAXCPU; i++)
vcpu_cleanup(&vm->vcpu[i]);
- vioapic_cleanup(vm->vioapic);
-
VMSPACE_FREE(vm->vmspace);
VMCLEANUP(vm->cookie);
@@ -967,13 +971,16 @@ vm_handle_inst_emul(struct vm *vm, int vcpuid, boolean_t *retu)
if (vmm_decode_instruction(vm, vcpuid, gla, vie) != 0)
return (EFAULT);
- /* return to userland unless this is a local apic access */
+ /* return to userland unless this is an in-kernel emulated device */
if (gpa >= DEFAULT_APIC_BASE && gpa < DEFAULT_APIC_BASE + PAGE_SIZE) {
mread = lapic_mmio_read;
mwrite = lapic_mmio_write;
} else if (gpa >= VIOAPIC_BASE && gpa < VIOAPIC_BASE + VIOAPIC_SIZE) {
mread = vioapic_mmio_read;
mwrite = vioapic_mmio_write;
+ } else if (gpa >= VHPET_BASE && gpa < VHPET_BASE + VHPET_SIZE) {
+ mread = vhpet_mmio_read;
+ mwrite = vhpet_mmio_write;
} else {
*retu = TRUE;
return (0);
@@ -1169,6 +1176,13 @@ vm_ioapic(struct vm *vm)
return (vm->vioapic);
}
+struct vhpet *
+vm_hpet(struct vm *vm)
+{
+
+ return (vm->vhpet);
+}
+
boolean_t
vmm_is_pptdev(int bus, int slot, int func)
{
OpenPOWER on IntegriCloud