1 // Copyright 2018 The Fuchsia Authors
2 //
3 // Use of this source code is governed by a MIT-style
4 // license that can be found in the LICENSE file or at
5 // https://opensource.org/licenses/MIT
6 
7 #pragma once
8 
9 #include <hypervisor/guest_physical_address_space.h>
10 #include <zircon/types.h>
11 
12 struct PvClockState;
13 
14 // This structure contains mapping between TSC and host wall time at some point
15 // in time. KVM has a hypercall that asks the VMM to populate this structure and
16 // it's actually used, which is rather puzzling considering that PV clock
17 // provides an API to get wall time at the time of boot and offset from that time
18 // which seem to be enough.
19 //
20 // More detailed description of KVM API is available here:
21 //  https://www.kernel.org/doc/Documentation/virtual/kvm/hypercalls.txt
22 struct PvClockOffset {
23     uint64_t sec;
24     uint64_t nsec;
25     uint64_t tsc;
26     uint32_t flags;
27     uint32_t unused[9];
28 } __PACKED;
29 
30 // Updates guest boot time.
31 zx_status_t pvclock_update_boot_time(hypervisor::GuestPhysicalAddressSpace* gpas,
32                                      zx_vaddr_t guest_paddr);
33 
34 // Remembers guest physical address for KVM clock system time structure and enables updates
35 // to guest system time.
36 zx_status_t pvclock_reset_clock(PvClockState* pvclock, hypervisor::GuestPhysicalAddressSpace* gpas,
37                                 zx_vaddr_t guest_paddr);
38 
39 // Disables updates to guest system time.
40 void pvclock_stop_clock(PvClockState* pvclock);
41 
42 // Updates guest system time. If updates disabled does nothing.
43 void pvclock_update_system_time(PvClockState* pvclock, hypervisor::GuestPhysicalAddressSpace* gpas);
44 
45 // Populates mapping between TSC and wall time per guest request. guest_padds contains
46 // physical address of PvClockOffset structure where the result should be stored.
47 zx_status_t pvclock_populate_offset(hypervisor::GuestPhysicalAddressSpace* gpas,
48                                     zx_vaddr_t guest_paddr);
49