xref: /illumos-gate/usr/src/uts/intel/io/vmm/sys/vmm_vm.h (revision 50fe091cff3f2dccec5f588584a3ccb4f9933570)
1 /*
2  * This file and its contents are supplied under the terms of the
3  * Common Development and Distribution License ("CDDL"), version 1.0.
4  * You may only use this file in accordance with the terms of version
5  * 1.0 of the CDDL.
6  *
7  * A full copy of the text of the CDDL should have accompanied this
8  * source.  A copy of the CDDL is also available via the Internet at
9  * http://www.illumos.org/license/CDDL.
10  */
11 /* This file is dual-licensed; see usr/src/contrib/bhyve/LICENSE */
12 
13 /*
14  * Copyright 2019 Joyent, Inc.
15  * Copyright 2025 Oxide Computer Company
16  */
17 
18 #ifndef	_VMM_VM_H
19 #define	_VMM_VM_H
20 
21 #include <sys/types.h>
22 
23 typedef struct vmspace vmspace_t;
24 typedef struct vm_client vm_client_t;
25 typedef struct vm_page vm_page_t;
26 typedef struct vm_object vm_object_t;
27 
28 typedef void (*vmc_inval_cb_t)(void *, uintptr_t, size_t);
29 
30 typedef enum vmspace_bit_operation {
31 	VBO_RESET_DIRTY = 1,
32 	VBO_SET_DIRTY = 2,
33 	VBO_GET_DIRTY = 3,
34 
35 	VBO_FLAG_BITMAP_IN = (1 << 30),
36 	VBO_FLAG_BITMAP_OUT = (1 << 31),
37 } vmspace_bit_oper_t;
38 
39 bool vmm_vm_init(void);
40 void vmm_vm_fini(void);
41 
42 /* vmspace_t operations */
43 vmspace_t *vmspace_alloc(size_t);
44 void vmspace_destroy(vmspace_t *);
45 int vmspace_map(vmspace_t *, vm_object_t *, uintptr_t, uintptr_t, size_t,
46     uint8_t);
47 int vmspace_unmap(vmspace_t *, uintptr_t, uintptr_t);
48 int vmspace_populate(vmspace_t *, uintptr_t, uintptr_t);
49 vm_client_t *vmspace_client_alloc(vmspace_t *);
50 uint64_t vmspace_table_root(vmspace_t *);
51 uint64_t vmspace_table_gen(vmspace_t *);
52 uint64_t vmspace_resident_count(vmspace_t *);
53 void vmspace_bits_operate(vmspace_t *, uint64_t, size_t, vmspace_bit_oper_t,
54     uint8_t *);
55 bool vmspace_get_tracking(vmspace_t *);
56 int vmspace_set_tracking(vmspace_t *, bool);
57 
58 /* vm_client_t operations */
59 vm_page_t *vmc_hold(vm_client_t *, uintptr_t, int);
60 vm_page_t *vmc_hold_ext(vm_client_t *, uintptr_t, int, int);
61 uint64_t vmc_table_enter(vm_client_t *);
62 void vmc_table_exit(vm_client_t *);
63 int vmc_fault(vm_client_t *, uintptr_t, int);
64 vm_client_t *vmc_clone(vm_client_t *);
65 int vmc_set_inval_cb(vm_client_t *, vmc_inval_cb_t, void *);
66 void vmc_destroy(vm_client_t *);
67 
68 /* vm_object_t operations */
69 vm_object_t *vm_object_mem_allocate(size_t, bool);
70 vm_object_t *vmm_mmio_alloc(vmspace_t *, uintptr_t, size_t, uintptr_t);
71 void vm_object_reference(vm_object_t *);
72 void vm_object_release(vm_object_t *);
73 pfn_t vm_object_pfn(vm_object_t *, uintptr_t);
74 
75 /* vm_page_t operations */
76 const void *vmp_get_readable(const vm_page_t *);
77 void *vmp_get_writable(const vm_page_t *);
78 pfn_t vmp_get_pfn(const vm_page_t *);
79 void vmp_mark_dirty(vm_page_t *);
80 void vmp_chain(vm_page_t *, vm_page_t *);
81 vm_page_t *vmp_next(const vm_page_t *);
82 bool vmp_release(vm_page_t *);
83 bool vmp_release_chain(vm_page_t *);
84 
85 /*
86  * Flags for vmc_hold_ext():
87  */
88 
89 /* The default flags are empty */
90 #define	VPF_DEFAULT		0
91 
92 /*
93  * When a page is held for potential writes, the consumer may not perform those
94  * writes immediately, or in some cases ever.  They may wish to defer the page
95  * being considered dirty until such a determination is made.  By establishing a
96  * page hold with this flag, the consumer commits to a later vmp_mark_dirty()
97  * call if they write any data though the vm_page.  Doing so will effectively
98  * clear the flag and subject the page to expected dirty-tracking logic.
99  */
100 #define	VPF_DEFER_DIRTY		(1 << 0)
101 
102 /* seg_vmm mapping */
103 struct vm;
104 int vm_segmap_obj(struct vm *, int, off_t, off_t, struct as *, caddr_t *,
105     uint_t, uint_t, uint_t);
106 int vm_segmap_space(struct vm *, off_t, struct as *, caddr_t *, off_t, uint_t,
107     uint_t, uint_t);
108 
109 /* Glue functions */
110 vm_paddr_t vtophys(void *);
111 void invalidate_cache_all(void);
112 
113 /*
114  * The VM_MAXUSER_ADDRESS determines the upper size limit of a vmspace.
115  * This value is sized well below the host userlimit, halving the
116  * available space below the VA hole to avoid Intel EPT limits and
117  * leave room available in the usable VA range for other mmap tricks.
118  */
119 #define	VM_MAXUSER_ADDRESS	0x00003ffffffffffful
120 
121 #endif /* _VMM_VM_H */
122