1/* 2 * Copyright (c) 2000-2007 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#ifndef _KERN_DEBUG_H_ 30#define _KERN_DEBUG_H_ 31 32#include <sys/cdefs.h> 33#include <stdint.h> 34#include <uuid/uuid.h> 35 36#ifndef XNU_KERNEL_PRIVATE 37#include <TargetConditionals.h> 38#endif 39 40#ifdef __APPLE_API_PRIVATE 41#ifdef __APPLE_API_UNSTABLE 42 43/* This value must always match IO_NUM_PRIORITIES defined in thread_info.h */ 44#define STACKSHOT_IO_NUM_PRIORITIES 4 45/* This value must always match MAXTHREADNAMESIZE used in bsd */ 46#define STACKSHOT_MAX_THREAD_NAME_SIZE 64 47 48struct thread_snapshot { 49 uint32_t snapshot_magic; 50 uint32_t nkern_frames; 51 uint32_t nuser_frames; 52 uint64_t wait_event; 53 uint64_t continuation; 54 uint64_t thread_id; 55 uint64_t user_time; 56 uint64_t system_time; 57 int32_t state; 58 int32_t priority; /* static priority */ 59 int32_t sched_pri; /* scheduled (current) priority */ 60 int32_t sched_flags; /* scheduler flags */ 61 char ss_flags; 62 char ts_qos; 63 char io_tier; 64 65 /* 66 * I/O Statistics 67 * XXX: These fields must be together 68 */ 69 uint64_t disk_reads_count; 70 uint64_t disk_reads_size; 71 uint64_t disk_writes_count; 72 uint64_t disk_writes_size; 73 uint64_t io_priority_count[STACKSHOT_IO_NUM_PRIORITIES]; 74 uint64_t io_priority_size[STACKSHOT_IO_NUM_PRIORITIES]; 75 uint64_t paging_count; 76 uint64_t paging_size; 77 uint64_t non_paging_count; 78 uint64_t non_paging_size; 79 uint64_t data_count; 80 uint64_t data_size; 81 uint64_t metadata_count; 82 uint64_t metadata_size; 83 /* XXX: I/O Statistics end */ 84 85 uint64_t voucher_identifier; /* obfuscated voucher identifier */ 86 uint64_t total_syscalls; 87 char pth_name[STACKSHOT_MAX_THREAD_NAME_SIZE]; 88 89} __attribute__ ((packed)); 90 91struct task_snapshot { 92 uint32_t snapshot_magic; 93 int32_t pid; 94 uint64_t uniqueid; 95 uint64_t user_time_in_terminated_threads; 96 uint64_t system_time_in_terminated_threads; 97 uint8_t shared_cache_identifier[16]; 98 uint64_t shared_cache_slide; 99 uint32_t nloadinfos; 100 int suspend_count; 101 int task_size; /* pages */ 102 int faults; /* number of page faults */ 103 int pageins; /* number of actual pageins */ 104 int cow_faults; /* number of copy-on-write faults */ 105 uint32_t ss_flags; 106 uint64_t p_start_sec; /* from the bsd proc struct */ 107 uint64_t p_start_usec; /* from the bsd proc struct */ 108 109 /* 110 * We restrict ourselves to a statically defined 111 * (current as of 2009) length for the 112 * p_comm string, due to scoping issues (osfmk/bsd and user/kernel 113 * binary compatibility). 114 */ 115 char p_comm[17]; 116 uint32_t was_throttled; 117 uint32_t did_throttle; 118 uint32_t latency_qos; 119 /* 120 * I/O Statistics 121 * XXX: These fields must be together. 122 */ 123 uint64_t disk_reads_count; 124 uint64_t disk_reads_size; 125 uint64_t disk_writes_count; 126 uint64_t disk_writes_size; 127 uint64_t io_priority_count[STACKSHOT_IO_NUM_PRIORITIES]; 128 uint64_t io_priority_size[STACKSHOT_IO_NUM_PRIORITIES]; 129 uint64_t paging_count; 130 uint64_t paging_size; 131 uint64_t non_paging_count; 132 uint64_t non_paging_size; 133 uint64_t data_count; 134 uint64_t data_size; 135 uint64_t metadata_count; 136 uint64_t metadata_size; 137 /* XXX: I/O Statistics end */ 138 139 uint32_t donating_pid_count; 140 141} __attribute__ ((packed)); 142 143struct micro_snapshot { 144 uint32_t snapshot_magic; 145 uint32_t ms_cpu; /* cpu number this snapshot was recorded on */ 146 uint64_t ms_time; /* time at sample (seconds) */ 147 uint64_t ms_time_microsecs; 148 uint8_t ms_flags; 149 uint16_t ms_opaque_flags; /* managed by external entity, e.g. fdrmicrod */ 150} __attribute__ ((packed)); 151 152struct mem_and_io_snapshot { 153 uint32_t snapshot_magic; 154 uint32_t free_pages; 155 uint32_t active_pages; 156 uint32_t inactive_pages; 157 uint32_t purgeable_pages; 158 uint32_t wired_pages; 159 uint32_t speculative_pages; 160 uint32_t throttled_pages; 161 uint32_t filebacked_pages; 162 uint32_t compressions; 163 uint32_t decompressions; 164 uint32_t compressor_size; 165 int busy_buffer_count; 166 uint32_t pages_wanted; 167 uint32_t pages_reclaimed; 168 uint8_t pages_wanted_reclaimed_valid; // did mach_vm_pressure_monitor succeed? 169} __attribute__((packed)); 170 171struct stack_snapshot_frame32 { 172 uint32_t lr; 173 uint32_t sp; 174}; 175 176struct stack_snapshot_frame64 { 177 uint64_t lr; 178 uint64_t sp; 179}; 180 181struct _dyld_cache_header 182{ 183 char magic[16]; // e.g. "dyld_v0 i386" 184 uint32_t mappingOffset; // file offset to first dyld_cache_mapping_info 185 uint32_t mappingCount; // number of dyld_cache_mapping_info entries 186 uint32_t imagesOffset; // file offset to first dyld_cache_image_info 187 uint32_t imagesCount; // number of dyld_cache_image_info entries 188 uint64_t dyldBaseAddress; // base address of dyld when cache was built 189 uint64_t codeSignatureOffset; // file offset of code signature blob 190 uint64_t codeSignatureSize; // size of code signature blob (zero means to end of file) 191 uint64_t slideInfoOffset; // file offset of kernel slid info 192 uint64_t slideInfoSize; // size of kernel slid info 193 uint64_t localSymbolsOffset; // file offset of where local symbols are stored 194 uint64_t localSymbolsSize; // size of local symbols information 195 uint8_t uuid[16]; // unique value for each shared cache file 196}; 197 198struct dyld_uuid_info_32 { 199 uint32_t imageLoadAddress; /* base address image is mapped at */ 200 uuid_t imageUUID; 201}; 202 203struct dyld_uuid_info_64 { 204 uint64_t imageLoadAddress; /* base address image is mapped at */ 205 uuid_t imageUUID; 206}; 207 208enum micro_snapshot_flags { 209 kInterruptRecord = 0x1, 210 kTimerArmingRecord = 0x2, 211 kUserMode = 0x4, /* interrupted usermode, or armed by usermode */ 212}; 213 214/* 215 * Flags used in the following assortment of snapshots. 216 */ 217enum generic_snapshot_flags { 218 kUser64_p = 0x1, 219 kKernel64_p = 0x2 220}; 221 222 enum task_snapshot_flags { 223 kTaskRsrcFlagged = 0x4, // In the EXC_RESOURCE danger zone? 224 kTerminatedSnapshot = 0x8, 225 kPidSuspended = 0x10, // true for suspended task 226 kFrozen = 0x20, // true for hibernated task (along with pidsuspended) 227 kTaskDarwinBG = 0x40, 228 kTaskExtDarwinBG = 0x80, 229 kTaskVisVisible = 0x100, 230 kTaskVisNonvisible = 0x200, 231 kTaskIsForeground = 0x400, 232 kTaskIsBoosted = 0x800, 233 kTaskIsSuppressed = 0x1000, 234 kTaskIsTimerThrottled = 0x2000, /* deprecated */ 235 kTaskIsImpDonor = 0x4000, 236 kTaskIsLiveImpDonor = 0x8000 237 }; 238 239enum thread_snapshot_flags { 240 kHasDispatchSerial = 0x4, 241 kStacksPCOnly = 0x8, /* Stack traces have no frame pointers. */ 242 kThreadDarwinBG = 0x10, /* Thread is darwinbg */ 243 kThreadIOPassive = 0x20, /* Thread uses passive IO */ 244 kThreadSuspended = 0x40 /* Thread is supsended */ 245}; 246 247#define VM_PRESSURE_TIME_WINDOW 5 /* seconds */ 248 249enum { 250 STACKSHOT_GET_DQ = 0x01, 251 STACKSHOT_SAVE_LOADINFO = 0x02, 252 STACKSHOT_GET_GLOBAL_MEM_STATS = 0x04, 253 STACKSHOT_SAVE_KEXT_LOADINFO = 0x08, 254 STACKSHOT_GET_MICROSTACKSHOT = 0x10, 255 STACKSHOT_GLOBAL_MICROSTACKSHOT_ENABLE = 0x20, 256 STACKSHOT_GLOBAL_MICROSTACKSHOT_DISABLE = 0x40, 257 STACKSHOT_SET_MICROSTACKSHOT_MARK = 0x80, 258 STACKSHOT_SAVE_KERNEL_FRAMES_ONLY = 0x100, 259 STACKSHOT_GET_BOOT_PROFILE = 0x200, 260 STACKSHOT_GET_WINDOWED_MICROSTACKSHOTS = 0x400, 261 STACKSHOT_WINDOWED_MICROSTACKSHOTS_ENABLE = 0x800, 262 STACKSHOT_WINDOWED_MICROSTACKSHOTS_DISABLE = 0x1000, 263 STACKSHOT_SAVE_IMP_DONATION_PIDS = 0x2000 264}; 265 266#define STACKSHOT_THREAD_SNAPSHOT_MAGIC 0xfeedface 267#define STACKSHOT_TASK_SNAPSHOT_MAGIC 0xdecafbad 268#define STACKSHOT_MEM_AND_IO_SNAPSHOT_MAGIC 0xbfcabcde 269#define STACKSHOT_MICRO_SNAPSHOT_MAGIC 0x31c54011 270 271#endif /* __APPLE_API_UNSTABLE */ 272#endif /* __APPLE_API_PRIVATE */ 273 274#ifdef KERNEL_PRIVATE 275 276extern unsigned int systemLogDiags; 277#if (!defined(__arm64__) && !defined(NAND_PANIC_DEVICE)) || defined(LEGACY_PANIC_LOGS) 278extern char debug_buf[]; 279#endif 280extern char *debug_buf_addr; 281extern unsigned int debug_boot_arg; 282extern unsigned char *kernel_uuid; 283extern char kernel_uuid_string[]; 284 285#ifdef MACH_KERNEL_PRIVATE 286 287extern unsigned int halt_in_debugger; 288 289extern unsigned int switch_debugger; 290 291extern unsigned int current_debugger; 292#define NO_CUR_DB 0x0 293#define KDP_CUR_DB 0x1 294#define KDB_CUR_DB 0x2 295 296extern unsigned int active_debugger; 297extern unsigned int debug_mode; 298extern unsigned int disable_debug_output; 299 300extern unsigned int panicDebugging; 301extern unsigned int logPanicDataToScreen; 302 303extern int db_run_mode; 304 305/* modes the system may be running in */ 306 307#define STEP_NONE 0 308#define STEP_ONCE 1 309#define STEP_RETURN 2 310#define STEP_CALLT 3 311#define STEP_CONTINUE 4 312#define STEP_INVISIBLE 5 313#define STEP_COUNT 6 314#define STEP_TRACE 7 /* Show all calls to functions and returns */ 315 316extern const char *panicstr; 317extern volatile unsigned int nestedpanic; 318extern int unsigned long panic_caller; 319 320extern char *debug_buf_ptr; 321extern unsigned int debug_buf_size; 322 323extern void debug_log_init(void); 324extern void debug_putc(char); 325 326extern void panic_init(void); 327 328int packA(char *inbuf, uint32_t length, uint32_t buflen); 329void unpackA(char *inbuf, uint32_t length); 330 331void panic_display_system_configuration(void); 332void panic_display_zprint(void); 333void panic_display_kernel_aslr(void); 334void panic_display_hibb(void); 335#if CONFIG_ZLEAKS 336void panic_display_ztrace(void); 337#endif /* CONFIG_ZLEAKS */ 338#if CONFIG_ECC_LOGGING 339void panic_display_ecc_errors(void); 340#endif /* CONFIG_ECC_LOGGING */ 341#endif /* MACH_KERNEL_PRIVATE */ 342 343#define DB_HALT 0x1 344#define DB_PRT 0x2 345#define DB_NMI 0x4 346#define DB_KPRT 0x8 347#define DB_KDB 0x10 348#define DB_SLOG 0x20 349#define DB_ARP 0x40 350#define DB_KDP_BP_DIS 0x80 351#define DB_LOG_PI_SCRN 0x100 352#define DB_KDP_GETC_ENA 0x200 353 354#define DB_KERN_DUMP_ON_PANIC 0x400 /* Trigger core dump on panic*/ 355#define DB_KERN_DUMP_ON_NMI 0x800 /* Trigger core dump on NMI */ 356#define DB_DBG_POST_CORE 0x1000 /*Wait in debugger after NMI core */ 357#define DB_PANICLOG_DUMP 0x2000 /* Send paniclog on panic,not core*/ 358#define DB_REBOOT_POST_CORE 0x4000 /* Attempt to reboot after 359 * post-panic crashdump/paniclog 360 * dump. 361 */ 362#define DB_NMI_BTN_ENA 0x8000 /* Enable button to directly trigger NMI */ 363 364#if DEBUG 365/* 366 * For the DEBUG kernel, support the following: 367 * sysctl -w debug.kprint_syscall=<syscall_mask> 368 * sysctl -w debug.kprint_syscall_process=<p_comm> 369 * <syscall_mask> should be an OR of the masks below 370 * for UNIX, MACH, MDEP, or IPC. This debugging aid 371 * assumes the task/process is locked/wired and will 372 * not go away during evaluation. If no process is 373 * specified, all processes will be traced 374 */ 375extern int debug_kprint_syscall; 376extern int debug_kprint_current_process(const char **namep); 377#define DEBUG_KPRINT_SYSCALL_PREDICATE_INTERNAL(mask, namep) \ 378 ( (debug_kprint_syscall & (mask)) && debug_kprint_current_process(namep) ) 379#define DEBUG_KPRINT_SYSCALL_MASK(mask, fmt, args...) do { \ 380 const char *dks_name = NULL; \ 381 if (DEBUG_KPRINT_SYSCALL_PREDICATE_INTERNAL(mask, &dks_name)) { \ 382 kprintf("[%s%s%p]" fmt, dks_name ? dks_name : "", \ 383 dks_name ? "@" : "", current_thread(), args); \ 384 } \ 385 } while (0) 386#else /* !DEBUG */ 387#define DEBUG_KPRINT_SYSCALL_PREDICATE_INTERNAL(mask, namep) (0) 388#define DEBUG_KPRINT_SYSCALL_MASK(mask, fmt, args...) do { } while (0) /* kprintf(fmt, args) */ 389#endif /* !DEBUG */ 390 391enum { 392 DEBUG_KPRINT_SYSCALL_UNIX_MASK = 1 << 0, 393 DEBUG_KPRINT_SYSCALL_MACH_MASK = 1 << 1, 394 DEBUG_KPRINT_SYSCALL_MDEP_MASK = 1 << 2, 395 DEBUG_KPRINT_SYSCALL_IPC_MASK = 1 << 3 396}; 397 398#define DEBUG_KPRINT_SYSCALL_PREDICATE(mask) \ 399 DEBUG_KPRINT_SYSCALL_PREDICATE_INTERNAL(mask, NULL) 400#define DEBUG_KPRINT_SYSCALL_UNIX(fmt, args...) \ 401 DEBUG_KPRINT_SYSCALL_MASK(DEBUG_KPRINT_SYSCALL_UNIX_MASK,fmt,args) 402#define DEBUG_KPRINT_SYSCALL_MACH(fmt, args...) \ 403 DEBUG_KPRINT_SYSCALL_MASK(DEBUG_KPRINT_SYSCALL_MACH_MASK,fmt,args) 404#define DEBUG_KPRINT_SYSCALL_MDEP(fmt, args...) \ 405 DEBUG_KPRINT_SYSCALL_MASK(DEBUG_KPRINT_SYSCALL_MDEP_MASK,fmt,args) 406#define DEBUG_KPRINT_SYSCALL_IPC(fmt, args...) \ 407 DEBUG_KPRINT_SYSCALL_MASK(DEBUG_KPRINT_SYSCALL_IPC_MASK,fmt,args) 408 409#endif /* KERNEL_PRIVATE */ 410 411#ifdef KERNEL 412 413__BEGIN_DECLS 414 415extern void panic(const char *string, ...) __printflike(1,2); 416 417#if KERNEL_PRIVATE 418void _consume_panic_args(int, ...); 419void panic_context(unsigned int reason, void *ctx, const char *string, ...); 420#endif 421 422#if CONFIG_NO_PANIC_STRINGS 423#if KERNEL_PRIVATE 424#define panic_plain(x, ...) _consume_panic_args( 0, ## __VA_ARGS__ ) 425#define panic(x, ...) _consume_panic_args( 0, ## __VA_ARGS__ ) 426#else 427#define panic_plain(...) (panic)((char *)0) 428#define panic(...) (panic)((char *)0) 429#endif 430#else /* CONFIGS_NO_PANIC_STRINGS */ 431#define panic_plain(ex, ...) \ 432 (panic)(ex, ## __VA_ARGS__) 433#define __STRINGIFY(x) #x 434#define LINE_NUMBER(x) __STRINGIFY(x) 435#define PANIC_LOCATION __FILE__ ":" LINE_NUMBER(__LINE__) 436#define panic(ex, ...) \ 437 (panic)(# ex "@" PANIC_LOCATION, ## __VA_ARGS__) 438#endif /* CONFIGS_NO_PANIC_STRINGS */ 439 440#ifdef KERNEL_PRIVATE 441void populate_model_name(char *); 442unsigned panic_active(void); 443#endif 444 445__END_DECLS 446 447#endif /* KERNEL */ 448 449#endif /* _KERN_DEBUG_H_ */ 450