Framework

Hypervisor

Build virtualization solutions on top of a lightweight hypervisor, without the need for third-party kernel extensions.

Overview

The Hypervisor framework provides C APIs for interacting with virtualization technologies in user-space, without the need for writing kernel extensions (KEXTs). As a result, apps created using this framework are suitable for distribution on the Mac App Store.

Hardware-facilitated virtual machines (VMs) and virtual processors (vCPUs) can be created and controlled by an entitled sandboxed user space process, the hypervisor client. The Hypervisor framework abstracts virtual machines as tasks and virtual processors as threads.

Requirements

The Hypervisor framework has the following requirements:

Entitlements

A sandboxed user space process must have the com.apple.vm.hypervisor entitlement in order to use Hypervisor APIs.

Supported Hardware

Generally, machines with an Intel VT-x feature set that includes Extended Page Tables (EPT) and Unrestricted Mode are supported. You can determine the availability of Hypervisor APIs on a particular machine at runtime with the sysctl(8) command, passing kern.hv_support as an argument.

Example VM Life Cycle

The following figure illustrates a simplified life cycle of creating and running a virtual machine with one or more virtual CPUs using the Hypervisor Framework API.

Symbols

Creating and Destroying VM Instances

func hv_vm_create(hv_vm_options_t)

Creates a VM instance for the current task.

func hv_vm_destroy()

Destroys the VM instance associated with the current task.

Managing Memory Regions

func hv_vm_map(hv_uvaddr_t!, hv_gpaddr_t, Int, hv_memory_flags_t)

Maps a region in the virtual address space of the current task into the guest physical address space of the VM.

func hv_vm_unmap(hv_gpaddr_t, Int)

Unmaps a region in the guest physical address space of the VM.

func hv_vm_protect(hv_gpaddr_t, Int, hv_memory_flags_t)

Modifies the permissions of a region in the guest physical address space of the VM.

Creating and Managing vCPU Instances

func hv_vcpu_destroy(hv_vcpuid_t)

Destroys the vCPU instance associated with the current thread.

func hv_vcpu_interrupt(Unsafe​Mutable​Pointer<hv_vcpuid_t>!, UInt32)

Forces an immediate VMEXIT of a set of vCPU instances of the VM.

func hv_vcpu_invalidate_tlb(hv_vcpuid_t)

Invalidates the translation look-aside buffer (TLB) of a vCPU.

func hv_vcpu_flush(hv_vcpuid_t)

Flushes the cached state of a vCPU.

func hv_vcpu_enable_native_msr(hv_vcpuid_t, UInt32, Bool)

Enables or disables a machine specific register (MSR) to be used natively by the VM.

func hv_vcpu_get_exec_time(hv_vcpuid_t, Unsafe​Mutable​Pointer<UInt64>!)

Returns, by reference, the cumulative execution time of a vCPU, in nanoseconds.

Managing Timestamp-Counters (TSC)

func hv_vm_sync_tsc(UInt64)

Synchronizes guest timestamp-counters (TSC) across all vCPUs.

Accessing Registers

func hv_vcpu_read_register(hv_vcpuid_t, hv_x86_reg_t, Unsafe​Mutable​Pointer<UInt64>!)

Returns, by reference, the current value of an architectural x86 register of a vCPU.

func hv_vcpu_write_register(hv_vcpuid_t, hv_x86_reg_t, UInt64)

Sets the value of an architectural x86 register of a vCPU.

Accessing Floating Point (FP) State

func hv_vcpu_read_fpstate(hv_vcpuid_t, Unsafe​Mutable​Raw​Pointer!, Int)

Returns, by reference, the current architectural x86 floating point and SIMD state of a vCPU.

func hv_vcpu_write_fpstate(hv_vcpuid_t, Unsafe​Mutable​Raw​Pointer!, Int)

Sets the architectural x86 floating point and SIMD state of a vCPU.

Accessing Machine Specific Registers (MSRs)

func hv_vcpu_read_msr(hv_vcpuid_t, UInt32, Unsafe​Mutable​Pointer<UInt64>!)

Returns, by reference, the current value of a machine specific register (MSR) of a vCPU.

func hv_vcpu_write_msr(hv_vcpuid_t, UInt32, UInt64)

Sets the value of an machine specific register (MSR) of a vCPU.

Managing Virtual Machine Control Structure (VMCS)

func hv_vmx_vcpu_read_vmcs(hv_vcpuid_t, UInt32, Unsafe​Mutable​Pointer<UInt64>!)

Returns, by reference, the current value of a virtual machine control structure (VMCS) field of a vCPU.

func hv_vmx_vcpu_write_vmcs(hv_vcpuid_t, UInt32, UInt64)

Sets the value of a virtual machine control structure (VMCS) field of a vCPU.

func hv_vmx_read_capability(hv_vmx_capability_t, Unsafe​Mutable​Pointer<UInt64>!)

Returns, by reference, the VMX virtualization capabilities of the host processor.

func hv_vmx_vcpu_set_apic_address(hv_vcpuid_t, hv_gpaddr_t)

Sets the address of the guest APIC for a vCPU in the guest physical address space of the VM.

Data Types

hv_return_t

The return type for Hypervisor Framework functions.

hv_vm_options_t

Options for the hv_vm_create(_:​) function.

hv_memory_flags_t

Guest physical memory region permissions for the hv_vm_map(_:​_:​_:​_:​) and hv_vm_protect(_:​_:​_:​) functions.

hv_x86_reg_t

x86 architectural register IDs.

hv_vmx_capability_t

VMX capability field IDs.

hv_vcpuid_t

Type of a vCPU ID.

hv_uvaddr_t

Type of a user virtual address.

hv_gpaddr_t

Type of a guest physical address (GPA).