-
Notifications
You must be signed in to change notification settings - Fork 20
drivers: hv: mshv_vtl: Implement restore partition time IOCTL #116
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: product/hcl-main/6.12
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -32,6 +32,7 @@ | |
|
|
||
| #ifdef CONFIG_X86_64 | ||
| #include <linux/cleanup.h> | ||
| #include <linux/stop_machine.h> | ||
|
|
||
| #include <asm/apic.h> | ||
| #include <uapi/asm/mtrr.h> | ||
|
|
@@ -42,6 +43,7 @@ | |
| #include <asm/vmx.h> | ||
|
|
||
| #include "../../kernel/fpu/legacy.h" | ||
| #include "../../kernel/time/timekeeping.h" | ||
|
|
||
| #endif | ||
|
|
||
|
|
@@ -865,6 +867,57 @@ static int mshv_vtl_ioctl_add_vtl0_mem(struct mshv_vtl *vtl, void __user *arg) | |
| return 0; | ||
| } | ||
|
|
||
| #ifdef CONFIG_X86_64 | ||
| static int restore_partition_time_with_cpus_stopped(void *data) | ||
| { | ||
| struct mshv_partition_time *partition_time = data; | ||
| struct hv_input_restore_partition_time *input; | ||
| int result = 0; | ||
| u64 status; | ||
|
|
||
| /* Save current clock state. No other CPUs are running so no locks are taken. */ | ||
| sched_clock_suspend(); | ||
| timekeeping_suspend(); | ||
| hv_save_sched_clock_state(); | ||
|
|
||
| /* Interrupts are disabled, make the hypercall to update the TSC. */ | ||
| input = *this_cpu_ptr(hyperv_pcpu_input_arg); | ||
| input->partition_id = HV_PARTITION_ID_SELF; | ||
| input->tsc_sequence = partition_time->tsc_sequence; | ||
| input->reserved = 0; | ||
| input->reference_time_in_100_ns = partition_time->reference_time_in_100_ns; | ||
| input->tsc = partition_time->tsc; | ||
| status = hv_do_hypercall(HVCALL_RESTORE_PARTITION_TIME, input, NULL); | ||
| if (!hv_result_success(status)) { | ||
| pr_err("HVCALL_RESTORE_PARTITION_TIME failed with %#llx\n", status); | ||
| result = -EINVAL; | ||
| } | ||
|
|
||
| /* Restore clock state using current TSC value. */ | ||
| hv_restore_sched_clock_state(); | ||
| timekeeping_resume(); | ||
| sched_clock_resume(); | ||
|
|
||
| return result; | ||
| } | ||
|
|
||
| static int mshv_restore_partition_time(void __user *arg) | ||
| { | ||
| unsigned long irq_flags; | ||
| struct mshv_partition_time partition_time; | ||
| int ret; | ||
|
|
||
| if (copy_from_user(&partition_time, arg, sizeof(partition_time))) | ||
| return -EFAULT; | ||
|
|
||
| /* Stop other CPUs, using the current one to restore partition time. */ | ||
| local_irq_save(irq_flags); | ||
| ret = stop_machine(restore_partition_time_with_cpus_stopped, &partition_time, cpumask_of(smp_processor_id())); | ||
|
||
| local_irq_restore(irq_flags); | ||
|
Comment on lines
+914
to
+916
|
||
| return ret; | ||
| } | ||
| #endif | ||
|
|
||
| static void mshv_vtl_cancel(int cpu) | ||
| { | ||
| int here = get_cpu(); | ||
|
|
@@ -2596,6 +2649,13 @@ mshv_vtl_ioctl(struct file *filp, unsigned int ioctl, unsigned long arg) | |
| case MSHV_VTL_ADD_VTL0_MEMORY: | ||
| ret = mshv_vtl_ioctl_add_vtl0_mem(vtl, (void __user *)arg); | ||
| break; | ||
|
|
||
| #if defined(CONFIG_X86_64) | ||
| case MSHV_RESTORE_PARTITION_TIME: | ||
| ret = mshv_restore_partition_time((void __user *)arg); | ||
| break; | ||
| #endif | ||
|
|
||
| #if defined(CONFIG_X86_64) && defined(CONFIG_INTEL_TDX_GUEST) | ||
| case MSHV_VTL_TDCALL: | ||
| ret = mshv_vtl_ioctl_tdcall((void __user *)arg); | ||
|
|
||
| Original file line number | Diff line number | Diff line change | ||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -197,6 +197,7 @@ union hv_reference_tsc_msr { | |||||||||||||||
| #define HVCALL_FLUSH_GUEST_PHYSICAL_ADDRESS_SPACE 0x00af | ||||||||||||||||
| #define HVCALL_FLUSH_GUEST_PHYSICAL_ADDRESS_LIST 0x00b0 | ||||||||||||||||
| #define HVCALL_MODIFY_SPARSE_GPA_PAGE_HOST_VISIBILITY 0x00db | ||||||||||||||||
| #define HVCALL_RESTORE_PARTITION_TIME 0x0103 | ||||||||||||||||
| #define HVCALL_MMIO_READ 0x0106 | ||||||||||||||||
| #define HVCALL_MMIO_WRITE 0x0107 | ||||||||||||||||
|
|
||||||||||||||||
|
|
@@ -1002,4 +1003,12 @@ struct hv_enable_vp_vtl { | |||||||||||||||
| u16 mbz1; | ||||||||||||||||
| struct hv_init_vp_context vp_context; | ||||||||||||||||
| } __packed; | ||||||||||||||||
|
|
||||||||||||||||
| struct hv_input_restore_partition_time { | ||||||||||||||||
| u64 partition_id; | ||||||||||||||||
| u32 tsc_sequence; | ||||||||||||||||
| u32 reserved; | ||||||||||||||||
| u64 reference_time_in_100_ns; | ||||||||||||||||
| u64 tsc; | ||||||||||||||||
| } __packed; | ||||||||||||||||
|
Comment on lines
+1007
to
+1013
|
||||||||||||||||
| struct hv_input_restore_partition_time { | |
| u64 partition_id; | |
| u32 tsc_sequence; | |
| u32 reserved; | |
| u64 reference_time_in_100_ns; | |
| u64 tsc; | |
| } __packed; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Inclusion of internal kernel header: The file includes "../../kernel/time/timekeeping.h" using a relative path. This is an internal kernel header that is not part of the public kernel API. Driver code should not include internal headers using relative paths, as this breaks modularity and may cause build issues. The functions from this header (timekeeping_suspend, timekeeping_resume, sched_clock_suspend, sched_clock_resume) are also not exported symbols, which means they cannot be used from driver code that could potentially be built as a module.