1 /* SPDX-License-Identifier: GPL-2.0 */ 2 /* 3 * Type definitions for the Microsoft hypervisor. 4 */ 5 #ifndef _HV_HVHDK_H 6 #define _HV_HVHDK_H 7 8 #include <linux/build_bug.h> 9 10 #include "hvhdk_mini.h" 11 #include "hvgdk.h" 12 13 /* 14 * Hypervisor statistics page format 15 */ 16 struct hv_stats_page { 17 u64 data[HV_HYP_PAGE_SIZE / sizeof(u64)]; 18 } __packed; 19 20 /* Bits for dirty mask of hv_vp_register_page */ 21 #define HV_X64_REGISTER_CLASS_GENERAL 0 22 #define HV_X64_REGISTER_CLASS_IP 1 23 #define HV_X64_REGISTER_CLASS_XMM 2 24 #define HV_X64_REGISTER_CLASS_SEGMENT 3 25 #define HV_X64_REGISTER_CLASS_FLAGS 4 26 27 #define HV_VP_REGISTER_PAGE_VERSION_1 1u 28 29 #define HV_VP_REGISTER_PAGE_MAX_VECTOR_COUNT 7 30 31 union hv_vp_register_page_interrupt_vectors { 32 u64 as_uint64; 33 struct { 34 u8 vector_count; 35 u8 vector[HV_VP_REGISTER_PAGE_MAX_VECTOR_COUNT]; 36 } __packed; 37 }; 38 39 struct hv_vp_register_page { 40 u16 version; 41 u8 isvalid; 42 u8 rsvdz; 43 u32 dirty; 44 45 #if IS_ENABLED(CONFIG_X86) 46 47 union { 48 struct { 49 /* General purpose registers 50 * (HV_X64_REGISTER_CLASS_GENERAL) 51 */ 52 union { 53 struct { 54 u64 rax; 55 u64 rcx; 56 u64 rdx; 57 u64 rbx; 58 u64 rsp; 59 u64 rbp; 60 u64 rsi; 61 u64 rdi; 62 u64 r8; 63 u64 r9; 64 u64 r10; 65 u64 r11; 66 u64 r12; 67 u64 r13; 68 u64 r14; 69 u64 r15; 70 } __packed; 71 72 u64 gp_registers[16]; 73 }; 74 /* Instruction pointer (HV_X64_REGISTER_CLASS_IP) */ 75 u64 rip; 76 /* Flags (HV_X64_REGISTER_CLASS_FLAGS) */ 77 u64 rflags; 78 } __packed; 79 80 u64 registers[18]; 81 }; 82 u8 reserved[8]; 83 /* Volatile XMM registers (HV_X64_REGISTER_CLASS_XMM) */ 84 union { 85 struct { 86 struct hv_u128 xmm0; 87 struct hv_u128 xmm1; 88 struct hv_u128 xmm2; 89 struct hv_u128 xmm3; 90 struct hv_u128 xmm4; 91 struct hv_u128 xmm5; 92 } __packed; 93 94 struct hv_u128 xmm_registers[6]; 95 }; 96 /* Segment registers (HV_X64_REGISTER_CLASS_SEGMENT) */ 97 union { 98 struct { 99 struct hv_x64_segment_register es; 100 struct hv_x64_segment_register cs; 101 struct hv_x64_segment_register ss; 102 struct hv_x64_segment_register ds; 103 struct hv_x64_segment_register fs; 104 struct hv_x64_segment_register gs; 105 } __packed; 106 107 struct hv_x64_segment_register segment_registers[6]; 108 }; 109 /* Misc. control registers (cannot be set via this interface) */ 110 u64 cr0; 111 u64 cr3; 112 u64 cr4; 113 u64 cr8; 114 u64 efer; 115 u64 dr7; 116 union hv_x64_pending_interruption_register pending_interruption; 117 union hv_x64_interrupt_state_register interrupt_state; 118 u64 instruction_emulation_hints; 119 u64 xfem; 120 121 /* 122 * Fields from this point are not included in the register page save chunk. 123 * The reserved field is intended to maintain alignment for unsaved fields. 124 */ 125 u8 reserved1[0x100]; 126 127 /* 128 * Interrupts injected as part of HvCallDispatchVp. 129 */ 130 union hv_vp_register_page_interrupt_vectors interrupt_vectors; 131 132 #elif IS_ENABLED(CONFIG_ARM64) 133 /* Not yet supported in ARM */ 134 #endif 135 } __packed; 136 137 #define HV_PARTITION_PROCESSOR_FEATURES_BANKS 2 138 139 union hv_partition_processor_features { 140 u64 as_uint64[HV_PARTITION_PROCESSOR_FEATURES_BANKS]; 141 struct { 142 u64 sse3_support : 1; 143 u64 lahf_sahf_support : 1; 144 u64 ssse3_support : 1; 145 u64 sse4_1_support : 1; 146 u64 sse4_2_support : 1; 147 u64 sse4a_support : 1; 148 u64 xop_support : 1; 149 u64 pop_cnt_support : 1; 150 u64 cmpxchg16b_support : 1; 151 u64 altmovcr8_support : 1; 152 u64 lzcnt_support : 1; 153 u64 mis_align_sse_support : 1; 154 u64 mmx_ext_support : 1; 155 u64 amd3dnow_support : 1; 156 u64 extended_amd3dnow_support : 1; 157 u64 page_1gb_support : 1; 158 u64 aes_support : 1; 159 u64 pclmulqdq_support : 1; 160 u64 pcid_support : 1; 161 u64 fma4_support : 1; 162 u64 f16c_support : 1; 163 u64 rd_rand_support : 1; 164 u64 rd_wr_fs_gs_support : 1; 165 u64 smep_support : 1; 166 u64 enhanced_fast_string_support : 1; 167 u64 bmi1_support : 1; 168 u64 bmi2_support : 1; 169 u64 hle_support_deprecated : 1; 170 u64 rtm_support_deprecated : 1; 171 u64 movbe_support : 1; 172 u64 npiep1_support : 1; 173 u64 dep_x87_fpu_save_support : 1; 174 u64 rd_seed_support : 1; 175 u64 adx_support : 1; 176 u64 intel_prefetch_support : 1; 177 u64 smap_support : 1; 178 u64 hle_support : 1; 179 u64 rtm_support : 1; 180 u64 rdtscp_support : 1; 181 u64 clflushopt_support : 1; 182 u64 clwb_support : 1; 183 u64 sha_support : 1; 184 u64 x87_pointers_saved_support : 1; 185 u64 invpcid_support : 1; 186 u64 ibrs_support : 1; 187 u64 stibp_support : 1; 188 u64 ibpb_support: 1; 189 u64 unrestricted_guest_support : 1; 190 u64 mdd_support : 1; 191 u64 fast_short_rep_mov_support : 1; 192 u64 l1dcache_flush_support : 1; 193 u64 rdcl_no_support : 1; 194 u64 ibrs_all_support : 1; 195 u64 skip_l1df_support : 1; 196 u64 ssb_no_support : 1; 197 u64 rsb_a_no_support : 1; 198 u64 virt_spec_ctrl_support : 1; 199 u64 rd_pid_support : 1; 200 u64 umip_support : 1; 201 u64 mbs_no_support : 1; 202 u64 mb_clear_support : 1; 203 u64 taa_no_support : 1; 204 u64 tsx_ctrl_support : 1; 205 /* 206 * N.B. The final processor feature bit in bank 0 is reserved to 207 * simplify potential downlevel backports. 208 */ 209 u64 reserved_bank0 : 1; 210 211 /* N.B. Begin bank 1 processor features. */ 212 u64 acount_mcount_support : 1; 213 u64 tsc_invariant_support : 1; 214 u64 cl_zero_support : 1; 215 u64 rdpru_support : 1; 216 u64 la57_support : 1; 217 u64 mbec_support : 1; 218 u64 nested_virt_support : 1; 219 u64 psfd_support : 1; 220 u64 cet_ss_support : 1; 221 u64 cet_ibt_support : 1; 222 u64 vmx_exception_inject_support : 1; 223 u64 enqcmd_support : 1; 224 u64 umwait_tpause_support : 1; 225 u64 movdiri_support : 1; 226 u64 movdir64b_support : 1; 227 u64 cldemote_support : 1; 228 u64 serialize_support : 1; 229 u64 tsc_deadline_tmr_support : 1; 230 u64 tsc_adjust_support : 1; 231 u64 fzlrep_movsb : 1; 232 u64 fsrep_stosb : 1; 233 u64 fsrep_cmpsb : 1; 234 u64 reserved_bank1 : 42; 235 } __packed; 236 }; 237 238 union hv_partition_processor_xsave_features { 239 struct { 240 u64 xsave_support : 1; 241 u64 xsaveopt_support : 1; 242 u64 avx_support : 1; 243 u64 reserved1 : 61; 244 } __packed; 245 u64 as_uint64; 246 }; 247 248 struct hv_partition_creation_properties { 249 union hv_partition_processor_features disabled_processor_features; 250 union hv_partition_processor_xsave_features 251 disabled_processor_xsave_features; 252 } __packed; 253 254 #define HV_PARTITION_SYNTHETIC_PROCESSOR_FEATURES_BANKS 1 255 256 union hv_partition_synthetic_processor_features { 257 u64 as_uint64[HV_PARTITION_SYNTHETIC_PROCESSOR_FEATURES_BANKS]; 258 259 struct { 260 u64 hypervisor_present : 1; 261 /* Support for HV#1: (CPUID leaves 0x40000000 - 0x40000006)*/ 262 u64 hv1 : 1; 263 u64 access_vp_run_time_reg : 1; /* HV_X64_MSR_VP_RUNTIME */ 264 u64 access_partition_reference_counter : 1; /* HV_X64_MSR_TIME_REF_COUNT */ 265 u64 access_synic_regs : 1; /* SINT-related registers */ 266 /* 267 * Access to HV_X64_MSR_STIMER0_CONFIG through 268 * HV_X64_MSR_STIMER3_COUNT. 269 */ 270 u64 access_synthetic_timer_regs : 1; 271 u64 access_intr_ctrl_regs : 1; /* APIC MSRs and VP assist page*/ 272 /* HV_X64_MSR_GUEST_OS_ID and HV_X64_MSR_HYPERCALL */ 273 u64 access_hypercall_regs : 1; 274 u64 access_vp_index : 1; 275 u64 access_partition_reference_tsc : 1; 276 u64 access_guest_idle_reg : 1; 277 u64 access_frequency_regs : 1; 278 u64 reserved_z12 : 1; 279 u64 reserved_z13 : 1; 280 u64 reserved_z14 : 1; 281 u64 enable_extended_gva_ranges_for_flush_virtual_address_list : 1; 282 u64 reserved_z16 : 1; 283 u64 reserved_z17 : 1; 284 /* Use fast hypercall output. Corresponds to privilege. */ 285 u64 fast_hypercall_output : 1; 286 u64 reserved_z19 : 1; 287 u64 start_virtual_processor : 1; /* Can start VPs */ 288 u64 reserved_z21 : 1; 289 /* Synthetic timers in direct mode. */ 290 u64 direct_synthetic_timers : 1; 291 u64 reserved_z23 : 1; 292 u64 extended_processor_masks : 1; 293 294 /* Enable various hypercalls */ 295 u64 tb_flush_hypercalls : 1; 296 u64 synthetic_cluster_ipi : 1; 297 u64 notify_long_spin_wait : 1; 298 u64 query_numa_distance : 1; 299 u64 signal_events : 1; 300 u64 retarget_device_interrupt : 1; 301 u64 restore_time : 1; 302 303 /* EnlightenedVmcs nested enlightenment is supported. */ 304 u64 enlightened_vmcs : 1; 305 u64 reserved : 31; 306 } __packed; 307 }; 308 309 #define HV_MAKE_COMPATIBILITY_VERSION(major_, minor_) \ 310 ((u32)((major_) << 8 | (minor_))) 311 312 #define HV_COMPATIBILITY_21_H2 HV_MAKE_COMPATIBILITY_VERSION(0X6, 0X9) 313 314 union hv_partition_isolation_properties { 315 u64 as_uint64; 316 struct { 317 u64 isolation_type: 5; 318 u64 isolation_host_type : 2; 319 u64 rsvd_z: 5; 320 u64 shared_gpa_boundary_page_number: 52; 321 } __packed; 322 }; 323 324 /* 325 * Various isolation types supported by MSHV. 326 */ 327 #define HV_PARTITION_ISOLATION_TYPE_NONE 0 328 #define HV_PARTITION_ISOLATION_TYPE_SNP 2 329 #define HV_PARTITION_ISOLATION_TYPE_TDX 3 330 331 /* 332 * Various host isolation types supported by MSHV. 333 */ 334 #define HV_PARTITION_ISOLATION_HOST_TYPE_NONE 0x0 335 #define HV_PARTITION_ISOLATION_HOST_TYPE_HARDWARE 0x1 336 #define HV_PARTITION_ISOLATION_HOST_TYPE_RESERVED 0x2 337 338 /* Note: Exo partition is enabled by default */ 339 #define HV_PARTITION_CREATION_FLAG_SMT_ENABLED_GUEST BIT(0) 340 #define HV_PARTITION_CREATION_FLAG_NESTED_VIRTUALIZATION_CAPABLE BIT(1) 341 #define HV_PARTITION_CREATION_FLAG_GPA_SUPER_PAGES_ENABLED BIT(4) 342 #define HV_PARTITION_CREATION_FLAG_EXO_PARTITION BIT(8) 343 #define HV_PARTITION_CREATION_FLAG_LAPIC_ENABLED BIT(13) 344 #define HV_PARTITION_CREATION_FLAG_INTERCEPT_MESSAGE_PAGE_ENABLED BIT(19) 345 #define HV_PARTITION_CREATION_FLAG_X2APIC_CAPABLE BIT(22) 346 347 struct hv_input_create_partition { 348 u64 flags; 349 struct hv_proximity_domain_info proximity_domain_info; 350 u32 compatibility_version; 351 u32 padding; 352 struct hv_partition_creation_properties partition_creation_properties; 353 union hv_partition_isolation_properties isolation_properties; 354 } __packed; 355 356 struct hv_output_create_partition { 357 u64 partition_id; 358 } __packed; 359 360 struct hv_input_initialize_partition { 361 u64 partition_id; 362 } __packed; 363 364 struct hv_input_finalize_partition { 365 u64 partition_id; 366 } __packed; 367 368 struct hv_input_delete_partition { 369 u64 partition_id; 370 } __packed; 371 372 struct hv_input_get_partition_property { 373 u64 partition_id; 374 u32 property_code; /* enum hv_partition_property_code */ 375 u32 padding; 376 } __packed; 377 378 struct hv_output_get_partition_property { 379 u64 property_value; 380 } __packed; 381 382 struct hv_input_set_partition_property { 383 u64 partition_id; 384 u32 property_code; /* enum hv_partition_property_code */ 385 u32 padding; 386 u64 property_value; 387 } __packed; 388 389 union hv_partition_property_arg { 390 u64 as_uint64; 391 struct { 392 union { 393 u32 arg; 394 u32 vp_index; 395 }; 396 u16 reserved0; 397 u8 reserved1; 398 u8 object_type; 399 } __packed; 400 }; 401 402 struct hv_input_get_partition_property_ex { 403 u64 partition_id; 404 u32 property_code; /* enum hv_partition_property_code */ 405 u32 padding; 406 union { 407 union hv_partition_property_arg arg_data; 408 u64 arg; 409 }; 410 } __packed; 411 412 /* 413 * NOTE: Should use hv_input_set_partition_property_ex_header to compute this 414 * size, but hv_input_get_partition_property_ex is identical so it suffices 415 */ 416 #define HV_PARTITION_PROPERTY_EX_MAX_VAR_SIZE \ 417 (HV_HYP_PAGE_SIZE - sizeof(struct hv_input_get_partition_property_ex)) 418 419 union hv_partition_property_ex { 420 u8 buffer[HV_PARTITION_PROPERTY_EX_MAX_VAR_SIZE]; 421 struct hv_partition_property_vmm_capabilities vmm_capabilities; 422 /* More fields to be filled in when needed */ 423 }; 424 425 struct hv_output_get_partition_property_ex { 426 union hv_partition_property_ex property_value; 427 } __packed; 428 429 enum hv_vp_state_page_type { 430 HV_VP_STATE_PAGE_REGISTERS = 0, 431 HV_VP_STATE_PAGE_INTERCEPT_MESSAGE = 1, 432 HV_VP_STATE_PAGE_GHCB = 2, 433 HV_VP_STATE_PAGE_COUNT 434 }; 435 436 struct hv_input_map_vp_state_page { 437 u64 partition_id; 438 u32 vp_index; 439 u16 type; /* enum hv_vp_state_page_type */ 440 union hv_input_vtl input_vtl; 441 union { 442 u8 as_uint8; 443 struct { 444 u8 map_location_provided : 1; 445 u8 reserved : 7; 446 }; 447 } flags; 448 u64 requested_map_location; 449 } __packed; 450 451 struct hv_output_map_vp_state_page { 452 u64 map_location; /* GPA page number */ 453 } __packed; 454 455 struct hv_input_unmap_vp_state_page { 456 u64 partition_id; 457 u32 vp_index; 458 u16 type; /* enum hv_vp_state_page_type */ 459 union hv_input_vtl input_vtl; 460 u8 reserved0; 461 } __packed; 462 463 struct hv_x64_apic_eoi_message { 464 u32 vp_index; 465 u32 interrupt_vector; 466 } __packed; 467 468 struct hv_opaque_intercept_message { 469 u32 vp_index; 470 } __packed; 471 472 enum hv_port_type { 473 HV_PORT_TYPE_MESSAGE = 1, 474 HV_PORT_TYPE_EVENT = 2, 475 HV_PORT_TYPE_MONITOR = 3, 476 HV_PORT_TYPE_DOORBELL = 4 /* Root Partition only */ 477 }; 478 479 struct hv_port_info { 480 u32 port_type; /* enum hv_port_type */ 481 u32 padding; 482 union { 483 struct { 484 u32 target_sint; 485 u32 target_vp; 486 u64 rsvdz; 487 } message_port_info; 488 struct { 489 u32 target_sint; 490 u32 target_vp; 491 u16 base_flag_number; 492 u16 flag_count; 493 u32 rsvdz; 494 } event_port_info; 495 struct { 496 u64 monitor_address; 497 u64 rsvdz; 498 } monitor_port_info; 499 struct { 500 u32 target_sint; 501 u32 target_vp; 502 u64 rsvdz; 503 } doorbell_port_info; 504 }; 505 } __packed; 506 507 struct hv_connection_info { 508 u32 port_type; 509 u32 padding; 510 union { 511 struct { 512 u64 rsvdz; 513 } message_connection_info; 514 struct { 515 u64 rsvdz; 516 } event_connection_info; 517 struct { 518 u64 monitor_address; 519 } monitor_connection_info; 520 struct { 521 u64 gpa; 522 u64 trigger_value; 523 u64 flags; 524 } doorbell_connection_info; 525 }; 526 } __packed; 527 528 /* Define synthetic interrupt controller flag constants. */ 529 #define HV_EVENT_FLAGS_COUNT (256 * 8) 530 #define HV_EVENT_FLAGS_BYTE_COUNT (256) 531 #define HV_EVENT_FLAGS32_COUNT (256 / sizeof(u32)) 532 533 /* linux side we create long version of flags to use long bit ops on flags */ 534 #define HV_EVENT_FLAGS_UL_COUNT (256 / sizeof(ulong)) 535 536 /* Define the synthetic interrupt controller event flags format. */ 537 union hv_synic_event_flags { 538 unsigned char flags8[HV_EVENT_FLAGS_BYTE_COUNT]; 539 u32 flags32[HV_EVENT_FLAGS32_COUNT]; 540 ulong flags[HV_EVENT_FLAGS_UL_COUNT]; /* linux only */ 541 }; 542 543 struct hv_synic_event_flags_page { 544 volatile union hv_synic_event_flags event_flags[HV_SYNIC_SINT_COUNT]; 545 }; 546 547 #define HV_SYNIC_EVENT_RING_MESSAGE_COUNT 63 548 549 struct hv_synic_event_ring { 550 u8 signal_masked; 551 u8 ring_full; 552 u16 reserved_z; 553 u32 data[HV_SYNIC_EVENT_RING_MESSAGE_COUNT]; 554 } __packed; 555 556 struct hv_synic_event_ring_page { 557 struct hv_synic_event_ring sint_event_ring[HV_SYNIC_SINT_COUNT]; 558 }; 559 560 /* Define SynIC control register. */ 561 union hv_synic_scontrol { 562 u64 as_uint64; 563 struct { 564 u64 enable : 1; 565 u64 reserved : 63; 566 } __packed; 567 }; 568 569 /* Define the format of the SIEFP register */ 570 union hv_synic_siefp { 571 u64 as_uint64; 572 struct { 573 u64 siefp_enabled : 1; 574 u64 preserved : 11; 575 u64 base_siefp_gpa : 52; 576 } __packed; 577 }; 578 579 union hv_synic_sirbp { 580 u64 as_uint64; 581 struct { 582 u64 sirbp_enabled : 1; 583 u64 preserved : 11; 584 u64 base_sirbp_gpa : 52; 585 } __packed; 586 }; 587 588 union hv_interrupt_control { 589 u64 as_uint64; 590 struct { 591 u32 interrupt_type; /* enum hv_interrupt_type */ 592 #if IS_ENABLED(CONFIG_X86) 593 u32 level_triggered : 1; 594 u32 logical_dest_mode : 1; 595 u32 rsvd : 30; 596 #elif IS_ENABLED(CONFIG_ARM64) 597 u32 rsvd1 : 2; 598 u32 asserted : 1; 599 u32 rsvd2 : 29; 600 #endif 601 } __packed; 602 }; 603 604 struct hv_stimer_state { 605 struct { 606 u32 undelivered_msg_pending : 1; 607 u32 reserved : 31; 608 } __packed flags; 609 u32 resvd; 610 u64 config; 611 u64 count; 612 u64 adjustment; 613 u64 undelivered_exp_time; 614 } __packed; 615 616 struct hv_synthetic_timers_state { 617 struct hv_stimer_state timers[HV_SYNIC_STIMER_COUNT]; 618 u64 reserved[5]; 619 } __packed; 620 621 struct hv_async_completion_message_payload { 622 u64 partition_id; 623 u32 status; 624 u32 completion_count; 625 u64 sub_status; 626 } __packed; 627 628 union hv_input_delete_vp { 629 u64 as_uint64[2]; 630 struct { 631 u64 partition_id; 632 u32 vp_index; 633 u8 reserved[4]; 634 } __packed; 635 } __packed; 636 637 struct hv_input_assert_virtual_interrupt { 638 u64 partition_id; 639 union hv_interrupt_control control; 640 u64 dest_addr; /* cpu's apic id */ 641 u32 vector; 642 u8 target_vtl; 643 u8 rsvd_z0; 644 u16 rsvd_z1; 645 } __packed; 646 647 struct hv_input_create_port { 648 u64 port_partition_id; 649 union hv_port_id port_id; 650 u8 port_vtl; 651 u8 min_connection_vtl; 652 u16 padding; 653 u64 connection_partition_id; 654 struct hv_port_info port_info; 655 struct hv_proximity_domain_info proximity_domain_info; 656 } __packed; 657 658 union hv_input_delete_port { 659 u64 as_uint64[2]; 660 struct { 661 u64 port_partition_id; 662 union hv_port_id port_id; 663 u32 reserved; 664 }; 665 } __packed; 666 667 struct hv_input_connect_port { 668 u64 connection_partition_id; 669 union hv_connection_id connection_id; 670 u8 connection_vtl; 671 u8 rsvdz0; 672 u16 rsvdz1; 673 u64 port_partition_id; 674 union hv_port_id port_id; 675 u32 reserved2; 676 struct hv_connection_info connection_info; 677 struct hv_proximity_domain_info proximity_domain_info; 678 } __packed; 679 680 union hv_input_disconnect_port { 681 u64 as_uint64[2]; 682 struct { 683 u64 connection_partition_id; 684 union hv_connection_id connection_id; 685 u32 is_doorbell: 1; 686 u32 reserved: 31; 687 } __packed; 688 } __packed; 689 690 union hv_input_notify_port_ring_empty { 691 u64 as_uint64; 692 struct { 693 u32 sint_index; 694 u32 reserved; 695 }; 696 } __packed; 697 698 struct hv_vp_state_data_xsave { 699 u64 flags; 700 union hv_x64_xsave_xfem_register states; 701 } __packed; 702 703 /* 704 * For getting and setting VP state, there are two options based on the state type: 705 * 706 * 1.) Data that is accessed by PFNs in the input hypercall page. This is used 707 * for state which may not fit into the hypercall pages. 708 * 2.) Data that is accessed directly in the input\output hypercall pages. 709 * This is used for state that will always fit into the hypercall pages. 710 * 711 * In the future this could be dynamic based on the size if needed. 712 * 713 * Note these hypercalls have an 8-byte aligned variable header size as per the tlfs 714 */ 715 716 #define HV_GET_SET_VP_STATE_TYPE_PFN BIT(31) 717 718 enum hv_get_set_vp_state_type { 719 /* HvGetSetVpStateLocalInterruptControllerState - APIC/GIC state */ 720 HV_GET_SET_VP_STATE_LAPIC_STATE = 0 | HV_GET_SET_VP_STATE_TYPE_PFN, 721 HV_GET_SET_VP_STATE_XSAVE = 1 | HV_GET_SET_VP_STATE_TYPE_PFN, 722 HV_GET_SET_VP_STATE_SIM_PAGE = 2 | HV_GET_SET_VP_STATE_TYPE_PFN, 723 HV_GET_SET_VP_STATE_SIEF_PAGE = 3 | HV_GET_SET_VP_STATE_TYPE_PFN, 724 HV_GET_SET_VP_STATE_SYNTHETIC_TIMERS = 4, 725 }; 726 727 struct hv_vp_state_data { 728 u32 type; 729 u32 rsvd; 730 struct hv_vp_state_data_xsave xsave; 731 } __packed; 732 733 struct hv_input_get_vp_state { 734 u64 partition_id; 735 u32 vp_index; 736 u8 input_vtl; 737 u8 rsvd0; 738 u16 rsvd1; 739 struct hv_vp_state_data state_data; 740 u64 output_data_pfns[]; 741 } __packed; 742 743 union hv_output_get_vp_state { 744 struct hv_synthetic_timers_state synthetic_timers_state; 745 } __packed; 746 747 union hv_input_set_vp_state_data { 748 u64 pfns; 749 u8 bytes; 750 } __packed; 751 752 struct hv_input_set_vp_state { 753 u64 partition_id; 754 u32 vp_index; 755 u8 input_vtl; 756 u8 rsvd0; 757 u16 rsvd1; 758 struct hv_vp_state_data state_data; 759 union hv_input_set_vp_state_data data[]; 760 } __packed; 761 762 union hv_x64_vp_execution_state { 763 u16 as_uint16; 764 struct { 765 u16 cpl:2; 766 u16 cr0_pe:1; 767 u16 cr0_am:1; 768 u16 efer_lma:1; 769 u16 debug_active:1; 770 u16 interruption_pending:1; 771 u16 vtl:4; 772 u16 enclave_mode:1; 773 u16 interrupt_shadow:1; 774 u16 virtualization_fault_active:1; 775 u16 reserved:2; 776 } __packed; 777 }; 778 779 struct hv_x64_intercept_message_header { 780 u32 vp_index; 781 u8 instruction_length:4; 782 u8 cr8:4; /* Only set for exo partitions */ 783 u8 intercept_access_type; /* enum hv_intercept_access_type */ 784 union hv_x64_vp_execution_state execution_state; 785 struct hv_x64_segment_register cs_segment; 786 u64 rip; 787 u64 rflags; 788 } __packed; 789 790 union hv_x64_memory_access_info { 791 u8 as_uint8; 792 struct { 793 u8 gva_valid:1; 794 u8 gva_gpa_valid:1; 795 u8 hypercall_output_pending:1; 796 u8 tlb_locked_no_overlay:1; 797 u8 reserved:4; 798 } __packed; 799 }; 800 801 struct hv_x64_memory_intercept_message { 802 struct hv_x64_intercept_message_header header; 803 u32 cache_type; /* enum hv_cache_type */ 804 u8 instruction_byte_count; 805 union hv_x64_memory_access_info memory_access_info; 806 u8 tpr_priority; 807 u8 reserved1; 808 u64 guest_virtual_address; 809 u64 guest_physical_address; 810 u8 instruction_bytes[16]; 811 } __packed; 812 813 #if IS_ENABLED(CONFIG_ARM64) 814 union hv_arm64_vp_execution_state { 815 u16 as_uint16; 816 struct { 817 u16 cpl:2; /* Exception Level (EL) */ 818 u16 debug_active:1; 819 u16 interruption_pending:1; 820 u16 vtl:4; 821 u16 virtualization_fault_active:1; 822 u16 reserved:7; 823 } __packed; 824 }; 825 826 struct hv_arm64_intercept_message_header { 827 u32 vp_index; 828 u8 instruction_length; 829 u8 intercept_access_type; /* enum hv_intercept_access_type */ 830 union hv_arm64_vp_execution_state execution_state; 831 u64 pc; 832 u64 cpsr; 833 } __packed; 834 835 union hv_arm64_memory_access_info { 836 u8 as_uint8; 837 struct { 838 u8 gva_valid:1; 839 u8 gva_gpa_valid:1; 840 u8 hypercall_output_pending:1; 841 u8 reserved:5; 842 } __packed; 843 }; 844 845 struct hv_arm64_memory_intercept_message { 846 struct hv_arm64_intercept_message_header header; 847 u32 cache_type; /* enum hv_cache_type */ 848 u8 instruction_byte_count; 849 union hv_arm64_memory_access_info memory_access_info; 850 u16 reserved1; 851 u8 instruction_bytes[4]; 852 u32 reserved2; 853 u64 guest_virtual_address; 854 u64 guest_physical_address; 855 u64 syndrome; 856 } __packed; 857 858 #endif /* CONFIG_ARM64 */ 859 860 /* 861 * Dispatch state for the VP communicated by the hypervisor to the 862 * VP-dispatching thread in the root on return from HVCALL_DISPATCH_VP. 863 */ 864 enum hv_vp_dispatch_state { 865 HV_VP_DISPATCH_STATE_INVALID = 0, 866 HV_VP_DISPATCH_STATE_BLOCKED = 1, 867 HV_VP_DISPATCH_STATE_READY = 2, 868 }; 869 870 /* 871 * Dispatch event that caused the current dispatch state on return from 872 * HVCALL_DISPATCH_VP. 873 */ 874 enum hv_vp_dispatch_event { 875 HV_VP_DISPATCH_EVENT_INVALID = 0x00000000, 876 HV_VP_DISPATCH_EVENT_SUSPEND = 0x00000001, 877 HV_VP_DISPATCH_EVENT_INTERCEPT = 0x00000002, 878 }; 879 880 #define HV_ROOT_SCHEDULER_MAX_VPS_PER_CHILD_PARTITION 1024 881 /* The maximum array size of HV_GENERIC_SET (vp_set) buffer */ 882 #define HV_GENERIC_SET_QWORD_COUNT(max) (((((max) - 1) >> 6) + 1) + 2) 883 884 struct hv_vp_signal_bitset_scheduler_message { 885 u64 partition_id; 886 u32 overflow_count; 887 u16 vp_count; 888 u16 reserved; 889 890 #define BITSET_BUFFER_SIZE \ 891 HV_GENERIC_SET_QWORD_COUNT(HV_ROOT_SCHEDULER_MAX_VPS_PER_CHILD_PARTITION) 892 union { 893 struct hv_vpset bitset; 894 u64 bitset_buffer[BITSET_BUFFER_SIZE]; 895 } vp_bitset; 896 #undef BITSET_BUFFER_SIZE 897 } __packed; 898 899 static_assert(sizeof(struct hv_vp_signal_bitset_scheduler_message) <= 900 (sizeof(struct hv_message) - sizeof(struct hv_message_header))); 901 902 #define HV_MESSAGE_MAX_PARTITION_VP_PAIR_COUNT \ 903 (((sizeof(struct hv_message) - sizeof(struct hv_message_header)) / \ 904 (sizeof(u64 /* partition id */) + sizeof(u32 /* vp index */))) - 1) 905 906 struct hv_vp_signal_pair_scheduler_message { 907 u32 overflow_count; 908 u8 vp_count; 909 u8 reserved1[3]; 910 911 u64 partition_ids[HV_MESSAGE_MAX_PARTITION_VP_PAIR_COUNT]; 912 u32 vp_indexes[HV_MESSAGE_MAX_PARTITION_VP_PAIR_COUNT]; 913 914 u8 reserved2[4]; 915 } __packed; 916 917 static_assert(sizeof(struct hv_vp_signal_pair_scheduler_message) == 918 (sizeof(struct hv_message) - sizeof(struct hv_message_header))); 919 920 /* Input and output structures for HVCALL_DISPATCH_VP */ 921 #define HV_DISPATCH_VP_FLAG_CLEAR_INTERCEPT_SUSPEND 0x1 922 #define HV_DISPATCH_VP_FLAG_ENABLE_CALLER_INTERRUPTS 0x2 923 #define HV_DISPATCH_VP_FLAG_SET_CALLER_SPEC_CTRL 0x4 924 #define HV_DISPATCH_VP_FLAG_SKIP_VP_SPEC_FLUSH 0x8 925 #define HV_DISPATCH_VP_FLAG_SKIP_CALLER_SPEC_FLUSH 0x10 926 #define HV_DISPATCH_VP_FLAG_SKIP_CALLER_USER_SPEC_FLUSH 0x20 927 #define HV_DISPATCH_VP_FLAG_SCAN_INTERRUPT_INJECTION 0x40 928 929 struct hv_input_dispatch_vp { 930 u64 partition_id; 931 u32 vp_index; 932 u32 flags; 933 u64 time_slice; /* in 100ns */ 934 u64 spec_ctrl; 935 } __packed; 936 937 struct hv_output_dispatch_vp { 938 u32 dispatch_state; /* enum hv_vp_dispatch_state */ 939 u32 dispatch_event; /* enum hv_vp_dispatch_event */ 940 } __packed; 941 942 struct hv_input_modify_sparse_spa_page_host_access { 943 u32 host_access : 2; 944 u32 reserved : 30; 945 u32 flags; 946 u64 partition_id; 947 u64 spa_page_list[]; 948 } __packed; 949 950 /* hv_input_modify_sparse_spa_page_host_access flags */ 951 #define HV_MODIFY_SPA_PAGE_HOST_ACCESS_MAKE_EXCLUSIVE 0x1 952 #define HV_MODIFY_SPA_PAGE_HOST_ACCESS_MAKE_SHARED 0x2 953 #define HV_MODIFY_SPA_PAGE_HOST_ACCESS_LARGE_PAGE 0x4 954 #define HV_MODIFY_SPA_PAGE_HOST_ACCESS_HUGE_PAGE 0x8 955 956 #endif /* _HV_HVHDK_H */ 957