94 throw std::logic_error(
"the secondary controls field doesn't exist");
107 throw std::logic_error(
"cr3 target count > 4");
119 if ((addr_a & 0x0000000000000FFF) != 0)
120 throw std::logic_error(
"io bitmap a addr not page aligned");
122 if ((addr_b & 0x0000000000000FFF) != 0)
123 throw std::logic_error(
"io bitmap b addr not page aligned");
126 throw std::logic_error(
"io bitmap a addr too large");
129 throw std::logic_error(
"io bitmap b addr too large");
140 if ((
addr & 0x0000000000000FFF) != 0)
141 throw std::logic_error(
"msr bitmap addr not page aligned");
144 throw std::logic_error(
"msr bitmap addr too large");
150 using namespace primary_processor_based_vm_execution_controls;
151 using namespace secondary_processor_based_vm_execution_controls;
160 throw std::logic_error(
"virtual apic physical addr is NULL");
162 if ((phys_addr & 0x0000000000000FFFUL) != 0)
163 throw std::logic_error(
"virtual apic addr not 4k aligned");
166 throw std::logic_error(
"virtual apic addr too large");
169 throw std::logic_error(
"tpr_shadow is enabled, but virtual interrupt delivery is enabled");
173 if ((tpr_threshold & 0xFFFFFFF0UL) != 0)
174 throw std::logic_error(
"bits 31:4 of the tpr threshold must be 0");
177 throw std::logic_error(
"tpr_shadow is enabled, but virtual apic is enabled");
179 auto virt_addr =
static_cast<uint8_t *
>(
g_mm->physint_to_virtptr(phys_addr));
181 if (virt_addr ==
nullptr)
182 throw std::logic_error(
"virtual apic virtual addr is NULL");
184 auto virt_addr_span = gsl::span<uint8_t>(virt_addr, 0x81);
185 auto vtpr = virt_addr_span[0x80];
186 auto vtpr_74 = (vtpr & 0xF0U) >> 4;
187 auto tpr_threshold_30 =
static_cast<uint8_t
>(tpr_threshold & 0x0000000FUL);
189 if (tpr_threshold_30 > vtpr_74)
190 throw std::logic_error(
"invalid TPR threshold");
198 throw std::logic_error(
"virtualize_x2apic_mode must be disabled if tpr shadow is disabled");
201 throw std::logic_error(
"apic_register_virtualization must be disabled if tpr shadow is disabled");
204 throw std::logic_error(
"virtual_interrupt_delivery must be disabled if tpr shadow is disabled");
215 throw std::logic_error(
"virtual NMI must be 0 if NMI exiting is 0");
225 throw std::logic_error(
"NMI window exiting must be 0 if virtual NMI is 0");
240 throw std::logic_error(
"apic access physical addr is NULL");
242 if ((phys_addr & 0x0000000000000FFF) != 0)
243 throw std::logic_error(
"apic access addr not 4k aligned");
246 throw std::logic_error(
"apic access addr too large");
259 throw std::logic_error(
"apic accesses must be 0 if x2 apic mode is 1");
272 throw std::logic_error(
"external_interrupt_exiting must be 1 " 273 "if virtual_interrupt_delivery is 1");
283 throw std::logic_error(
"virtual interrupt delivery must be 1 " 284 "if posted interrupts is 1");
287 throw std::logic_error(
"virtual interrupt delivery must be 1 " 288 "if posted interrupts is 1");
291 throw std::logic_error(
"ack interrupt on exit must be 1 " 292 "if posted interrupts is 1");
296 if ((vector & 0x000000000000FF00UL) != 0)
297 throw std::logic_error(
"bits 15:8 of the notification vector must " 298 "be 0 if posted interrupts is 1");
302 if ((
addr & 0x000000000000003FUL) != 0)
303 throw std::logic_error(
"bits 5:0 of the interrupt descriptor addr " 304 "must be 0 if posted interrupts is 1");
307 throw std::logic_error(
"interrupt descriptor addr too large");
320 throw std::logic_error(
"vpid cannot equal 0");
326 using namespace msrs::ia32_vmx_ept_vpid_cap;
327 using namespace vmcs::ept_pointer;
338 throw std::logic_error(
"hardware does not support ept memory type: uncachable");
341 throw std::logic_error(
"hardware does not support ept memory type: write-back");
344 throw std::logic_error(
"unknown eptp memory type");
347 throw std::logic_error(
"the ept walk-through length must be 1 less than 4, i.e. 3");
350 throw std::logic_error(
"hardware does not support dirty / accessed flags for ept");
353 throw std::logic_error(
"bits 11:7 and 63:48 of the eptp must be 0");
368 throw std::logic_error(
"ept must be enabled if pml is enabled");
371 throw std::logic_error(
"pml address must be a valid physical address");
373 if ((pml_addr & 0x0000000000000FFF) != 0)
374 throw std::logic_error(
"bits 11:0 of the pml address must be 0");
387 throw std::logic_error(
"enable ept must be 1 if unrestricted guest is 1");
403 throw std::logic_error(
"unsupported vm function control bit set");
409 throw std::logic_error(
"enable ept must be 1 if eptp switching is 1");
413 if ((eptp_list & 0x0000000000000FFFU) != 0)
414 throw std::logic_error(
"bits 11:0 must be 0 for eptp list address");
417 throw std::logic_error(
"eptp list address addr too large");
432 if ((vmcs_vmread_bitmap_address & 0x0000000000000FFF) != 0)
433 throw std::logic_error(
"bits 11:0 must be 0 for the vmcs read bitmap address");
435 if ((vmcs_vmwrite_bitmap_address & 0x0000000000000FFF) != 0)
436 throw std::logic_error(
"bits 11:0 must be 0 for the vmcs write bitmap address");
439 throw std::logic_error(
"vmcs read bitmap address addr too large");
442 throw std::logic_error(
"vmcs write bitmap address addr too large");
454 auto vmcs_virt_except_info_address =
457 if ((vmcs_virt_except_info_address & 0x0000000000000FFF) != 0)
458 throw std::logic_error(
"bits 11:0 must be 0 for the vmcs virt except info address");
461 throw std::logic_error(
"vmcs virt except info address addr too large");
490 throw std::logic_error(
"save vmx preemption timer must be 0 " 491 "if activate vmx preemption timer is 0");
499 if (msr_store_count == 0)
504 if ((msr_store_addr & 0x000000000000000F) != 0)
505 throw std::logic_error(
"bits 3:0 must be 0 for the exit msr store address");
508 throw std::logic_error(
"exit msr store addr too large");
510 auto msr_store_addr_end = msr_store_addr + (msr_store_count * 16) - 1;
513 throw std::logic_error(
"end of exit msr store area too large");
521 if (msr_load_count == 0)
526 if ((msr_load_addr & 0x000000000000000F) != 0)
527 throw std::logic_error(
"bits 3:0 must be 0 for the exit msr load address");
530 throw std::logic_error(
"exit msr load addr too large");
532 auto msr_load_addr_end = msr_load_addr + (msr_load_count * 16) - 1;
535 throw std::logic_error(
"end of exit msr load area too large");
563 using namespace vm_entry_interruption_information_field;
564 using namespace msrs::ia32_vmx_true_procbased_ctls;
573 throw std::logic_error(
"interrupt information field type of 1 is reserved");
576 throw std::logic_error(
"interrupt information field type of 7 " 577 "is reserved on this hardware");
580 throw std::logic_error(
"interrupt information field vector must be " 581 "2 if the type field is 2 (NMI)");
584 throw std::logic_error(
"interrupt information field vector must be " 585 "at most 31 if the type field is 3 (HE)");
588 throw std::logic_error(
"interrupt information field vector must be " 589 "0 if the type field is 7 (other)");
595 using namespace vm_entry_interruption_information_field;
596 using namespace primary_processor_based_vm_execution_controls;
597 using namespace secondary_processor_based_vm_execution_controls;
608 throw std::logic_error(
"unrestricted guest must be 0 or PE must " 609 "be enabled in cr0 if deliver_error_code_bit is set");
613 throw std::logic_error(
"interrupt information field type must be " 614 "3 if deliver_error_code_bit is set");
629 throw std::logic_error(
"vector must indicate exception that would normally " 630 "deliver an error code if deliver_error_code_bit is set");
634 throw std::logic_error(
"deliver_error_code_bit must be 1");
644 throw std::logic_error(
"reserved bits of the interrupt info field must be 0");
657 throw std::logic_error(
"bits 31:15 of the exception error code field must be 0 " 658 "if deliver error code bit is set in the interrupt info field");
664 using namespace vm_entry_interruption_information_field;
684 throw std::logic_error(
"instruction length must be greater than zero");
686 if (instruction_length > 15)
687 throw std::logic_error(
"instruction length must be in the range of 0-15 if type is 4, 5, 6");
695 if (msr_load_count == 0)
700 if ((msr_load_addr & 0x000000000000000F) != 0)
701 throw std::logic_error(
"bits 3:0 must be 0 for the entry msr load address");
704 throw std::logic_error(
"entry msr load addr too large");
706 auto msr_load_addr_end = msr_load_addr + (msr_load_count * 16) - 1;
709 throw std::logic_error(
"end of entry msr load area too large");
void control_entry_msr_load_address()
constexpr const auto name
constexpr const auto addr
void control_x2apic_mode_and_virtual_apic_access()
constexpr const auto addr
void control_vmx_controls_all()
auto get_if_exists(bool verbose=false) noexcept
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_pin_based_ctls_reserved_properly_set()
constexpr const auto msr_addr
void control_event_injection_reserved_bits_checks()
auto get_if_exists(bool verbose=false) noexcept
void control_process_posted_interrupt_checks()
void control_vm_entry_ctls_reserved_properly_set()
auto is_disabled_if_exists(bool verbose=false) noexcept
auto get_if_exists(bool verbose=false) noexcept
auto get_if_exists(bool verbose=false) noexcept
constexpr const auto name
void control_cr3_count_less_then_4()
constexpr const auto name
auto is_disabled_if_exists(bool verbose=false) noexcept
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_virtual_interrupt_and_external_interrupt()
auto is_physical_address_valid(T addr)
void control_exit_msr_load_address()
auto get_if_exists(bool verbose=false) noexcept
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_virtual_nmi_and_nmi_window()
constexpr const auto addr
void control_enable_ept_checks()
void control_event_injection_instr_length_checks()
constexpr const auto software_interrupt
void control_unrestricted_guests()
void control_proc_based_ctls_reserved_properly_set()
auto is_disabled_if_exists(bool verbose=false) noexcept
constexpr const auto other_event
auto get_if_exists(bool verbose=false) noexcept
constexpr const auto hardware_exception
void control_event_injection_ec_checks()
void control_enable_vm_functions()
void control_enable_vmcs_shadowing()
constexpr const auto addr
constexpr const auto addr
void control_virtual_apic_address_bits()
constexpr const auto software_exception
auto get_if_exists(bool verbose=false) noexcept
void control_vm_entry_control_fields_all()
constexpr const auto write_back
constexpr const auto non_maskable_interrupt
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_exit_msr_store_address()
auto is_enabled_if_exists(bool verbose=false) noexcept
void control_nmi_exiting_and_virtual_nmi()
void control_enable_ept_violation_checks()
constexpr const auto name
constexpr const auto privileged_software_exception
void control_msr_bitmap_address_bits()
constexpr const auto reserved
void control_vpid_checks()
auto is_allowed1() noexcept
void control_proc_based_ctls2_reserved_properly_set()
constexpr const auto uncacheable
void control_io_bitmap_address_bits()
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_tpr_shadow_and_virtual_apic()
void control_vm_execution_control_fields_all()
void control_event_injection_delivery_ec_checks()
constexpr const auto addr
constexpr const auto addr
auto get_if_exists(bool verbose=false) noexcept
auto is_disabled_if_exists(bool verbose=false) noexcept
constexpr const auto name
void control_enable_pml_checks()
constexpr const auto msr_addr
constexpr const auto name
auto is_disabled_if_exists(bool verbose=false) noexcept
void control_activate_and_save_preemption_timer_must_be_0()
void control_vm_exit_ctls_reserved_properly_set()
void control_event_injection_type_vector_checks()
void control_vm_exit_control_fields_all()
auto is_enabled_if_exists(bool verbose=false) noexcept
auto control_reserved_properly_set(MA msr_addr, C ctls, const char *ctls_name)