]>
Commit | Line | Data |
---|---|---|
1c79356b A |
1 | /* |
2 | * Copyright (c) 2000 Apple Computer, Inc. All rights reserved. | |
3 | * | |
4 | * @APPLE_LICENSE_HEADER_START@ | |
5 | * | |
e5568f75 A |
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. | |
1c79356b | 11 | * |
e5568f75 A |
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 | |
1c79356b A |
14 | * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, |
15 | * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, | |
e5568f75 A |
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. | |
1c79356b A |
19 | * |
20 | * @APPLE_LICENSE_HEADER_END@ | |
21 | */ | |
22 | /* | |
23 | * @OSF_COPYRIGHT@ | |
24 | */ | |
25 | ||
26 | #include <debug.h> | |
55e303ae | 27 | #include <mach_ldebug.h> |
1c79356b A |
28 | #include <mach_kdb.h> |
29 | #include <mach_kdp.h> | |
30 | ||
31 | #include <kern/misc_protos.h> | |
32 | #include <kern/thread.h> | |
33 | #include <kern/processor.h> | |
34 | #include <machine/machine_routines.h> | |
35 | #include <ppc/boot.h> | |
36 | #include <ppc/proc_reg.h> | |
37 | #include <ppc/misc_protos.h> | |
38 | #include <ppc/pmap.h> | |
39 | #include <ppc/new_screen.h> | |
40 | #include <ppc/exception.h> | |
41 | #include <ppc/Firmware.h> | |
42 | #include <ppc/savearea.h> | |
43 | #include <ppc/low_trace.h> | |
44 | #include <ppc/Diagnostics.h> | |
d52fe63f | 45 | #include <ppc/mem.h> |
55e303ae | 46 | #include <ppc/mappings.h> |
1c79356b A |
47 | |
48 | #include <pexpert/pexpert.h> | |
49 | ||
1c79356b | 50 | extern unsigned int intstack_top_ss; /* declared in start.s */ |
55e303ae | 51 | extern unsigned int debstackptr; /* declared in start.s */ |
1c79356b | 52 | extern unsigned int debstack_top_ss; /* declared in start.s */ |
1c79356b | 53 | |
1c79356b A |
54 | int pc_trace_buf[1024] = {0}; |
55 | int pc_trace_cnt = 1024; | |
56 | ||
55e303ae A |
57 | extern unsigned int extPatchMCK; |
58 | extern unsigned int extPatch32; | |
59 | extern unsigned int hwulckPatch_isync; | |
60 | extern unsigned int hwulckPatch_eieio; | |
61 | extern unsigned int hwulckbPatch_isync; | |
62 | extern unsigned int hwulckbPatch_eieio; | |
63 | extern unsigned int mulckPatch_isync; | |
64 | extern unsigned int mulckPatch_eieio; | |
65 | extern unsigned int sulckPatch_isync; | |
66 | extern unsigned int sulckPatch_eieio; | |
67 | extern unsigned int retfsectPatch_eieio; | |
68 | extern unsigned int retfsectPatch_isync; | |
69 | ||
70 | int forcenap = 0; | |
71 | ||
72 | patch_entry_t patch_table[PATCH_TABLE_SIZE] = { | |
73 | &extPatch32, 0x60000000, PATCH_FEATURE, PatchExt32, | |
74 | &extPatchMCK, 0x60000000, PATCH_PROCESSOR, CPU_SUBTYPE_POWERPC_970, | |
75 | &hwulckPatch_isync, 0x60000000, PATCH_FEATURE, PatchLwsync, | |
76 | &hwulckPatch_eieio, 0x7c2004ac, PATCH_FEATURE, PatchLwsync, | |
77 | &hwulckbPatch_isync, 0x60000000, PATCH_FEATURE, PatchLwsync, | |
78 | &hwulckbPatch_eieio, 0x7c2004ac, PATCH_FEATURE, PatchLwsync, | |
79 | &mulckPatch_isync, 0x60000000, PATCH_FEATURE, PatchLwsync, | |
80 | &mulckPatch_eieio, 0x7c2004ac, PATCH_FEATURE, PatchLwsync, | |
81 | &sulckPatch_isync, 0x60000000, PATCH_FEATURE, PatchLwsync, | |
82 | &sulckPatch_eieio, 0x7c2004ac, PATCH_FEATURE, PatchLwsync, | |
83 | #if !MACH_LDEBUG | |
84 | &retfsectPatch_isync, 0x60000000, PATCH_FEATURE, PatchLwsync, | |
85 | &retfsectPatch_eieio, 0x7c2004ac, PATCH_FEATURE, PatchLwsync | |
86 | #else | |
87 | 0, 0, PATCH_INVALID, 0, | |
88 | 0, 0, PATCH_INVALID, 0 | |
89 | #endif | |
90 | }; | |
91 | ||
1c79356b A |
92 | void ppc_init(boot_args *args) |
93 | { | |
94 | int i; | |
95 | unsigned long *src,*dst; | |
96 | char *str; | |
97 | unsigned long addr, videoAddr; | |
98 | unsigned int maxmem; | |
e5568f75 | 99 | uint64_t xmaxmem, newhid; |
9bccf70c | 100 | unsigned int cputrace; |
e5568f75 | 101 | unsigned int novmx, fhrdl1; |
1c79356b | 102 | extern vm_offset_t static_memory_end; |
55e303ae A |
103 | thread_t thread; |
104 | mapping *mp; | |
a3d08fcd A |
105 | |
106 | ||
1c79356b A |
107 | /* |
108 | * Setup per_proc info for first cpu. | |
109 | */ | |
110 | ||
111 | per_proc_info[0].cpu_number = 0; | |
112 | per_proc_info[0].cpu_flags = 0; | |
113 | per_proc_info[0].istackptr = 0; /* we're on the interrupt stack */ | |
114 | per_proc_info[0].intstack_top_ss = intstack_top_ss; | |
1c79356b A |
115 | per_proc_info[0].debstackptr = debstackptr; |
116 | per_proc_info[0].debstack_top_ss = debstack_top_ss; | |
0b4e3aa0 | 117 | per_proc_info[0].interrupts_enabled = 0; |
55e303ae | 118 | per_proc_info[0].pp_preemption_count = -1; |
9bccf70c A |
119 | per_proc_info[0].pp_simple_lock_count = 0; |
120 | per_proc_info[0].pp_interrupt_level = 0; | |
55e303ae | 121 | per_proc_info[0].need_ast = (unsigned int)&need_ast[0]; |
9bccf70c A |
122 | per_proc_info[0].FPU_owner = 0; |
123 | per_proc_info[0].VMX_owner = 0; | |
a3d08fcd | 124 | per_proc_info[0].rtcPop = 0xFFFFFFFFFFFFFFFFULL; |
55e303ae A |
125 | mp = (mapping *)per_proc_info[0].ppCIOmp; |
126 | mp->mpFlags = 0x01000000 | mpSpecial | 1; | |
127 | mp->mpSpace = invalSpace; | |
1c79356b A |
128 | |
129 | machine_slot[0].is_cpu = TRUE; | |
130 | ||
55e303ae A |
131 | thread_bootstrap(); |
132 | ||
133 | thread = current_act(); | |
134 | thread->mact.curctx = &thread->mact.facctx; | |
135 | thread->mact.facctx.facAct = thread; | |
136 | thread->mact.cioSpace = invalSpace; /* Initialize copyin/out space to invalid */ | |
137 | thread->mact.preemption_count = 1; | |
138 | ||
1c79356b A |
139 | cpu_init(); |
140 | ||
141 | /* | |
142 | * Setup some processor related structures to satisfy funnels. | |
143 | * Must be done before using unparallelized device drivers. | |
144 | */ | |
145 | processor_ptr[0] = &processor_array[0]; | |
146 | master_cpu = 0; | |
147 | master_processor = cpu_to_processor(master_cpu); | |
148 | ||
55e303ae A |
149 | static_memory_end = round_page_32(args->topOfKernelData);; |
150 | ||
151 | PE_init_platform(FALSE, args); /* Get platform expert set up */ | |
de355530 | 152 | |
55e303ae A |
153 | if (!PE_parse_boot_arg("novmx", &novmx)) novmx=0; /* Special run without VMX? */ |
154 | if(novmx) { /* Yeah, turn it off */ | |
155 | for(i = 0; i < NCPUS; i++) { /* Cycle through all potential processors */ | |
156 | per_proc_info[i].pf.Available &= ~pfAltivec; /* Turn off Altivec available */ | |
157 | } | |
158 | __asm__ volatile("mtsprg 2,%0" : : "r" (per_proc_info[0].pf.Available)); /* Set live value */ | |
159 | } | |
de355530 | 160 | |
55e303ae A |
161 | if (!PE_parse_boot_arg("fn", &forcenap)) forcenap = 0; /* If force nap not set, make 0 */ |
162 | else { | |
163 | if(forcenap < 2) forcenap = forcenap + 1; /* Else set 1 for off, 2 for on */ | |
164 | else forcenap = 0; /* Clear for error case */ | |
1c79356b A |
165 | } |
166 | ||
1c79356b A |
167 | if (!PE_parse_boot_arg("diag", &dgWork.dgFlags)) dgWork.dgFlags=0; /* Set diagnostic flags */ |
168 | if(dgWork.dgFlags & enaExpTrace) trcWork.traceMask = 0xFFFFFFFF; /* If tracing requested, enable it */ | |
169 | ||
9bccf70c A |
170 | if(PE_parse_boot_arg("ctrc", &cputrace)) { /* See if tracing is limited to a specific cpu */ |
171 | trcWork.traceMask = (trcWork.traceMask & 0xFFFFFFF0) | (cputrace & 0xF); /* Limit to 4 */ | |
172 | } | |
173 | ||
55e303ae | 174 | if(!PE_parse_boot_arg("tb", &trcWork.traceSize)) { /* See if non-default trace buffer size */ |
de355530 | 175 | #if DEBUG |
55e303ae A |
176 | trcWork.traceSize = 32; /* Default 32 page trace table for DEBUG */ |
177 | #else | |
178 | trcWork.traceSize = 8; /* Default 8 page trace table for RELEASE */ | |
179 | #endif | |
de355530 | 180 | } |
de355530 | 181 | |
55e303ae A |
182 | if(trcWork.traceSize < 1) trcWork.traceSize = 1; /* Minimum size of 1 page */ |
183 | if(trcWork.traceSize > 256) trcWork.traceSize = 256; /* Maximum size of 256 pages */ | |
e5568f75 | 184 | trcWork.traceSize = trcWork.traceSize * 4096; /* Change page count to size */ |
55e303ae | 185 | |
1c79356b | 186 | if (!PE_parse_boot_arg("maxmem", &maxmem)) |
55e303ae | 187 | xmaxmem=0; |
1c79356b | 188 | else |
55e303ae | 189 | xmaxmem = (uint64_t)maxmem * (1024 * 1024); |
1c79356b | 190 | |
55e303ae A |
191 | /* |
192 | * VM initialization, after this we're using page tables... | |
193 | */ | |
1c79356b | 194 | |
55e303ae A |
195 | ppc_vm_init(xmaxmem, args); |
196 | ||
e5568f75 A |
197 | if(per_proc_info[0].pf.Available & pf64Bit) { /* Are we on a 64-bit machine */ |
198 | if(PE_parse_boot_arg("fhrdl1", &fhrdl1)) { /* Have they supplied "Force Hardware Recovery of Data cache level 1 errors? */ | |
199 | newhid = per_proc_info[0].pf.pfHID5; /* Get the old HID5 */ | |
200 | if(fhrdl1 < 2) { | |
201 | newhid &= 0xFFFFFFFFFFFFDFFFULL; /* Clear the old one */ | |
202 | newhid |= (fhrdl1 ^ 1) << 13; /* Set new value to enable machine check recovery */ | |
203 | for(i = 0; i < NCPUS; i++) per_proc_info[i].pf.pfHID5 = newhid; /* Set all shadows */ | |
204 | hid5set64(newhid); /* Set the hid for this processir */ | |
205 | } | |
206 | } | |
207 | } | |
208 | ||
209 | ||
1c79356b A |
210 | PE_init_platform(TRUE, args); |
211 | ||
212 | machine_startup(args); | |
213 | } | |
214 | ||
215 | ppc_init_cpu( | |
216 | struct per_proc_info *proc_info) | |
217 | { | |
218 | int i; | |
1c79356b | 219 | |
55e303ae A |
220 | proc_info->cpu_flags &= ~SleepState; |
221 | ||
9bccf70c | 222 | if(!(proc_info->next_savearea)) /* Do we have a savearea set up already? */ |
55e303ae | 223 | proc_info->next_savearea = (uint64_t)save_get_init(); /* Get a savearea */ |
1c79356b A |
224 | |
225 | cpu_init(); | |
55e303ae | 226 | |
1c79356b A |
227 | ppc_vm_cpu_init(proc_info); |
228 | ||
229 | ml_thrm_init(); /* Start thermal monitoring on this processor */ | |
230 | ||
231 | slave_main(); | |
232 | } |