1 /* 2 * Copyright (c) 2000-2020 Apple Inc. All rights reserved. 3 * 4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. The rights granted to you under the License 10 * may not be used to create, or enable the creation or redistribution of, 11 * unlawful or unlicensed copies of an Apple operating system, or to 12 * circumvent, violate, or enable the circumvention or violation of, any 13 * terms of an Apple operating system software license agreement. 14 * 15 * Please obtain a copy of the License at 16 * http://www.opensource.apple.com/apsl/ and read it before using this file. 17 * 18 * The Original Code and all software distributed under the License are 19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 23 * Please see the License for the specific language governing rights and 24 * limitations under the License. 25 * 26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@ 27 */ 28 /* 29 * @OSF_COPYRIGHT@ 30 */ 31 /* 32 * Mach Operating System 33 * Copyright (c) 1991,1990,1989,1988,1987 Carnegie Mellon University 34 * All Rights Reserved. 35 * 36 * Permission to use, copy, modify and distribute this software and its 37 * documentation is hereby granted, provided that both the copyright 38 * notice and this permission notice appear in all copies of the 39 * software, derivative works or modified versions, and any portions 40 * thereof, and that both notices appear in supporting documentation. 41 * 42 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 43 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR 44 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. 45 * 46 * Carnegie Mellon requests users of this software to return to 47 * 48 * Software Distribution Coordinator or [email protected] 49 * School of Computer Science 50 * Carnegie Mellon University 51 * Pittsburgh PA 15213-3890 52 * 53 * any improvements or extensions that they make and grant Carnegie Mellon 54 * the rights to redistribute these changes. 55 */ 56 /* 57 */ 58 /* 59 * File: vm/vm_pageout.h 60 * Author: Avadis Tevanian, Jr. 61 * Date: 1986 62 * 63 * Declarations for the pageout daemon interface. 64 */ 65 66 #ifndef _VM_VM_PAGEOUT_H_ 67 #define _VM_VM_PAGEOUT_H_ 68 69 #ifdef KERNEL_PRIVATE 70 71 #include <mach/mach_types.h> 72 #include <mach/boolean.h> 73 #include <mach/machine/vm_types.h> 74 #include <mach/memory_object_types.h> 75 76 #include <kern/kern_types.h> 77 #include <kern/locks.h> 78 #include <kern/sched_prim.h> 79 #include <kern/bits.h> 80 81 #include <libkern/OSAtomic.h> 82 83 84 #include <vm/vm_options.h> 85 86 #ifdef MACH_KERNEL_PRIVATE 87 #include <vm/vm_page.h> 88 #endif 89 90 #include <sys/kdebug.h> 91 92 #define VM_PAGE_AVAILABLE_COUNT() ((unsigned int)(vm_page_cleaned_count)) 93 94 /* externally manipulated counters */ 95 extern unsigned int vm_pageout_cleaned_fault_reactivated; 96 97 #if CONFIG_FREEZE 98 extern boolean_t memorystatus_freeze_enabled; 99 100 struct freezer_context { 101 /* 102 * All these counters & variables track the task 103 * being frozen. 104 * Currently we only freeze one task at a time. Should that 105 * change, we'll need to add support for multiple freezer contexts. 106 */ 107 108 task_t freezer_ctx_task; /* Task being frozen. */ 109 110 void *freezer_ctx_chead; /* The chead used to track c_segs allocated */ 111 /* to freeze the task.*/ 112 113 uint64_t freezer_ctx_swapped_bytes; /* Tracks # of compressed bytes.*/ 114 115 int freezer_ctx_uncompressed_pages; /* Tracks # of uncompressed pages frozen. */ 116 117 char *freezer_ctx_compressor_scratch_buf; /* Scratch buffer for the compressor algorithm. */ 118 }; 119 120 #endif /* CONFIG_FREEZE */ 121 122 #define VM_DYNAMIC_PAGING_ENABLED() (VM_CONFIG_COMPRESSOR_IS_ACTIVE) 123 124 #if VM_PRESSURE_EVENTS 125 extern boolean_t vm_pressure_events_enabled; 126 #endif /* VM_PRESSURE_EVENTS */ 127 128 extern int vm_debug_events; 129 130 #define VM_DEBUG_EVENT(name, event, control, ...) \ 131 MACRO_BEGIN \ 132 if (__improbable(vm_debug_events)) { \ 133 KDBG_FILTERED((VMDBG_CODE(event)) | control, __VA_ARGS__); \ 134 } \ 135 MACRO_END 136 137 #define VM_DEBUG_CONSTANT_EVENT(name, event, control, ...) \ 138 MACRO_BEGIN \ 139 KDBG((VMDBG_CODE(event)) | control, __VA_ARGS__); \ 140 MACRO_END 141 142 extern upl_size_t upl_get_size( 143 upl_t upl); 144 145 146 extern kern_return_t mach_vm_pressure_level_monitor(boolean_t wait_for_pressure, unsigned int *pressure_level); 147 #if KERNEL_PRIVATE 148 extern kern_return_t mach_vm_wire_level_monitor(int64_t requested_pages); 149 #endif /* KERNEL_PRIVATE */ 150 151 152 153 #if UPL_DEBUG 154 extern kern_return_t upl_ubc_alias_set( 155 upl_t upl, 156 uintptr_t alias1, 157 uintptr_t alias2); 158 extern int upl_ubc_alias_get( 159 upl_t upl, 160 uintptr_t * al, 161 uintptr_t * al2); 162 #endif /* UPL_DEBUG */ 163 164 extern void vm_countdirtypages(void); 165 166 extern kern_return_t upl_transpose( 167 upl_t upl1, 168 upl_t upl2); 169 170 extern kern_return_t mach_vm_pressure_monitor( 171 boolean_t wait_for_pressure, 172 unsigned int nsecs_monitored, 173 unsigned int *pages_reclaimed_p, 174 unsigned int *pages_wanted_p); 175 176 extern kern_return_t 177 vm_set_buffer_cleanup_callout( 178 boolean_t (*func)(int)); 179 180 struct vm_page_stats_reusable { 181 SInt32 reusable_count; 182 uint64_t reusable; 183 uint64_t reused; 184 uint64_t reused_wire; 185 uint64_t reused_remove; 186 uint64_t all_reusable_calls; 187 uint64_t partial_reusable_calls; 188 uint64_t all_reuse_calls; 189 uint64_t partial_reuse_calls; 190 uint64_t reusable_pages_success; 191 uint64_t reusable_pages_failure; 192 uint64_t reusable_pages_shared; 193 uint64_t reuse_pages_success; 194 uint64_t reuse_pages_failure; 195 uint64_t can_reuse_success; 196 uint64_t can_reuse_failure; 197 uint64_t reusable_reclaimed; 198 uint64_t reusable_nonwritable; 199 uint64_t reusable_shared; 200 uint64_t free_shared; 201 }; 202 extern struct vm_page_stats_reusable vm_page_stats_reusable; 203 204 extern int hibernate_flush_memory(void); 205 extern void hibernate_reset_stats(void); 206 extern void hibernate_create_paddr_map(void); 207 208 extern void vm_set_restrictions(unsigned int num_cpus); 209 210 extern int vm_compressor_mode; 211 extern kern_return_t vm_pageout_compress_page(void **, char *, vm_page_t); 212 extern kern_return_t vm_pageout_anonymous_pages(void); 213 extern void vm_pageout_disconnect_all_pages(void); 214 extern int vm_toggle_task_selfdonate_pages(task_t); 215 extern void vm_task_set_selfdonate_pages(task_t, bool); 216 217 struct vm_config { 218 boolean_t compressor_is_present; /* compressor is initialized and can be used by the freezer, the sweep or the pager */ 219 boolean_t compressor_is_active; /* pager can actively compress pages... 'compressor_is_present' must be set */ 220 boolean_t swap_is_present; /* swap is initialized and can be used by the freezer, the sweep or the pager */ 221 boolean_t swap_is_active; /* pager can actively swap out compressed segments... 'swap_is_present' must be set */ 222 boolean_t freezer_swap_is_active; /* freezer can swap out frozen tasks... "compressor_is_present + swap_is_present" must be set */ 223 }; 224 225 extern struct vm_config vm_config; 226 227 228 #define VM_PAGER_NOT_CONFIGURED 0x0 /* no compresser or swap configured */ 229 #define VM_PAGER_DEFAULT 0x1 /* Use default pager... DEPRECATED */ 230 #define VM_PAGER_COMPRESSOR_NO_SWAP 0x2 /* Active in-core compressor only. */ 231 #define VM_PAGER_COMPRESSOR_WITH_SWAP 0x4 /* Active in-core compressor + swap backend. */ 232 #define VM_PAGER_FREEZER_DEFAULT 0x8 /* Freezer backed by default pager... DEPRECATED */ 233 #define VM_PAGER_FREEZER_COMPRESSOR_NO_SWAP 0x10 /* Freezer backed by in-core compressor only i.e. frozen data remain in-core compressed.*/ 234 #define VM_PAGER_COMPRESSOR_NO_SWAP_PLUS_FREEZER_COMPRESSOR_WITH_SWAP 0x20 /* Active in-core compressor + Freezer backed by in-core compressor with swap support too.*/ 235 236 #define VM_PAGER_MAX_MODES 6 /* Total number of vm compressor modes supported */ 237 238 239 #define VM_CONFIG_COMPRESSOR_IS_PRESENT (vm_config.compressor_is_present == TRUE) 240 #define VM_CONFIG_COMPRESSOR_IS_ACTIVE (vm_config.compressor_is_active == TRUE) 241 #define VM_CONFIG_SWAP_IS_PRESENT (vm_config.swap_is_present == TRUE) 242 #define VM_CONFIG_SWAP_IS_ACTIVE (vm_config.swap_is_active == TRUE) 243 #define VM_CONFIG_FREEZER_SWAP_IS_ACTIVE (vm_config.freezer_swap_is_active == TRUE) 244 245 #endif /* KERNEL_PRIVATE */ 246 247 248 #endif /* _VM_VM_PAGEOUT_H_ */ 249