X-Git-Url: https://git.saurik.com/apple/xnu.git/blobdiff_plain/de355530ae67247cbd0da700edb3a2a1dae884c2..91447636331957f3d9b5ca5b508f07c526b0074d:/osfmk/i386/AT386/model_dep.c diff --git a/osfmk/i386/AT386/model_dep.c b/osfmk/i386/AT386/model_dep.c index c3cb5bc94..588e59611 100644 --- a/osfmk/i386/AT386/model_dep.c +++ b/osfmk/i386/AT386/model_dep.c @@ -60,12 +60,9 @@ * Basic initialization for I386 - ISA bus machines. */ -#include #include -#include #include #include -#include #include @@ -74,320 +71,165 @@ #include #include #include -#include #include #include #include #include #include #include -#include -#include #include -#include -#include -#include +#include #include -#include #include #include #include -#include -#include -#include +#include +#include +#include +#include #if MACH_KDB #include #endif /* MACH_KDB */ -#include -#ifdef __MACHO__ -#include -#include -#include -#endif -#if NCPUS > 1 #include -#endif /* NCPUS */ - -#if MP_V1_1 -#include -#endif /* MP_V1_1 */ +#include #include -vm_size_t mem_size = 0; -vm_offset_t first_addr = 0; /* set by start.s - keep out of bss */ -vm_offset_t first_avail = 0;/* first after page tables */ -vm_offset_t last_addr; - -vm_offset_t avail_start, avail_end; -vm_offset_t virtual_avail, virtual_end; -vm_offset_t hole_start, hole_end; -vm_offset_t avail_next; -unsigned int avail_remaining; - -/* parameters passed from bootstrap loader */ -int cnvmem = 0; /* must be in .data section */ -int extmem = 0; - -/* FIXME!! REMOVE WHEN OSFMK DEVICES ARE COMPLETELY PULLED OUT */ -int dev_name_count = 0; -int dev_name_list = 0; - -#ifndef __MACHO__ -extern char edata, end; -#endif - -extern char version[]; - -void parse_arguments(void); -const char *getenv(const char *); - -#define BOOT_LINE_LENGTH 160 -char boot_string_store[BOOT_LINE_LENGTH] = {0}; -char *boot_string = (char *)0; -int boot_string_sz = BOOT_LINE_LENGTH; -int boottype = 0; - -#if __MACHO__ -#include -vm_offset_t edata, etext, end; - -extern struct mach_header _mh_execute_header; -void *sectTEXTB; int sectSizeTEXT; -void *sectDATAB; int sectSizeDATA; -void *sectOBJCB; int sectSizeOBJC; -void *sectLINKB; int sectSizeLINK; - -/* Kernel boot information */ -KERNBOOTSTRUCT kernBootStructData; -KERNBOOTSTRUCT *kernBootStruct; -#endif - -vm_offset_t kern_args_start = 0; /* kernel arguments */ -vm_size_t kern_args_size = 0; /* size of kernel arguments */ - -#ifdef __MACHO__ - -unsigned long -i386_preinit() -{ - int i; - struct segment_command *sgp; - struct section *sp; - - sgp = (struct segment_command *) getsegbyname("__DATA"); - if (sgp) { - sp = (struct section *) firstsect(sgp); - if (sp) { - do { - if (sp->flags & S_ZEROFILL) - bzero((char *) sp->addr, sp->size); - } while (sp = (struct section *)nextsect(sgp, sp)); - } - } - - bcopy((char *) KERNSTRUCT_ADDR, (char *) &kernBootStructData, - sizeof(kernBootStructData)); +void enable_bluebox(void); +void disable_bluebox(void); - kernBootStruct = &kernBootStructData; +static void machine_conf(void); +#include - end = round_page( kernBootStruct->kaddr + kernBootStruct->ksize ); +extern int default_preemption_rate; +extern int max_unsafe_quanta; +extern int max_poll_quanta; +extern int idlehalt; +extern unsigned int panic_is_inited; - return end; -} -#endif - -/* - * Cpu initialization. Running virtual, but without MACH VM - * set up. First C routine called. - */ void -machine_startup(void) +machine_startup() { + int boot_arg; -#ifdef __MACHO__ - /* Now copy over various bits.. */ - cnvmem = kernBootStruct->convmem; - extmem = kernBootStruct->extmem; - kern_args_start = (vm_offset_t) kernBootStruct->bootString; - kern_args_size = strlen(kernBootStruct->bootString); - boottype = kernBootStruct->rootdev; - - /* Now retrieve addresses for end, edata, and etext - * from MACH-O headers. - */ - - sectTEXTB = (void *) getsegdatafromheader( - &_mh_execute_header, "__TEXT", §SizeTEXT); - sectDATAB = (void *) getsegdatafromheader( - &_mh_execute_header, "__DATA", §SizeDATA); - sectOBJCB = (void *) getsegdatafromheader( - &_mh_execute_header, "__OBJC", §SizeOBJC); - sectLINKB = (void *) getsegdatafromheader( - &_mh_execute_header, "__LINKEDIT", §SizeLINK); - - etext = (vm_offset_t) sectTEXTB + sectSizeTEXT; - edata = (vm_offset_t) sectDATAB + sectSizeDATA; +#if 0 + if( PE_get_hotkey( kPEControlKey )) + halt_in_debugger = halt_in_debugger ? 0 : 1; #endif - printf_init(); /* Init this in case we need debugger */ - panic_init(); /* Init this in case we need debugger */ - - PE_init_platform(FALSE, kernBootStruct); - PE_init_kprintf(FALSE); - PE_init_printf(FALSE); - - /* - * Parse startup arguments - */ - parse_arguments(); - - /* - * Set up initial thread so current_thread() works early on - */ - pageout_thread.top_act = &pageout_act; - pageout_act.thread = &pageout_thread; - thread_machine_set_current(&pageout_thread); - - /* - * Do basic VM initialization - */ - i386_init(); + if (PE_parse_boot_arg("debug", &boot_arg)) { + if (boot_arg & DB_HALT) halt_in_debugger=1; + if (boot_arg & DB_PRT) disableDebugOuput=FALSE; + if (boot_arg & DB_SLOG) systemLogDiags=TRUE; + if (boot_arg & DB_NMI) panicDebugging=TRUE; + if (boot_arg & DB_LOG_PI_SCRN) logPanicDataToScreen=TRUE; + } - PE_init_platform(TRUE, kernBootStruct); - PE_init_kprintf(TRUE); - PE_init_printf(TRUE); +#if NOTYET + hw_lock_init(&debugger_lock); /* initialize debugger lock */ + hw_lock_init(&pbtlock); /* initialize print backtrace lock */ +#endif #if MACH_KDB /* - * Initialize the kernel debugger. + * Initialize KDB */ +#if DB_MACHINE_COMMANDS + db_machine_commands_install(ppc_db_commands); +#endif /* DB_MACHINE_COMMANDS */ ddb_init(); + if (boot_arg & DB_KDB) + current_debugger = KDB_CUR_DB; + /* * Cause a breakpoint trap to the debugger before proceeding * any further if the proper option bit was specified in * the boot flags. */ - - if (halt_in_debugger) { - printf("inline call to debugger(machine_startup)\n"); - Debugger("inline call"); + if (halt_in_debugger && (current_debugger == KDB_CUR_DB)) { + Debugger("inline call to debugger(machine_startup)"); + halt_in_debugger = 0; + active_debugger =1; } -#endif /* MACH_KDB */ +#endif /* MACH_KDB */ - TR_INIT(); + if (PE_parse_boot_arg("preempt", &boot_arg)) { + default_preemption_rate = boot_arg; + } + if (PE_parse_boot_arg("unsafe", &boot_arg)) { + max_unsafe_quanta = boot_arg; + } + if (PE_parse_boot_arg("poll", &boot_arg)) { + max_poll_quanta = boot_arg; + } + if (PE_parse_boot_arg("yield", &boot_arg)) { + sched_poll_yield_shift = boot_arg; + } + if (PE_parse_boot_arg("idlehalt", &boot_arg)) { + idlehalt = boot_arg; + } - printf(version); + machine_conf(); - machine_slot[0].is_cpu = TRUE; - machine_slot[0].running = TRUE; -#ifdef MACH_BSD - /* FIXME */ - machine_slot[0].cpu_type = CPU_TYPE_I386; - machine_slot[0].cpu_subtype = CPU_SUBTYPE_PENTPRO; -#else - machine_slot[0].cpu_type = cpuid_cputype(0); - machine_slot[0].cpu_subtype = CPU_SUBTYPE_AT386; +#if NOTYET + ml_thrm_init(); /* Start thermal monitoring on this processor */ #endif /* * Start the system. */ -#if NCPUS > 1 - mp_desc_init(0); -#endif /* NCPUS */ - - setup_main(); + kernel_bootstrap(); + /*NOTREACHED*/ } -vm_offset_t env_start = 0; /* environment */ -vm_size_t env_size = 0; /* size of environment */ - -/* - * Parse command line arguments. - */ -void -parse_arguments(void) -{ - unsigned int boot_arg; - - if (PE_parse_boot_arg("maxmem", &boot_arg)) - { - mem_size = boot_arg * (1024 * 1024); - } - - if (PE_parse_boot_arg("debug", &boot_arg)) - { - if (boot_arg & DB_HALT) halt_in_debugger = 1; - if (boot_arg & DB_PRT) disableDebugOuput = FALSE; - } -} - -const char * -getenv(const char *name) +static void +machine_conf(void) { - int len = strlen(name); - const char *p = (const char *)env_start; - const char *endp = p + env_size; - - while (p < endp) { - if (len >= endp - p) - break; - if (strncmp(name, p, len) == 0 && *(p + len) == '=') - return p + len + 1; - while (*p++) - ; - } - return NULL; + machine_info.memory_size = mem_size; } -extern void -calibrate_delay(void); - /* * Find devices. The system is alive. */ void machine_init(void) { - int unit; - const char *p; - int n; - - /* - * Adjust delay count before entering drivers - */ - - calibrate_delay(); - /* * Display CPU identification */ cpuid_cpu_display("CPU identification", 0); - cpuid_cache_display("CPU configuration", 0); + cpuid_feature_display("CPU features", 0); -#if MP_V1_1 - mp_v1_1_init(); -#endif /* MP_V1_1 */ + + smp_init(); /* * Set up to use floating point. */ init_fpu(); -#if 0 -#if NPCI > 0 - dma_zones_init(); -#endif /* NPCI > 0 */ -#endif - /* * Configure clock devices. */ clock_config(); + + /* + * Initialize MTRR from boot processor. + */ + mtrr_init(); + + /* + * Set up PAT for boot processor. + */ + pat_init(); + + /* + * Free lowmem pages + */ + x86_lowmem_free(); } /* @@ -407,188 +249,27 @@ int reset_mem_on_reboot = 1; void halt_all_cpus(boolean_t reboot) { - if (reboot) - { - /* - * Tell the BIOS not to clear and test memory. - */ - if (!reset_mem_on_reboot) - *(unsigned short *)phystokv(0x472) = 0x1234; - - printf("MACH Reboot\n"); - PEHaltRestart( kPERestartCPU ); - } - else - { - printf("CPU halted\n"); - PEHaltRestart( kPEHaltCPU ); - } - while(1); -} - -/* - * Basic VM initialization. - */ - -void -i386_init(void) -{ - int i,j; /* Standard index vars. */ - vm_size_t bios_hole_size; - -#ifndef __MACHO__ - /* - * Zero the BSS. - */ - - bzero((char *)&edata,(unsigned)(&end - &edata)); -#endif - - boot_string = &boot_string_store[0]; - - /* - * Initialize the pic prior to any possible call to an spl. - */ - - set_cpu_model(); - vm_set_page_size(); - - /* - * Initialize the Event Trace Analysis Package - * Static Phase: 1 of 2 - */ - etap_init_phase1(); - - /* - * Compute the memory size. - */ - -#if 1 - /* FIXME - * fdisk needs to change to use a sysctl instead of - * opening /dev/kmem and reading out the kernboot structure - */ - - first_addr = (char *)(KERNSTRUCT_ADDR) + sizeof(KERNBOOTSTRUCT); -#else -#if NCPUS > 1 - first_addr = 0x1000; -#else - /* First two pages are used to boot the other cpus. */ - /* TODO - reclaim pages after all cpus have booted */ - - first_addr = 0x3000; -#endif -#endif - - /* BIOS leaves data in low memory */ - last_addr = 1024*1024 + extmem*1024; - - /* extended memory starts at 1MB */ - - bios_hole_size = 1024*1024 - trunc_page((vm_offset_t)(1024 * cnvmem)); - - /* - * Initialize for pmap_free_pages and pmap_next_page. - * These guys should be page-aligned. - */ - - hole_start = trunc_page((vm_offset_t)(1024 * cnvmem)); - hole_end = round_page((vm_offset_t)first_avail); - - /* - * compute mem_size - */ - - if (mem_size != 0) { - if (mem_size < (last_addr) - bios_hole_size) - last_addr = mem_size + bios_hole_size; - } - - first_addr = round_page(first_addr); - last_addr = trunc_page(last_addr); - mem_size = last_addr - bios_hole_size; - - avail_start = first_addr; - avail_end = last_addr; - avail_next = avail_start; - - /* - * Initialize kernel physical map, mapping the - * region from loadpt to avail_start. - * Kernel virtual address starts at VM_KERNEL_MIN_ADDRESS. - */ - - -#if NCPUS > 1 && AT386 - /* - * Must Allocate interrupt stacks before kdb is called and also - * before vm is initialized. Must find out number of cpus first. - */ - /* - * Get number of cpus to boot, passed as an optional argument - * boot: mach [-sah#] # from 0 to 9 is the number of cpus to boot - */ - if (wncpu == -1) { + if (reboot) { /* - * "-1" check above is to allow for old boot loader to pass - * wncpu through boothowto. New boot loader uses environment. + * Tell the BIOS not to clear and test memory. */ - const char *cpus; - if ((cpus = getenv("cpus")) != NULL) { - /* only a single digit for now */ - if ((*cpus > '0') && (*cpus <= '9')) - wncpu = *cpus - '0'; - } else - wncpu = NCPUS; - } - mp_probe_cpus(); - interrupt_stack_alloc(); - -#endif /* NCPUS > 1 && AT386 */ - - pmap_bootstrap(0); - - avail_remaining = atop((avail_end - avail_start) - - (hole_end - hole_start)); -} - -unsigned int -pmap_free_pages(void) -{ - return avail_remaining; -} - -boolean_t -pmap_next_page( - vm_offset_t *addrp) -{ - if (avail_next == avail_end) - return FALSE; - - /* skip the hole */ - - if (avail_next == hole_start) - avail_next = hole_end; - - *addrp = avail_next; - avail_next += PAGE_SIZE; - avail_remaining--; - - return TRUE; -} +#if 0 /* XXX fixme */ + if (!reset_mem_on_reboot) + *(unsigned short *)phystokv(0x472) = 0x1234; +#endif -boolean_t -pmap_valid_page( - vm_offset_t x) -{ - return ((avail_start <= x) && (x < avail_end)); + printf("MACH Reboot\n"); + PEHaltRestart( kPERestartCPU ); + } else { + printf("CPU halted\n"); + PEHaltRestart( kPEHaltCPU ); + } + while(1); } /*XXX*/ void fc_get(mach_timespec_t *ts); #include -#include extern kern_return_t sysclk_gettime( mach_timespec_t *cur_time); void fc_get(mach_timespec_t *ts) { @@ -599,40 +280,31 @@ void Debugger( const char *message) { - printf("Debugger called: <%s>\n", message); - - __asm__("int3"); -} - -void -display_syscall(int syscall) -{ - printf("System call happened %d\n", syscall); -} -#if XPR_DEBUG && (NCPUS == 1 || MP_V1_1) + if (!panic_is_inited) { + postcode(PANIC_HLT); + asm("hlt"); + } -extern kern_return_t sysclk_gettime_interrupts_disabled( - mach_timespec_t *cur_time); + printf("Debugger called: <%s>\n", message); + kprintf("Debugger called: <%s>\n", message); -int xpr_time(void) -{ - mach_timespec_t time; + draw_panic_dialog(); - sysclk_gettime_interrupts_disabled(&time); - return(time.tv_sec*1000000 + time.tv_nsec/1000); + __asm__("int3"); } -#endif /* XPR_DEBUG && (NCPUS == 1 || MP_V1_1) */ -enable_bluebox() +void +enable_bluebox(void) { } -disable_bluebox() +void +disable_bluebox(void) { } char * -machine_boot_info(char *buf, vm_size_t size) +machine_boot_info(char *buf, __unused vm_size_t size) { *buf ='\0'; return buf;