Annotation of XNU/osfmk/ppc/machine_routines.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
                      3:  *
                      4:  * @APPLE_LICENSE_HEADER_START@
                      5:  * 
                      6:  * The contents of this file constitute Original Code as defined in and
                      7:  * are subject to the Apple Public Source License Version 1.1 (the
                      8:  * "License").  You may not use this file except in compliance with the
                      9:  * License.  Please obtain a copy of the License at
                     10:  * http://www.apple.com/publicsource and read it before using this file.
                     11:  * 
                     12:  * This Original Code and all software distributed under the License are
                     13:  * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
                     14:  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
                     15:  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
                     16:  * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
                     17:  * License for the specific language governing rights and limitations
                     18:  * under the License.
                     19:  * 
                     20:  * @APPLE_LICENSE_HEADER_END@
                     21:  */
                     22: #include <ppc/machine_routines.h>
                     23: #include <ppc/exception.h>
                     24: #include <ppc/misc_protos.h>
                     25: #include <ppc/Firmware.h>
                     26: #include <vm/vm_page.h>
                     27: #include <ppc/pmap.h>
                     28: #include <ppc/proc_reg.h>
                     29: #include <kern/processor.h>
                     30: 
                     31: boolean_t get_interrupts_enabled(void);
                     32: extern boolean_t set_interrupts_enabled(boolean_t);
                     33: 
                     34: /* Map memory map IO space */
                     35: vm_offset_t 
                     36: ml_io_map(
                     37:        vm_offset_t phys_addr, 
                     38:        vm_size_t size)
                     39: {
                     40:        return(io_map(phys_addr,size));
                     41: }
                     42: 
                     43: /* static memory allocation */
                     44: vm_offset_t 
                     45: ml_static_malloc(
                     46:        vm_size_t size)
                     47: {
                     48:        extern vm_offset_t static_memory_end;
                     49:        extern boolean_t pmap_initialized;
                     50:        vm_offset_t vaddr;
                     51: 
                     52:        if (pmap_initialized)
                     53:                return((vm_offset_t)NULL);
                     54:        else {
                     55:                vaddr = static_memory_end;
                     56:                static_memory_end = round_page(vaddr+size);
                     57:                return(vaddr);
                     58:        }
                     59: }
                     60: 
                     61: vm_offset_t
                     62: ml_static_ptovirt(
                     63:        vm_offset_t paddr)
                     64: {
                     65:        extern vm_offset_t static_memory_end;
                     66:        vm_offset_t vaddr;
                     67: 
                     68:        /* Static memory is map V=R */
                     69:        vaddr = paddr;
                     70:        if ( (vaddr < static_memory_end) && (pmap_extract(kernel_pmap, vaddr)==paddr) )
                     71:                return(vaddr);
                     72:        else
                     73:                return((vm_offset_t)NULL);
                     74: }
                     75: 
                     76: void
                     77: ml_static_mfree(
                     78:        vm_offset_t vaddr,
                     79:        vm_size_t size)
                     80: {
                     81:        vm_offset_t paddr_cur, vaddr_cur;
                     82: 
                     83:        for (vaddr_cur = round_page(vaddr);
                     84:             vaddr_cur < trunc_page(vaddr+size);
                     85:             vaddr_cur += PAGE_SIZE) {
                     86:                paddr_cur = pmap_extract(kernel_pmap, vaddr_cur);
                     87:                if (paddr_cur != (vm_offset_t)NULL) {
                     88:                        vm_page_wire_count--;
                     89:                        pmap_remove(kernel_pmap, vaddr_cur, vaddr_cur+PAGE_SIZE);
                     90:                        vm_page_create(paddr_cur,paddr_cur+PAGE_SIZE);
                     91:                }
                     92:        }
                     93: }
                     94: 
                     95: /* virtual to physical on wired pages */
                     96: vm_offset_t ml_vtophys(
                     97:        vm_offset_t vaddr)
                     98: {
                     99:        return(pmap_extract(kernel_pmap, vaddr));
                    100: }
                    101: 
                    102: /* Initialize Interrupts */
                    103: void ml_install_interrupt_handler(
                    104:        void *nub,
                    105:        int source,
                    106:        void *target,
                    107:        IOInterruptHandler handler,
                    108:        void *refCon)
                    109: {
                    110:        int     current_cpu;
                    111:        boolean_t current_state;
                    112: 
                    113:        current_state = ml_get_interrupts_enabled();
                    114: 
                    115:        current_cpu = cpu_number();
                    116:        per_proc_info[current_cpu].interrupt_nub     = nub;
                    117:        per_proc_info[current_cpu].interrupt_source  = source;
                    118:        per_proc_info[current_cpu].interrupt_target  = target;
                    119:        per_proc_info[current_cpu].interrupt_handler = handler;
                    120:        per_proc_info[current_cpu].interrupt_refCon  = refCon;
                    121:        per_proc_info[current_cpu].get_interrupts_enabled 
                    122:                                                = get_interrupts_enabled;
                    123:        per_proc_info[current_cpu].set_interrupts_enabled 
                    124:                                                = set_interrupts_enabled;  
                    125: 
                    126:        (void) ml_set_interrupts_enabled(current_state);
                    127: }
                    128: 
                    129: boolean_t fake_get_interrupts_enabled(void)
                    130: {
                    131:        /*
                    132:         * The scheduler is not active on this cpu. There is no need to disable 
                    133:         * preemption. The current thread wont be dispatched on anhother cpu.
                    134:         */
                    135:        return(per_proc_info[cpu_number()].cpu_flags & turnEEon);
                    136: }
                    137: 
                    138: boolean_t fake_set_interrupts_enabled(boolean_t enable)
                    139: {
                    140:        boolean_t interrupt_state_prev;
                    141: 
                    142:        /*
                    143:         * The scheduler is not active on this cpu. There is no need to disable 
                    144:         * preemption. The current thread wont be dispatched on anhother cpu.
                    145:         */
                    146:        interrupt_state_prev = 
                    147:                (per_proc_info[cpu_number()].cpu_flags & turnEEon) != 0;
                    148:        if (interrupt_state_prev != enable)
                    149:                per_proc_info[cpu_number()].cpu_flags ^= turnEEon;
                    150:        return(interrupt_state_prev);
                    151: }
                    152: 
                    153: /* Get Interrupts Enabled */
                    154: boolean_t ml_get_interrupts_enabled(void)
                    155: {
                    156:        return(per_proc_info[cpu_number()].get_interrupts_enabled());
                    157: }
                    158: 
                    159: boolean_t get_interrupts_enabled(void)
                    160: {
                    161:        return((mfmsr() & MASK(MSR_EE)) != 0);
                    162: }
                    163: 
                    164: /* Set Interrupts Enabled */
                    165: boolean_t ml_set_interrupts_enabled(boolean_t enable)
                    166: {
                    167:        return(per_proc_info[cpu_number()].set_interrupts_enabled(enable));
                    168: }
                    169: 
                    170: /* Check if running at interrupt context */
                    171: boolean_t ml_at_interrupt_context(void)
                    172: {
                    173:        /*
                    174:         * If running at interrupt context, the current thread won't be 
                    175:         * dispatched on another cpu. There is no need to turn off preemption.
                    176:         */
                    177:        return (per_proc_info[cpu_number()].istackptr == 0);
                    178: }
                    179: 
                    180: /* Generate a fake interrupt */
                    181: void ml_cause_interrupt(void)
                    182: {
                    183:        CreateFakeIO();
                    184: }
                    185: 
                    186: void machine_clock_assist(void)
                    187: {
                    188:        if (per_proc_info[cpu_number()].get_interrupts_enabled == fake_get_interrupts_enabled)
                    189:                CreateFakeDEC();
                    190: }
                    191: 
                    192: extern void cpu_signal_handler(void);
                    193: 
                    194: kern_return_t
                    195: ml_processor_register(
                    196:        cpu_id_t        cpu_id,
                    197:        vm_offset_t     start_paddr,
                    198:        processor_t     *processor,
                    199:        ipi_handler_t   *ipi_handler,
                    200:        boolean_t       boot_cpu)
                    201: {
                    202:        kern_return_t ret;
                    203:        int target_cpu;
                    204: 
                    205:        if (boot_cpu == FALSE) {
                    206:                 if (cpu_register(&target_cpu) != KERN_SUCCESS)
                    207:                        return KERN_FAILURE;
                    208:        } else {
                    209:                /* boot_cpu is always 0 */
                    210:                target_cpu= 0;
                    211:        }
                    212: 
                    213:        per_proc_info[target_cpu].cpu_id = cpu_id;
                    214:        per_proc_info[target_cpu].start_paddr = start_paddr;
                    215:        *processor = cpu_to_processor(target_cpu);
                    216:        *ipi_handler = cpu_signal_handler;
                    217: 
                    218:        return KERN_SUCCESS;
                    219: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.