1 /* SPDX-License-Identifier: GPL-2.0 */ 2 /* 3 * Type definitions for the Microsoft Hypervisor. 4 */ 5 #ifndef _HV_HVHDK_MINI_H 6 #define _HV_HVHDK_MINI_H 7 8 #include "hvgdk_mini.h" 9 10 /* 11 * Doorbell connection_info flags. 12 */ 13 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_MASK 0x00000007 14 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_ANY 0x00000000 15 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_BYTE 0x00000001 16 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_WORD 0x00000002 17 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_DWORD 0x00000003 18 #define HV_DOORBELL_FLAG_TRIGGER_SIZE_QWORD 0x00000004 19 #define HV_DOORBELL_FLAG_TRIGGER_ANY_VALUE 0x80000000 20 21 /* Each generic set contains 64 elements */ 22 #define HV_GENERIC_SET_SHIFT (6) 23 #define HV_GENERIC_SET_MASK (63) 24 25 enum hv_generic_set_format { 26 HV_GENERIC_SET_SPARSE_4K, 27 HV_GENERIC_SET_ALL, 28 }; 29 #define HV_GENERIC_SET_FORMAT hv_generic_set_format 30 31 enum hv_scheduler_type { 32 HV_SCHEDULER_TYPE_LP = 1, /* Classic scheduler w/o SMT */ 33 HV_SCHEDULER_TYPE_LP_SMT = 2, /* Classic scheduler w/ SMT */ 34 HV_SCHEDULER_TYPE_CORE_SMT = 3, /* Core scheduler */ 35 HV_SCHEDULER_TYPE_ROOT = 4, /* Root / integrated scheduler */ 36 HV_SCHEDULER_TYPE_MAX 37 }; 38 39 /* HV_STATS_AREA_TYPE */ 40 enum hv_stats_area_type { 41 HV_STATS_AREA_SELF = 0, 42 HV_STATS_AREA_PARENT = 1, 43 HV_STATS_AREA_INTERNAL = 2, 44 HV_STATS_AREA_COUNT 45 }; 46 47 enum hv_stats_object_type { 48 HV_STATS_OBJECT_HYPERVISOR = 0x00000001, 49 HV_STATS_OBJECT_LOGICAL_PROCESSOR = 0x00000002, 50 HV_STATS_OBJECT_PARTITION = 0x00010001, 51 HV_STATS_OBJECT_VP = 0x00010002 52 }; 53 54 union hv_stats_object_identity { 55 /* hv_stats_hypervisor */ 56 struct { 57 u8 reserved[15]; 58 u8 stats_area_type; 59 } __packed hv; 60 61 /* hv_stats_logical_processor */ 62 struct { 63 u32 lp_index; 64 u8 reserved[11]; 65 u8 stats_area_type; 66 } __packed lp; 67 68 /* hv_stats_partition */ 69 struct { 70 u64 partition_id; 71 u8 reserved[7]; 72 u8 stats_area_type; 73 } __packed partition; 74 75 /* hv_stats_vp */ 76 struct { 77 u64 partition_id; 78 u32 vp_index; 79 u16 flags; 80 u8 reserved; 81 u8 stats_area_type; 82 } __packed vp; 83 }; 84 85 enum hv_partition_property_code { 86 /* Privilege properties */ 87 HV_PARTITION_PROPERTY_PRIVILEGE_FLAGS = 0x00010000, 88 HV_PARTITION_PROPERTY_SYNTHETIC_PROC_FEATURES = 0x00010001, 89 90 /* Resource properties */ 91 HV_PARTITION_PROPERTY_GPA_PAGE_ACCESS_TRACKING = 0x00050005, 92 HV_PARTITION_PROPERTY_UNIMPLEMENTED_MSR_ACTION = 0x00050017, 93 94 /* Compatibility properties */ 95 HV_PARTITION_PROPERTY_PROCESSOR_XSAVE_FEATURES = 0x00060002, 96 HV_PARTITION_PROPERTY_XSAVE_STATES = 0x00060007, 97 HV_PARTITION_PROPERTY_MAX_XSAVE_DATA_SIZE = 0x00060008, 98 HV_PARTITION_PROPERTY_PROCESSOR_CLOCK_FREQUENCY = 0x00060009, 99 100 /* Extended properties with larger property values */ 101 HV_PARTITION_PROPERTY_VMM_CAPABILITIES = 0x00090007, 102 }; 103 104 #define HV_PARTITION_VMM_CAPABILITIES_BANK_COUNT 1 105 #define HV_PARTITION_VMM_CAPABILITIES_RESERVED_BITFIELD_COUNT 59 106 107 struct hv_partition_property_vmm_capabilities { 108 u16 bank_count; 109 u16 reserved[3]; 110 union { 111 u64 as_uint64[HV_PARTITION_VMM_CAPABILITIES_BANK_COUNT]; 112 struct { 113 u64 map_gpa_preserve_adjustable: 1; 114 u64 vmm_can_provide_overlay_gpfn: 1; 115 u64 vp_affinity_property: 1; 116 #if IS_ENABLED(CONFIG_ARM64) 117 u64 vmm_can_provide_gic_overlay_locations: 1; 118 #else 119 u64 reservedbit3: 1; 120 #endif 121 u64 assignable_synthetic_proc_features: 1; 122 u64 reserved0: HV_PARTITION_VMM_CAPABILITIES_RESERVED_BITFIELD_COUNT; 123 } __packed; 124 }; 125 } __packed; 126 127 enum hv_snp_status { 128 HV_SNP_STATUS_NONE = 0, 129 HV_SNP_STATUS_AVAILABLE = 1, 130 HV_SNP_STATUS_INCOMPATIBLE = 2, 131 HV_SNP_STATUS_PSP_UNAVAILABLE = 3, 132 HV_SNP_STATUS_PSP_INIT_FAILED = 4, 133 HV_SNP_STATUS_PSP_BAD_FW_VERSION = 5, 134 HV_SNP_STATUS_BAD_CONFIGURATION = 6, 135 HV_SNP_STATUS_PSP_FW_UPDATE_IN_PROGRESS = 7, 136 HV_SNP_STATUS_PSP_RB_INIT_FAILED = 8, 137 HV_SNP_STATUS_PSP_PLATFORM_STATUS_FAILED = 9, 138 HV_SNP_STATUS_PSP_INIT_LATE_FAILED = 10, 139 }; 140 141 enum hv_system_property { 142 /* Add more values when needed */ 143 HV_SYSTEM_PROPERTY_SCHEDULER_TYPE = 15, 144 HV_DYNAMIC_PROCESSOR_FEATURE_PROPERTY = 21, 145 }; 146 147 enum hv_dynamic_processor_feature_property { 148 /* Add more values when needed */ 149 HV_X64_DYNAMIC_PROCESSOR_FEATURE_MAX_ENCRYPTED_PARTITIONS = 13, 150 HV_X64_DYNAMIC_PROCESSOR_FEATURE_SNP_STATUS = 16, 151 }; 152 153 struct hv_input_get_system_property { 154 u32 property_id; /* enum hv_system_property */ 155 union { 156 u32 as_uint32; 157 #if IS_ENABLED(CONFIG_X86) 158 /* enum hv_dynamic_processor_feature_property */ 159 u32 hv_processor_feature; 160 #endif 161 /* More fields to be filled in when needed */ 162 }; 163 } __packed; 164 165 struct hv_output_get_system_property { 166 union { 167 u32 scheduler_type; /* enum hv_scheduler_type */ 168 #if IS_ENABLED(CONFIG_X86) 169 u64 hv_processor_feature_value; 170 #endif 171 }; 172 } __packed; 173 174 struct hv_input_map_stats_page { 175 u32 type; /* enum hv_stats_object_type */ 176 u32 padding; 177 union hv_stats_object_identity identity; 178 } __packed; 179 180 struct hv_input_map_stats_page2 { 181 u32 type; /* enum hv_stats_object_type */ 182 u32 padding; 183 union hv_stats_object_identity identity; 184 u64 map_location; 185 } __packed; 186 187 struct hv_output_map_stats_page { 188 u64 map_location; 189 } __packed; 190 191 struct hv_input_unmap_stats_page { 192 u32 type; /* enum hv_stats_object_type */ 193 u32 padding; 194 union hv_stats_object_identity identity; 195 } __packed; 196 197 struct hv_proximity_domain_flags { 198 u32 proximity_preferred : 1; 199 u32 reserved : 30; 200 u32 proximity_info_valid : 1; 201 } __packed; 202 203 struct hv_proximity_domain_info { 204 u32 domain_id; 205 struct hv_proximity_domain_flags flags; 206 } __packed; 207 208 /* HvDepositMemory hypercall */ 209 struct hv_deposit_memory { /* HV_INPUT_DEPOSIT_MEMORY */ 210 u64 partition_id; 211 u64 gpa_page_list[]; 212 } __packed; 213 214 struct hv_input_withdraw_memory { 215 u64 partition_id; 216 struct hv_proximity_domain_info proximity_domain_info; 217 } __packed; 218 219 struct hv_output_withdraw_memory { 220 DECLARE_FLEX_ARRAY(u64, gpa_page_list); 221 } __packed; 222 223 /* HV Map GPA (Guest Physical Address) Flags */ 224 #define HV_MAP_GPA_PERMISSIONS_NONE 0x0 225 #define HV_MAP_GPA_READABLE 0x1 226 #define HV_MAP_GPA_WRITABLE 0x2 227 #define HV_MAP_GPA_KERNEL_EXECUTABLE 0x4 228 #define HV_MAP_GPA_USER_EXECUTABLE 0x8 229 #define HV_MAP_GPA_EXECUTABLE 0xC 230 #define HV_MAP_GPA_PERMISSIONS_MASK 0xF 231 #define HV_MAP_GPA_ADJUSTABLE 0x8000 232 #define HV_MAP_GPA_NO_ACCESS 0x10000 233 #define HV_MAP_GPA_NOT_CACHED 0x200000 234 #define HV_MAP_GPA_LARGE_PAGE 0x80000000 235 236 struct hv_input_map_gpa_pages { 237 u64 target_partition_id; 238 u64 target_gpa_base; 239 u32 map_flags; 240 u32 padding; 241 u64 source_gpa_page_list[]; 242 } __packed; 243 244 union hv_gpa_page_access_state_flags { 245 struct { 246 u64 clear_accessed : 1; 247 u64 set_accessed : 1; 248 u64 clear_dirty : 1; 249 u64 set_dirty : 1; 250 u64 reserved : 60; 251 } __packed; 252 u64 as_uint64; 253 }; 254 255 struct hv_input_get_gpa_pages_access_state { 256 u64 partition_id; 257 union hv_gpa_page_access_state_flags flags; 258 u64 hv_gpa_page_number; 259 } __packed; 260 261 union hv_gpa_page_access_state { 262 struct { 263 u8 accessed : 1; 264 u8 dirty : 1; 265 u8 reserved: 6; 266 }; 267 u8 as_uint8; 268 } __packed; 269 270 struct hv_lp_startup_status { 271 u64 hv_status; 272 u64 substatus1; 273 u64 substatus2; 274 u64 substatus3; 275 u64 substatus4; 276 u64 substatus5; 277 u64 substatus6; 278 } __packed; 279 280 struct hv_input_add_logical_processor { 281 u32 lp_index; 282 u32 apic_id; 283 struct hv_proximity_domain_info proximity_domain_info; 284 } __packed; 285 286 struct hv_output_add_logical_processor { 287 struct hv_lp_startup_status startup_status; 288 } __packed; 289 290 enum { /* HV_SUBNODE_TYPE */ 291 HV_SUBNODE_ANY = 0, 292 HV_SUBNODE_SOCKET, 293 HV_SUBNODE_CLUSTER, 294 HV_SUBNODE_L3, 295 HV_SUBNODE_COUNT, 296 HV_SUBNODE_INVALID = -1 297 }; 298 299 struct hv_create_vp { /* HV_INPUT_CREATE_VP */ 300 u64 partition_id; 301 u32 vp_index; 302 u8 padding[3]; 303 u8 subnode_type; 304 u64 subnode_id; 305 struct hv_proximity_domain_info proximity_domain_info; 306 u64 flags; 307 } __packed; 308 309 /* HV_INTERRUPT_TRIGGER_MODE */ 310 enum hv_interrupt_trigger_mode { 311 HV_INTERRUPT_TRIGGER_MODE_EDGE = 0, 312 HV_INTERRUPT_TRIGGER_MODE_LEVEL = 1, 313 }; 314 315 /* HV_DEVICE_INTERRUPT_DESCRIPTOR */ 316 struct hv_device_interrupt_descriptor { 317 u32 interrupt_type; 318 u32 trigger_mode; 319 u32 vector_count; 320 u32 reserved; 321 struct hv_device_interrupt_target target; 322 } __packed; 323 324 /* HV_INPUT_MAP_DEVICE_INTERRUPT */ 325 struct hv_input_map_device_interrupt { 326 u64 partition_id; 327 u64 device_id; 328 u32 flags; 329 u32 base_irt_idx; 330 struct hv_interrupt_entry logical_interrupt_entry; 331 struct hv_device_interrupt_descriptor interrupt_descriptor; 332 } __packed; 333 334 /* HV_OUTPUT_MAP_DEVICE_INTERRUPT */ 335 struct hv_output_map_device_interrupt { 336 struct hv_interrupt_entry interrupt_entry; 337 u64 ext_status_deprecated[5]; 338 } __packed; 339 340 /* HV_INPUT_UNMAP_DEVICE_INTERRUPT */ 341 struct hv_input_unmap_device_interrupt { 342 u64 partition_id; 343 u64 device_id; 344 struct hv_interrupt_entry interrupt_entry; 345 u32 flags; 346 } __packed; 347 348 #define HV_SOURCE_SHADOW_NONE 0x0 349 #define HV_SOURCE_SHADOW_BRIDGE_BUS_RANGE 0x1 350 351 struct hv_send_ipi_ex { /* HV_INPUT_SEND_SYNTHETIC_CLUSTER_IPI_EX */ 352 u32 vector; 353 u32 reserved; 354 struct hv_vpset vp_set; 355 } __packed; 356 357 typedef u16 hv_pci_rid; /* HV_PCI_RID */ 358 typedef u16 hv_pci_segment; /* HV_PCI_SEGMENT */ 359 typedef u64 hv_logical_device_id; 360 union hv_pci_bdf { /* HV_PCI_BDF */ 361 u16 as_uint16; 362 363 struct { 364 u8 function : 3; 365 u8 device : 5; 366 u8 bus; 367 }; 368 } __packed; 369 370 union hv_pci_bus_range { 371 u16 as_uint16; 372 373 struct { 374 u8 subordinate_bus; 375 u8 secondary_bus; 376 }; 377 } __packed; 378 379 enum hv_device_type { /* HV_DEVICE_TYPE */ 380 HV_DEVICE_TYPE_LOGICAL = 0, 381 HV_DEVICE_TYPE_PCI = 1, 382 HV_DEVICE_TYPE_IOAPIC = 2, 383 HV_DEVICE_TYPE_ACPI = 3, 384 }; 385 386 union hv_device_id { /* HV_DEVICE_ID */ 387 u64 as_uint64; 388 389 struct { 390 u64 reserved0 : 62; 391 u64 device_type : 2; 392 }; 393 394 /* HV_DEVICE_TYPE_LOGICAL */ 395 struct { 396 u64 id : 62; 397 u64 device_type : 2; 398 } logical; 399 400 /* HV_DEVICE_TYPE_PCI */ 401 struct { 402 union { 403 hv_pci_rid rid; 404 union hv_pci_bdf bdf; 405 }; 406 407 hv_pci_segment segment; 408 union hv_pci_bus_range shadow_bus_range; 409 410 u16 phantom_function_bits : 2; 411 u16 source_shadow : 1; 412 413 u16 rsvdz0 : 11; 414 u16 device_type : 2; 415 } pci; 416 417 /* HV_DEVICE_TYPE_IOAPIC */ 418 struct { 419 u8 ioapic_id; 420 u8 rsvdz0; 421 u16 rsvdz1; 422 u16 rsvdz2; 423 424 u16 rsvdz3 : 14; 425 u16 device_type : 2; 426 } ioapic; 427 428 /* HV_DEVICE_TYPE_ACPI */ 429 struct { 430 u32 input_mapping_base; 431 u32 input_mapping_count : 30; 432 u32 device_type : 2; 433 } acpi; 434 } __packed; 435 436 #endif /* _HV_HVHDK_MINI_H */ 437