X-Git-Url: https://git.saurik.com/apple/xnu.git/blobdiff_plain/3e170ce000f1506b7b5d2c5c7faec85ceabb573d..b226f5e54a60dc81db17b1260381d7dbfea3cdf1:/pexpert/i386/pe_init.c?ds=sidebyside diff --git a/pexpert/i386/pe_init.c b/pexpert/i386/pe_init.c index 35d44a25c..49f9caecf 100644 --- a/pexpert/i386/pe_init.c +++ b/pexpert/i386/pe_init.c @@ -49,7 +49,7 @@ /* extern references */ extern void pe_identify_machine(void * args); - +extern int kdb_printf(const char *format, ...) __printflike(1,2); /* private globals */ PE_state_t PE_state; @@ -189,14 +189,25 @@ void PE_init_platform(boolean_t vm_initialized, void * _args) // New EFI-style PE_state.bootArgs = _args; PE_state.deviceTreeHead = (void *) ml_static_ptovirt(args->deviceTreeP); - PE_state.video.v_baseAddr = args->Video.v_baseAddr; // remains physical address - PE_state.video.v_rowBytes = args->Video.v_rowBytes; - PE_state.video.v_width = args->Video.v_width; - PE_state.video.v_height = args->Video.v_height; - PE_state.video.v_depth = args->Video.v_depth; - PE_state.video.v_display = args->Video.v_display; - strlcpy(PE_state.video.v_pixelFormat, "PPPPPPPP", - sizeof(PE_state.video.v_pixelFormat)); + if (args->Video.v_baseAddr) { + PE_state.video.v_baseAddr = args->Video.v_baseAddr; // remains physical address + PE_state.video.v_rowBytes = args->Video.v_rowBytes; + PE_state.video.v_width = args->Video.v_width; + PE_state.video.v_height = args->Video.v_height; + PE_state.video.v_depth = args->Video.v_depth; + PE_state.video.v_display = args->Video.v_display; + strlcpy(PE_state.video.v_pixelFormat, "PPPPPPPP", + sizeof(PE_state.video.v_pixelFormat)); + } else { + PE_state.video.v_baseAddr = args->VideoV1.v_baseAddr; // remains physical address + PE_state.video.v_rowBytes = args->VideoV1.v_rowBytes; + PE_state.video.v_width = args->VideoV1.v_width; + PE_state.video.v_height = args->VideoV1.v_height; + PE_state.video.v_depth = args->VideoV1.v_depth; + PE_state.video.v_display = args->VideoV1.v_display; + strlcpy(PE_state.video.v_pixelFormat, "PPPPPPPP", + sizeof(PE_state.video.v_pixelFormat)); + } #ifdef kBootArgsFlagHiDPI if (args->flags & kBootArgsFlagHiDPI) @@ -215,7 +226,6 @@ void PE_init_platform(boolean_t vm_initialized, void * _args) } pe_identify_machine(args); - } else { pe_init_debug(); } @@ -325,13 +335,23 @@ PE_reboot_on_panic(void) return FALSE; } +void +PE_sync_panic_buffers(void) +{ +} + /* rdar://problem/21244753 */ uint32_t PE_i_can_has_debugger(uint32_t *debug_flags) { +#if DEVELOPMENT || DEBUG + if (debug_flags) { + assert(debug_boot_arg_inited); + } +#endif + #if CONFIG_CSR - if (csr_check(CSR_ALLOW_KERNEL_DEBUGGER) != 0 && - csr_check(CSR_ALLOW_APPLE_INTERNAL) != 0) { + if (csr_check(CSR_ALLOW_KERNEL_DEBUGGER) != 0) { if (debug_flags) *debug_flags = 0; return FALSE; @@ -342,3 +362,70 @@ PE_i_can_has_debugger(uint32_t *debug_flags) } return TRUE; } + +uint32_t +PE_get_offset_into_panic_region(char *location) +{ + assert(panic_info != NULL); + assert(location > (char *) panic_info); + + return (uint32_t) (location - (char *) panic_info); +} + +void +PE_init_panicheader() +{ + bzero(panic_info, offsetof(struct macos_panic_header, mph_data)); + panic_info->mph_panic_log_offset = PE_get_offset_into_panic_region(debug_buf_base); + + panic_info->mph_magic = MACOS_PANIC_MAGIC; + panic_info->mph_version = MACOS_PANIC_HEADER_CURRENT_VERSION; + + return; +} + +/* + * Tries to update the panic header to keep it consistent on nested panics. + * + * NOTE: The purpose of this function is NOT to detect/correct corruption in the panic region, + * it is to update the panic header to make it consistent when we nest panics. + * + * We try to avoid nested panics/asserts on x86 because they are difficult to debug, so log any + * inconsistencies we find. + */ +void +PE_update_panicheader_nestedpanic() +{ + /* If the panic log offset is not set, re-init the panic header */ + if (panic_info->mph_panic_log_offset == 0) { + PE_init_panicheader(); + panic_info->mph_panic_flags |= MACOS_PANIC_HEADER_FLAG_NESTED_PANIC; + return; + } + + panic_info->mph_panic_flags |= MACOS_PANIC_HEADER_FLAG_NESTED_PANIC; + + /* Usually indicative of corruption in the panic region */ + if(!(((panic_info->mph_stackshot_offset == 0) && (panic_info->mph_stackshot_len == 0)) || + ((panic_info->mph_stackshot_offset != 0) && (panic_info->mph_stackshot_len != 0)))) { + kdb_printf("panic_info contains invalid stackshot metadata: mph_stackshot_offset 0x%x mph_stackshot_len 0x%x\n", + panic_info->mph_stackshot_offset, panic_info->mph_stackshot_len); + } + + /* + * macOS panic logs contain nested panic data, if we've already closed the panic log, + * begin the other log. + */ + if ((panic_info->mph_panic_log_len != 0) && (panic_info->mph_other_log_offset == 0)) { + panic_info->mph_other_log_offset = PE_get_offset_into_panic_region(debug_buf_ptr); + + /* Usually indicative of corruption in the panic region */ + if (panic_info->mph_other_log_len != 0) { + kdb_printf("panic_info contains invalid other log metadata (zero offset but non-zero length), length was 0x%x, zeroing value\n", + panic_info->mph_other_log_len); + panic_info->mph_other_log_len = 0; + } + } + + return; +}