Revert the previous changes to EST. The used hack had an obvious flaw: the acpicpu(4) driver should attach even if the existing frequency management code fails to attach, mainly because ACPI is the only proper way to deal with EST on new Intel system. Use a more drastic hack to deal with this: when acpicpu(4) attachs, it tears down any existing sysctl(8) controls and installs identical ones in place. Upon detachment, the initialization function of the existing EST is called.diff -r1.8 -r1.9 src/sys/arch/x86/acpi/acpi_cpu_md.c
(jruoho)
--- src/sys/arch/x86/acpi/acpi_cpu_md.c 2010/08/09 13:41:39 1.8
+++ src/sys/arch/x86/acpi/acpi_cpu_md.c 2010/08/09 15:46:17 1.9
@@ -1,14 +1,14 @@ | @@ -1,14 +1,14 @@ | |||
1 | /* $NetBSD: acpi_cpu_md.c,v 1.8 2010/08/09 13:41:39 jruoho Exp $ */ | 1 | /* $NetBSD: acpi_cpu_md.c,v 1.9 2010/08/09 15:46:17 jruoho Exp $ */ | |
2 | 2 | |||
3 | /*- | 3 | /*- | |
4 | * Copyright (c) 2010 Jukka Ruohonen <jruohonen@iki.fi> | 4 | * Copyright (c) 2010 Jukka Ruohonen <jruohonen@iki.fi> | |
5 | * All rights reserved. | 5 | * All rights reserved. | |
6 | * | 6 | * | |
7 | * Redistribution and use in source and binary forms, with or without | 7 | * Redistribution and use in source and binary forms, with or without | |
8 | * modification, are permitted provided that the following conditions | 8 | * modification, are permitted provided that the following conditions | |
9 | * are met: | 9 | * are met: | |
10 | * | 10 | * | |
11 | * 1. Redistributions of source code must retain the above copyright | 11 | * 1. Redistributions of source code must retain the above copyright | |
12 | * notice, this list of conditions and the following disclaimer. | 12 | * notice, this list of conditions and the following disclaimer. | |
13 | * 2. Redistributions in binary form must reproduce the above copyright | 13 | * 2. Redistributions in binary form must reproduce the above copyright | |
14 | * notice, this list of conditions and the following disclaimer in the | 14 | * notice, this list of conditions and the following disclaimer in the | |
@@ -17,46 +17,47 @@ | @@ -17,46 +17,47 @@ | |||
17 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND | 17 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND | |
18 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | 18 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
19 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | 19 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
20 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | 20 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | |
21 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | 21 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |
22 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | 22 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |
23 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | 23 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |
24 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | 24 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |
25 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | 25 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |
26 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | 26 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
27 | * SUCH DAMAGE. | 27 | * SUCH DAMAGE. | |
28 | */ | 28 | */ | |
29 | #include <sys/cdefs.h> | 29 | #include <sys/cdefs.h> | |
30 | __KERNEL_RCSID(0, "$NetBSD: acpi_cpu_md.c,v 1.8 2010/08/09 13:41:39 jruoho Exp $"); | 30 | __KERNEL_RCSID(0, "$NetBSD: acpi_cpu_md.c,v 1.9 2010/08/09 15:46:17 jruoho Exp $"); | |
31 | 31 | |||
32 | #include <sys/param.h> | 32 | #include <sys/param.h> | |
33 | #include <sys/bus.h> | 33 | #include <sys/bus.h> | |
34 | #include <sys/kcore.h> | 34 | #include <sys/kcore.h> | |
35 | #include <sys/sysctl.h> | 35 | #include <sys/sysctl.h> | |
36 | #include <sys/xcall.h> | 36 | #include <sys/xcall.h> | |
37 | 37 | |||
38 | #include <x86/cpu.h> | 38 | #include <x86/cpu.h> | |
39 | #include <x86/cpufunc.h> | 39 | #include <x86/cpufunc.h> | |
40 | #include <x86/cputypes.h> | 40 | #include <x86/cputypes.h> | |
41 | #include <x86/cpuvar.h> | 41 | #include <x86/cpuvar.h> | |
42 | #include <x86/cpu_msr.h> | 42 | #include <x86/cpu_msr.h> | |
43 | #include <x86/machdep.h> | 43 | #include <x86/machdep.h> | |
44 | 44 | |||
45 | #include <dev/acpi/acpica.h> | 45 | #include <dev/acpi/acpica.h> | |
46 | #include <dev/acpi/acpi_cpu.h> | 46 | #include <dev/acpi/acpi_cpu.h> | |
47 | 47 | |||
48 | static char native_idle_text[16]; | 48 | static char native_idle_text[16]; | |
49 | void (*native_idle)(void) = NULL; | 49 | void (*native_idle)(void) = NULL; | |
50 | void (*native_cpu_freq_init)(int) = NULL; | |||
50 | 51 | |||
51 | static int acpicpu_md_pstate_sysctl_get(SYSCTLFN_PROTO); | 52 | static int acpicpu_md_pstate_sysctl_get(SYSCTLFN_PROTO); | |
52 | static int acpicpu_md_pstate_sysctl_set(SYSCTLFN_PROTO); | 53 | static int acpicpu_md_pstate_sysctl_set(SYSCTLFN_PROTO); | |
53 | static int acpicpu_md_pstate_sysctl_all(SYSCTLFN_PROTO); | 54 | static int acpicpu_md_pstate_sysctl_all(SYSCTLFN_PROTO); | |
54 | 55 | |||
55 | extern uint32_t cpus_running; | 56 | extern uint32_t cpus_running; | |
56 | extern struct acpicpu_softc **acpicpu_sc; | 57 | extern struct acpicpu_softc **acpicpu_sc; | |
57 | 58 | |||
58 | uint32_t | 59 | uint32_t | |
59 | acpicpu_md_cap(void) | 60 | acpicpu_md_cap(void) | |
60 | { | 61 | { | |
61 | struct cpu_info *ci = curcpu(); | 62 | struct cpu_info *ci = curcpu(); | |
62 | uint32_t val = 0; | 63 | uint32_t val = 0; | |
@@ -195,60 +196,136 @@ acpicpu_md_idle_enter(int method, int st | @@ -195,60 +196,136 @@ acpicpu_md_idle_enter(int method, int st | |||
195 | if (__predict_false(ci->ci_want_resched) != 0) { | 196 | if (__predict_false(ci->ci_want_resched) != 0) { | |
196 | x86_enable_intr(); | 197 | x86_enable_intr(); | |
197 | return; | 198 | return; | |
198 | } | 199 | } | |
199 | 200 | |||
200 | x86_stihlt(); | 201 | x86_stihlt(); | |
201 | break; | 202 | break; | |
202 | } | 203 | } | |
203 | } | 204 | } | |
204 | 205 | |||
205 | int | 206 | int | |
206 | acpicpu_md_pstate_start(void) | 207 | acpicpu_md_pstate_start(void) | |
207 | { | 208 | { | |
209 | const struct sysctlnode *fnode, *mnode, *rnode; | |||
210 | const char *str; | |||
211 | int rv; | |||
208 | 212 | |||
209 | cpu_freq_sysctl_get = acpicpu_md_pstate_sysctl_get; | 213 | switch (cpu_vendor) { | |
210 | cpu_freq_sysctl_set = acpicpu_md_pstate_sysctl_set; | 214 | ||
211 | cpu_freq_sysctl_all = acpicpu_md_pstate_sysctl_all; | 215 | case CPUVENDOR_INTEL: | |
216 | str = "est"; | |||
217 | break; | |||
218 | ||||
219 | default: | |||
220 | return ENODEV; | |||
221 | } | |||
222 | ||||
223 | /* | |||
224 | * A kludge for backwards compatibility. | |||
225 | */ | |||
226 | native_cpu_freq_init = cpu_freq_init; | |||
227 | ||||
228 | if (cpu_freq_sysctllog != NULL) { | |||
229 | sysctl_teardown(&cpu_freq_sysctllog); | |||
230 | cpu_freq_sysctllog = NULL; | |||
231 | } | |||
232 | ||||
233 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, NULL, &rnode, | |||
234 | CTLFLAG_PERMANENT, CTLTYPE_NODE, "machdep", NULL, | |||
235 | NULL, 0, NULL, 0, CTL_MACHDEP, CTL_EOL); | |||
236 | ||||
237 | if (rv != 0) | |||
238 | goto fail; | |||
239 | ||||
240 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, &rnode, &mnode, | |||
241 | 0, CTLTYPE_NODE, str, NULL, | |||
242 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL); | |||
243 | ||||
244 | if (rv != 0) | |||
245 | goto fail; | |||
246 | ||||
247 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, &mnode, &fnode, | |||
248 | 0, CTLTYPE_NODE, "frequency", NULL, | |||
249 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL); | |||
250 | ||||
251 | if (rv != 0) | |||
252 | goto fail; | |||
253 | ||||
254 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, &fnode, &rnode, | |||
255 | CTLFLAG_READWRITE, CTLTYPE_INT, "target", NULL, | |||
256 | acpicpu_md_pstate_sysctl_set, 0, NULL, 0, CTL_CREATE, CTL_EOL); | |||
257 | ||||
258 | if (rv != 0) | |||
259 | goto fail; | |||
260 | ||||
261 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, &fnode, &rnode, | |||
262 | CTLFLAG_READONLY, CTLTYPE_INT, "current", NULL, | |||
263 | acpicpu_md_pstate_sysctl_get, 0, NULL, 0, CTL_CREATE, CTL_EOL); | |||
264 | ||||
265 | if (rv != 0) | |||
266 | goto fail; | |||
267 | ||||
268 | rv = sysctl_createv(&cpu_freq_sysctllog, 0, &fnode, &rnode, | |||
269 | CTLFLAG_READONLY, CTLTYPE_STRING, "available", NULL, | |||
270 | acpicpu_md_pstate_sysctl_all, 0, NULL, 0, CTL_CREATE, CTL_EOL); | |||
271 | ||||
272 | if (rv != 0) | |||
273 | goto fail; | |||
212 | 274 | |||
213 | return 0; | 275 | return 0; | |
276 | ||||
277 | fail: | |||
278 | if (cpu_freq_sysctllog != NULL) { | |||
279 | sysctl_teardown(&cpu_freq_sysctllog); | |||
280 | cpu_freq_sysctllog = NULL; | |||
281 | } | |||
282 | ||||
283 | if (native_cpu_freq_init != NULL) | |||
284 | (*native_cpu_freq_init)(cpu_vendor); | |||
285 | ||||
286 | return rv; | |||
214 | } | 287 | } | |
215 | 288 | |||
216 | int | 289 | int | |
217 | acpicpu_md_pstate_stop(void) | 290 | acpicpu_md_pstate_stop(void) | |
218 | { | 291 | { | |
219 | 292 | |||
220 | cpu_freq_sysctl_get = NULL; | 293 | if (cpu_freq_sysctllog != NULL) { | |
221 | cpu_freq_sysctl_set = NULL; | 294 | sysctl_teardown(&cpu_freq_sysctllog); | |
222 | cpu_freq_sysctl_all = NULL; | 295 | cpu_freq_sysctllog = NULL; | |
296 | } | |||
297 | ||||
298 | if (native_cpu_freq_init != NULL) | |||
299 | (*native_cpu_freq_init)(cpu_vendor); | |||
223 | 300 | |||
224 | return 0; | 301 | return 0; | |
225 | } | 302 | } | |
226 | 303 | |||
227 | static int | 304 | static int | |
228 | acpicpu_md_pstate_sysctl_get(SYSCTLFN_ARGS) | 305 | acpicpu_md_pstate_sysctl_get(SYSCTLFN_ARGS) | |
229 | { | 306 | { | |
230 | struct cpu_info *ci = curcpu(); | 307 | struct cpu_info *ci = curcpu(); | |
231 | struct acpicpu_softc *sc; | 308 | struct acpicpu_softc *sc; | |
232 | struct sysctlnode node; | 309 | struct sysctlnode node; | |
233 | uint32_t freq; | 310 | uint32_t freq; | |
234 | int err; | 311 | int err; | |
235 | 312 | |||
236 | /* | 313 | /* | |
237 | * We can use any ACPI CPU to manipulate the | 314 | * We can use any ACPI CPU to manipulate the | |
238 | * frequencies. In MP environments all CPUs | 315 | * frequencies. In MP environments all CPUs | |
239 | * are mandated to support the same number of | 316 | * are mandated to support the same number of | |
240 | * P-states and each state must have identical | 317 | * P-states and each state must have identical | |
241 | * parameters across CPUs. | 318 | * parameters across processors. | |
242 | */ | 319 | */ | |
243 | sc = acpicpu_sc[ci->ci_acpiid]; | 320 | sc = acpicpu_sc[ci->ci_acpiid]; | |
244 | 321 | |||
245 | if (sc == NULL) | 322 | if (sc == NULL) | |
246 | return ENXIO; | 323 | return ENXIO; | |
247 | 324 | |||
248 | err = acpicpu_pstate_get(sc, &freq); | 325 | err = acpicpu_pstate_get(sc, &freq); | |
249 | 326 | |||
250 | if (err != 0) | 327 | if (err != 0) | |
251 | return err; | 328 | return err; | |
252 | 329 | |||
253 | node = *rnode; | 330 | node = *rnode; | |
254 | node.sysctl_data = &freq; | 331 | node.sysctl_data = &freq; |
--- src/sys/arch/x86/include/cpuvar.h 2010/08/09 04:18:48 1.36
+++ src/sys/arch/x86/include/cpuvar.h 2010/08/09 15:46:17 1.37
@@ -1,14 +1,14 @@ | @@ -1,14 +1,14 @@ | |||
1 | /* $NetBSD: cpuvar.h,v 1.36 2010/08/09 04:18:48 jruoho Exp $ */ | 1 | /* $NetBSD: cpuvar.h,v 1.37 2010/08/09 15:46:17 jruoho Exp $ */ | |
2 | 2 | |||
3 | /*- | 3 | /*- | |
4 | * Copyright (c) 2000, 2007 The NetBSD Foundation, Inc. | 4 | * Copyright (c) 2000, 2007 The NetBSD Foundation, Inc. | |
5 | * All rights reserved. | 5 | * All rights reserved. | |
6 | * | 6 | * | |
7 | * This code is derived from software contributed to The NetBSD Foundation | 7 | * This code is derived from software contributed to The NetBSD Foundation | |
8 | * by RedBack Networks Inc. | 8 | * by RedBack Networks Inc. | |
9 | * | 9 | * | |
10 | * Author: Bill Sommerfeld | 10 | * Author: Bill Sommerfeld | |
11 | * | 11 | * | |
12 | * Redistribution and use in source and binary forms, with or without | 12 | * Redistribution and use in source and binary forms, with or without | |
13 | * modification, are permitted provided that the following conditions | 13 | * modification, are permitted provided that the following conditions | |
14 | * are met: | 14 | * are met: | |
@@ -132,28 +132,27 @@ void coretemp_register(struct cpu_info * | @@ -132,28 +132,27 @@ void coretemp_register(struct cpu_info * | |||
132 | 132 | |||
133 | #ifdef INTEL_ONDEMAND_CLOCKMOD | 133 | #ifdef INTEL_ONDEMAND_CLOCKMOD | |
134 | void clockmod_init(void); | 134 | void clockmod_init(void); | |
135 | #endif | 135 | #endif | |
136 | 136 | |||
137 | #ifdef ENHANCED_SPEEDSTEP | 137 | #ifdef ENHANCED_SPEEDSTEP | |
138 | void est_init(int); | 138 | void est_init(int); | |
139 | int via_get_bus_clock(struct cpu_info *); | 139 | int via_get_bus_clock(struct cpu_info *); | |
140 | int viac7_get_bus_clock(struct cpu_info *); | 140 | int viac7_get_bus_clock(struct cpu_info *); | |
141 | int p3_get_bus_clock(struct cpu_info *); | 141 | int p3_get_bus_clock(struct cpu_info *); | |
142 | int p4_get_bus_clock(struct cpu_info *); | 142 | int p4_get_bus_clock(struct cpu_info *); | |
143 | #endif | 143 | #endif | |
144 | 144 | |||
145 | extern int (*cpu_freq_sysctl_get)(SYSCTLFN_PROTO); | 145 | extern void (*cpu_freq_init)(int); | |
146 | extern int (*cpu_freq_sysctl_set)(SYSCTLFN_PROTO); | 146 | extern struct sysctllog *cpu_freq_sysctllog; | |
147 | extern int (*cpu_freq_sysctl_all)(SYSCTLFN_PROTO); | |||
148 | 147 | |||
149 | void cpu_get_tsc_freq(struct cpu_info *); | 148 | void cpu_get_tsc_freq(struct cpu_info *); | |
150 | void pat_init(struct cpu_info *); | 149 | void pat_init(struct cpu_info *); | |
151 | 150 | |||
152 | extern int cpu_vendor; | 151 | extern int cpu_vendor; | |
153 | extern bool x86_mp_online; | 152 | extern bool x86_mp_online; | |
154 | 153 | |||
155 | extern uint32_t cpu_feature[5]; | 154 | extern uint32_t cpu_feature[5]; | |
156 | 155 | |||
157 | #endif /* _KERNEL */ | 156 | #endif /* _KERNEL */ | |
158 | 157 | |||
159 | #endif /* !_X86_CPUVAR_H_ */ | 158 | #endif /* !_X86_CPUVAR_H_ */ |
--- src/sys/arch/x86/x86/cpu.c 2010/08/09 04:18:48 1.75
+++ src/sys/arch/x86/x86/cpu.c 2010/08/09 15:46:17 1.76
@@ -1,14 +1,14 @@ | @@ -1,14 +1,14 @@ | |||
1 | /* $NetBSD: cpu.c,v 1.75 2010/08/09 04:18:48 jruoho Exp $ */ | 1 | /* $NetBSD: cpu.c,v 1.76 2010/08/09 15:46:17 jruoho Exp $ */ | |
2 | 2 | |||
3 | /*- | 3 | /*- | |
4 | * Copyright (c) 2000, 2006, 2007, 2008 The NetBSD Foundation, Inc. | 4 | * Copyright (c) 2000, 2006, 2007, 2008 The NetBSD Foundation, Inc. | |
5 | * All rights reserved. | 5 | * All rights reserved. | |
6 | * | 6 | * | |
7 | * This code is derived from software contributed to The NetBSD Foundation | 7 | * This code is derived from software contributed to The NetBSD Foundation | |
8 | * by Bill Sommerfeld of RedBack Networks Inc, and by Andrew Doran. | 8 | * by Bill Sommerfeld of RedBack Networks Inc, and by Andrew Doran. | |
9 | * | 9 | * | |
10 | * Redistribution and use in source and binary forms, with or without | 10 | * Redistribution and use in source and binary forms, with or without | |
11 | * modification, are permitted provided that the following conditions | 11 | * modification, are permitted provided that the following conditions | |
12 | * are met: | 12 | * are met: | |
13 | * 1. Redistributions of source code must retain the above copyright | 13 | * 1. Redistributions of source code must retain the above copyright | |
14 | * notice, this list of conditions and the following disclaimer. | 14 | * notice, this list of conditions and the following disclaimer. | |
@@ -52,27 +52,27 @@ | @@ -52,27 +52,27 @@ | |||
52 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | 52 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
53 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | 53 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
54 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR AND CONTRIBUTORS BE LIABLE | 54 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR AND CONTRIBUTORS BE LIABLE | |
55 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | 55 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |
56 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | 56 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |
57 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | 57 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |
58 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | 58 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |
59 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | 59 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |
60 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | 60 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
61 | * SUCH DAMAGE. | 61 | * SUCH DAMAGE. | |
62 | */ | 62 | */ | |
63 | 63 | |||
64 | #include <sys/cdefs.h> | 64 | #include <sys/cdefs.h> | |
65 | __KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.75 2010/08/09 04:18:48 jruoho Exp $"); | 65 | __KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.76 2010/08/09 15:46:17 jruoho Exp $"); | |
66 | 66 | |||
67 | #include "opt_ddb.h" | 67 | #include "opt_ddb.h" | |
68 | #include "opt_mpbios.h" /* for MPDEBUG */ | 68 | #include "opt_mpbios.h" /* for MPDEBUG */ | |
69 | #include "opt_mtrr.h" | 69 | #include "opt_mtrr.h" | |
70 | 70 | |||
71 | #include "lapic.h" | 71 | #include "lapic.h" | |
72 | #include "ioapic.h" | 72 | #include "ioapic.h" | |
73 | 73 | |||
74 | #ifdef i386 | 74 | #ifdef i386 | |
75 | #include "npx.h" | 75 | #include "npx.h" | |
76 | #endif | 76 | #endif | |
77 | 77 | |||
78 | #include <sys/param.h> | 78 | #include <sys/param.h> | |
@@ -175,29 +175,28 @@ uint32_t cpu_feature[5]; /* X86 CPUID fe | @@ -175,29 +175,28 @@ uint32_t cpu_feature[5]; /* X86 CPUID fe | |||
175 | * [1] basic features %ecx | 175 | * [1] basic features %ecx | |
176 | * [2] extended features %edx | 176 | * [2] extended features %edx | |
177 | * [3] extended features %ecx | 177 | * [3] extended features %ecx | |
178 | * [4] VIA padlock features | 178 | * [4] VIA padlock features | |
179 | */ | 179 | */ | |
180 | 180 | |||
181 | extern char x86_64_doubleflt_stack[]; | 181 | extern char x86_64_doubleflt_stack[]; | |
182 | 182 | |||
183 | bool x86_mp_online; | 183 | bool x86_mp_online; | |
184 | paddr_t mp_trampoline_paddr = MP_TRAMPOLINE; | 184 | paddr_t mp_trampoline_paddr = MP_TRAMPOLINE; | |
185 | static vaddr_t cmos_data_mapping; | 185 | static vaddr_t cmos_data_mapping; | |
186 | struct cpu_info *cpu_starting; | 186 | struct cpu_info *cpu_starting; | |
187 | 187 | |||
188 | int (*cpu_freq_sysctl_get)(SYSCTLFN_PROTO) = NULL; | 188 | void (*cpu_freq_init)(int) = NULL; | |
189 | int (*cpu_freq_sysctl_set)(SYSCTLFN_PROTO) = NULL; | 189 | struct sysctllog *cpu_freq_sysctllog = NULL; | |
190 | int (*cpu_freq_sysctl_all)(SYSCTLFN_PROTO) = NULL; | |||
191 | 190 | |||
192 | void cpu_hatch(void *); | 191 | void cpu_hatch(void *); | |
193 | static void cpu_boot_secondary(struct cpu_info *ci); | 192 | static void cpu_boot_secondary(struct cpu_info *ci); | |
194 | static void cpu_start_secondary(struct cpu_info *ci); | 193 | static void cpu_start_secondary(struct cpu_info *ci); | |
195 | static void cpu_copy_trampoline(void); | 194 | static void cpu_copy_trampoline(void); | |
196 | 195 | |||
197 | /* | 196 | /* | |
198 | * Runs once per boot once multiprocessor goo has been detected and | 197 | * Runs once per boot once multiprocessor goo has been detected and | |
199 | * the local APIC on the boot processor has been mapped. | 198 | * the local APIC on the boot processor has been mapped. | |
200 | * | 199 | * | |
201 | * Called from lapic_boot_init() (from mpbios_scan()). | 200 | * Called from lapic_boot_init() (from mpbios_scan()). | |
202 | */ | 201 | */ | |
203 | void | 202 | void |
--- src/sys/arch/x86/x86/est.c 2010/08/09 04:18:49 1.17
+++ src/sys/arch/x86/x86/est.c 2010/08/09 15:46:17 1.18
@@ -1,14 +1,14 @@ | @@ -1,14 +1,14 @@ | |||
1 | /* $NetBSD: est.c,v 1.17 2010/08/09 04:18:49 jruoho Exp $ */ | 1 | /* $NetBSD: est.c,v 1.18 2010/08/09 15:46:17 jruoho Exp $ */ | |
2 | /* | 2 | /* | |
3 | * Copyright (c) 2003 Michael Eriksson. | 3 | * Copyright (c) 2003 Michael Eriksson. | |
4 | * All rights reserved. | 4 | * All rights reserved. | |
5 | * | 5 | * | |
6 | * Redistribution and use in source and binary forms, with or without | 6 | * Redistribution and use in source and binary forms, with or without | |
7 | * modification, are permitted provided that the following conditions | 7 | * modification, are permitted provided that the following conditions | |
8 | * are met: | 8 | * are met: | |
9 | * 1. Redistributions of source code must retain the above copyright | 9 | * 1. Redistributions of source code must retain the above copyright | |
10 | * notice, this list of conditions and the following disclaimer. | 10 | * notice, this list of conditions and the following disclaimer. | |
11 | * 2. Redistributions in binary form must reproduce the above copyright | 11 | * 2. Redistributions in binary form must reproduce the above copyright | |
12 | * notice, this list of conditions and the following disclaimer in the | 12 | * notice, this list of conditions and the following disclaimer in the | |
13 | * documentation and/or other materials provided with the distribution. | 13 | * documentation and/or other materials provided with the distribution. | |
14 | * 3. The name of the author may not be used to endorse or promote products | 14 | * 3. The name of the author may not be used to endorse or promote products | |
@@ -71,27 +71,27 @@ | @@ -71,27 +71,27 @@ | |||
71 | * Table 3-4, 3-5, 3-6, Voltage and Current Specifications. | 71 | * Table 3-4, 3-5, 3-6, Voltage and Current Specifications. | |
72 | * http://www.intel.com/design/mobile/datashts/302189.htm | 72 | * http://www.intel.com/design/mobile/datashts/302189.htm | |
73 | * | 73 | * | |
74 | * - Linux cpufreq patches, speedstep-centrino.c. | 74 | * - Linux cpufreq patches, speedstep-centrino.c. | |
75 | * Encoding of MSR_PERF_CTL and MSR_PERF_STATUS. | 75 | * Encoding of MSR_PERF_CTL and MSR_PERF_STATUS. | |
76 | * http://www.codemonkey.org.uk/projects/cpufreq/cpufreq-2.4.22-pre6-1.gz | 76 | * http://www.codemonkey.org.uk/projects/cpufreq/cpufreq-2.4.22-pre6-1.gz | |
77 | * | 77 | * | |
78 | * ACPI objects: _PCT is MSR location, _PSS is freq/voltage, _PPC is caps. | 78 | * ACPI objects: _PCT is MSR location, _PSS is freq/voltage, _PPC is caps. | |
79 | */ | 79 | */ | |
80 | 80 | |||
81 | /* #define EST_DEBUG */ | 81 | /* #define EST_DEBUG */ | |
82 | 82 | |||
83 | #include <sys/cdefs.h> | 83 | #include <sys/cdefs.h> | |
84 | __KERNEL_RCSID(0, "$NetBSD: est.c,v 1.17 2010/08/09 04:18:49 jruoho Exp $"); | 84 | __KERNEL_RCSID(0, "$NetBSD: est.c,v 1.18 2010/08/09 15:46:17 jruoho Exp $"); | |
85 | 85 | |||
86 | #include <sys/param.h> | 86 | #include <sys/param.h> | |
87 | #include <sys/systm.h> | 87 | #include <sys/systm.h> | |
88 | #include <sys/device.h> | 88 | #include <sys/device.h> | |
89 | #include <sys/malloc.h> | 89 | #include <sys/malloc.h> | |
90 | #include <sys/sysctl.h> | 90 | #include <sys/sysctl.h> | |
91 | #include <sys/once.h> | 91 | #include <sys/once.h> | |
92 | #include <sys/xcall.h> | 92 | #include <sys/xcall.h> | |
93 | 93 | |||
94 | #include <x86/cpuvar.h> | 94 | #include <x86/cpuvar.h> | |
95 | #include <x86/cputypes.h> | 95 | #include <x86/cputypes.h> | |
96 | #include <x86/cpu_msr.h> | 96 | #include <x86/cpu_msr.h> | |
97 | 97 | |||
@@ -988,92 +988,41 @@ static const struct fqlist est_cpus[] = | @@ -988,92 +988,41 @@ static const struct fqlist est_cpus[] = | |||
988 | ENTRY(IDT, BUS133, C7M_795), | 988 | ENTRY(IDT, BUS133, C7M_795), | |
989 | 989 | |||
990 | ENTRY(IDT, BUS100, eden90_1000) | 990 | ENTRY(IDT, BUS100, eden90_1000) | |
991 | }; | 991 | }; | |
992 | 992 | |||
993 | #define MSR2FREQINC(msr) (((int) (msr) >> 8) & 0xff) | 993 | #define MSR2FREQINC(msr) (((int) (msr) >> 8) & 0xff) | |
994 | #define MSR2VOLTINC(msr) ((int) (msr) & 0xff) | 994 | #define MSR2VOLTINC(msr) ((int) (msr) & 0xff) | |
995 | 995 | |||
996 | #define MSR2MHZ(msr, bus) ((MSR2FREQINC((msr)) * (bus) + 50) / 100) | 996 | #define MSR2MHZ(msr, bus) ((MSR2FREQINC((msr)) * (bus) + 50) / 100) | |
997 | #define MSR2MV(msr) (MSR2VOLTINC(msr) * 16 + 700) | 997 | #define MSR2MV(msr) (MSR2VOLTINC(msr) * 16 + 700) | |
998 | 998 | |||
999 | static const struct fqlist *est_fqlist; /* not NULL if functional */ | 999 | static const struct fqlist *est_fqlist; /* not NULL if functional */ | |
1000 | static uint16_t *fake_table; /* guessed est_cpu table */ | 1000 | static uint16_t *fake_table; /* guessed est_cpu table */ | |
1001 | static char *freq_names; | |||
1002 | static struct fqlist fake_fqlist; | 1001 | static struct fqlist fake_fqlist; | |
1003 | static int est_node_target, est_node_current; | 1002 | static int est_node_target, est_node_current; | |
1004 | static const char est_desc[] = "Enhanced SpeedStep"; | 1003 | static const char est_desc[] = "Enhanced SpeedStep"; | |
1005 | static int lvendor, bus_clock; | 1004 | static int lvendor, bus_clock; | |
1006 | 1005 | |||
1006 | static int est_sysctl_helper(SYSCTLFN_PROTO); | |||
1007 | static int est_init_once(void); | 1007 | static int est_init_once(void); | |
1008 | static void est_init_main(int); | 1008 | static void est_init_main(int); | |
1009 | 1009 | |||
1010 | static int est_sysctl_helper(SYSCTLFN_PROTO); | |||
1011 | static int est_sysctl_helper_get(SYSCTLFN_PROTO); | |||
1012 | static int est_sysctl_helper_set(SYSCTLFN_PROTO); | |||
1013 | static int est_sysctl_helper_all(SYSCTLFN_PROTO); | |||
1014 | ||||
1015 | static int | |||
1016 | est_sysctl_helper_get(SYSCTLFN_ARGS) | |||
1017 | { | |||
1018 | ||||
1019 | if (cpu_freq_sysctl_get != NULL) | |||
1020 | return (*cpu_freq_sysctl_get)(SYSCTLFN_CALL(rnode)); | |||
1021 | ||||
1022 | return est_sysctl_helper(SYSCTLFN_CALL(rnode)); | |||
1023 | } | |||
1024 | ||||
1025 | static int | |||
1026 | est_sysctl_helper_set(SYSCTLFN_ARGS) | |||
1027 | { | |||
1028 | ||||
1029 | if (cpu_freq_sysctl_set != NULL) | |||
1030 | return (*cpu_freq_sysctl_set)(SYSCTLFN_CALL(rnode)); | |||
1031 | ||||
1032 | return est_sysctl_helper(SYSCTLFN_CALL(rnode)); | |||
1033 | } | |||
1034 | ||||
1035 | static int | |||
1036 | est_sysctl_helper_all(SYSCTLFN_ARGS) | |||
1037 | { | |||
1038 | struct sysctlnode node; | |||
1039 | int err; | |||
1040 | ||||
1041 | if (cpu_freq_sysctl_all != NULL) | |||
1042 | return (*cpu_freq_sysctl_all)(SYSCTLFN_CALL(rnode)); | |||
1043 | ||||
1044 | if (freq_names == NULL) | |||
1045 | return ENXIO; | |||
1046 | ||||
1047 | node = *rnode; | |||
1048 | node.sysctl_data = freq_names; | |||
1049 | ||||
1050 | err = sysctl_lookup(SYSCTLFN_CALL(&node)); | |||
1051 | ||||
1052 | if (err != 0 || newp == NULL) | |||
1053 | return err; | |||
1054 | ||||
1055 | return 0; | |||
1056 | } | |||
1057 | ||||
1058 | static int | 1010 | static int | |
1059 | est_sysctl_helper(SYSCTLFN_ARGS) | 1011 | est_sysctl_helper(SYSCTLFN_ARGS) | |
1060 | { | 1012 | { | |
1061 | struct sysctlnode node; | 1013 | struct sysctlnode node; | |
1062 | int fq, oldfq, error; | 1014 | int fq, oldfq, error; | |
1063 | 1015 | |||
1064 | if (freq_names == NULL) | |||
1065 | return ENXIO; | |||
1066 | ||||
1067 | if (est_fqlist == NULL) | 1016 | if (est_fqlist == NULL) | |
1068 | return EOPNOTSUPP; | 1017 | return EOPNOTSUPP; | |
1069 | 1018 | |||
1070 | node = *rnode; | 1019 | node = *rnode; | |
1071 | node.sysctl_data = &fq; | 1020 | node.sysctl_data = &fq; | |
1072 | 1021 | |||
1073 | oldfq = 0; | 1022 | oldfq = 0; | |
1074 | if (rnode->sysctl_num == est_node_target) | 1023 | if (rnode->sysctl_num == est_node_target) | |
1075 | fq = oldfq = MSR2MHZ(rdmsr(MSR_PERF_CTL), bus_clock); | 1024 | fq = oldfq = MSR2MHZ(rdmsr(MSR_PERF_CTL), bus_clock); | |
1076 | else if (rnode->sysctl_num == est_node_current) | 1025 | else if (rnode->sysctl_num == est_node_current) | |
1077 | fq = MSR2MHZ(rdmsr(MSR_PERF_STATUS), bus_clock); | 1026 | fq = MSR2MHZ(rdmsr(MSR_PERF_STATUS), bus_clock); | |
1078 | else | 1027 | else | |
1079 | return EOPNOTSUPP; | 1028 | return EOPNOTSUPP; | |
@@ -1127,26 +1076,27 @@ est_init(int vendor) | @@ -1127,26 +1076,27 @@ est_init(int vendor) | |||
1127 | 1076 | |||
1128 | static void | 1077 | static void | |
1129 | est_init_main(int vendor) | 1078 | est_init_main(int vendor) | |
1130 | { | 1079 | { | |
1131 | #ifdef __i386__ | 1080 | #ifdef __i386__ | |
1132 | const struct fqlist *fql; | 1081 | const struct fqlist *fql; | |
1133 | #endif | 1082 | #endif | |
1134 | const struct sysctlnode *node, *estnode, *freqnode; | 1083 | const struct sysctlnode *node, *estnode, *freqnode; | |
1135 | uint64_t msr; | 1084 | uint64_t msr; | |
1136 | uint16_t cur, idhi, idlo; | 1085 | uint16_t cur, idhi, idlo; | |
1137 | uint8_t crhi, crlo, crcur; | 1086 | uint8_t crhi, crlo, crcur; | |
1138 | int i, mv, rc; | 1087 | int i, mv, rc; | |
1139 | size_t len, freq_len; | 1088 | size_t len, freq_len; | |
1089 | char *freq_names; | |||
1140 | 1090 | |||
1141 | if (CPUID2FAMILY(curcpu()->ci_signature) == 15) | 1091 | if (CPUID2FAMILY(curcpu()->ci_signature) == 15) | |
1142 | bus_clock = p4_get_bus_clock(curcpu()); | 1092 | bus_clock = p4_get_bus_clock(curcpu()); | |
1143 | else if (CPUID2FAMILY(curcpu()->ci_signature) == 6) { | 1093 | else if (CPUID2FAMILY(curcpu()->ci_signature) == 6) { | |
1144 | if (vendor == CPUVENDOR_IDT) { | 1094 | if (vendor == CPUVENDOR_IDT) { | |
1145 | switch (CPUID2MODEL(curcpu()->ci_signature)) { | 1095 | switch (CPUID2MODEL(curcpu()->ci_signature)) { | |
1146 | case 0xa: /* C7 Esther */ | 1096 | case 0xa: /* C7 Esther */ | |
1147 | case 0xd: /* C7 Esther */ | 1097 | case 0xd: /* C7 Esther */ | |
1148 | bus_clock = viac7_get_bus_clock(curcpu()); | 1098 | bus_clock = viac7_get_bus_clock(curcpu()); | |
1149 | break; | 1099 | break; | |
1150 | default: | 1100 | default: | |
1151 | bus_clock = via_get_bus_clock(curcpu()); | 1101 | bus_clock = via_get_bus_clock(curcpu()); | |
1152 | break; | 1102 | break; | |
@@ -1301,55 +1251,64 @@ est_init_main(int vendor) | @@ -1301,55 +1251,64 @@ est_init_main(int vendor) | |||
1301 | len = 0; | 1251 | len = 0; | |
1302 | for (i = 0; i < est_fqlist->n; i++) { | 1252 | for (i = 0; i < est_fqlist->n; i++) { | |
1303 | len += snprintf(freq_names + len, freq_len - len, "%d%s", | 1253 | len += snprintf(freq_names + len, freq_len - len, "%d%s", | |
1304 | MSR2MHZ(est_fqlist->table[i], bus_clock), | 1254 | MSR2MHZ(est_fqlist->table[i], bus_clock), | |
1305 | i < est_fqlist->n - 1 ? " " : ""); | 1255 | i < est_fqlist->n - 1 ? " " : ""); | |
1306 | } | 1256 | } | |
1307 | 1257 | |||
1308 | aprint_debug_dev(curcpu()->ci_dev, "%s (%d mV) ", est_desc, mv); | 1258 | aprint_debug_dev(curcpu()->ci_dev, "%s (%d mV) ", est_desc, mv); | |
1309 | aprint_debug("%d (MHz): %s\n", MSR2MHZ(msr, bus_clock), freq_names); | 1259 | aprint_debug("%d (MHz): %s\n", MSR2MHZ(msr, bus_clock), freq_names); | |
1310 | 1260 | |||
1311 | /* | 1261 | /* | |
1312 | * Setup the sysctl sub-tree machdep.est.* | 1262 | * Setup the sysctl sub-tree machdep.est.* | |
1313 | */ | 1263 | */ | |
1314 | if ((rc = sysctl_createv(NULL, 0, NULL, &node, | 1264 | if (cpu_freq_sysctllog != NULL) { | |
1265 | rc = EALREADY; | |||
1266 | goto err; | |||
1267 | } | |||
1268 | ||||
1269 | cpu_freq_init = est_init_main; | |||
1270 | ||||
1271 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, NULL, &node, | |||
1315 | CTLFLAG_PERMANENT, CTLTYPE_NODE, "machdep", NULL, | 1272 | CTLFLAG_PERMANENT, CTLTYPE_NODE, "machdep", NULL, | |
1316 | NULL, 0, NULL, 0, CTL_MACHDEP, CTL_EOL)) != 0) | 1273 | NULL, 0, NULL, 0, CTL_MACHDEP, CTL_EOL)) != 0) | |
1317 | goto err; | 1274 | goto err; | |
1318 | 1275 | |||
1319 | if ((rc = sysctl_createv(NULL, 0, &node, &estnode, | 1276 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, &node, &estnode, | |
1320 | 0, CTLTYPE_NODE, "est", NULL, | 1277 | 0, CTLTYPE_NODE, "est", NULL, | |
1321 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | 1278 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | |
1322 | goto err; | 1279 | goto err; | |
1323 | 1280 | |||
1324 | if ((rc = sysctl_createv(NULL, 0, &estnode, &freqnode, | 1281 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, &estnode, &freqnode, | |
1325 | 0, CTLTYPE_NODE, "frequency", NULL, | 1282 | 0, CTLTYPE_NODE, "frequency", NULL, | |
1326 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | 1283 | NULL, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | |
1327 | goto err; | 1284 | goto err; | |
1328 | 1285 | |||
1329 | if ((rc = sysctl_createv(NULL, 0, &freqnode, &node, | 1286 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, &freqnode, &node, | |
1330 | EST_TARGET_CTLFLAG, CTLTYPE_INT, "target", NULL, | 1287 | EST_TARGET_CTLFLAG, CTLTYPE_INT, "target", NULL, | |
1331 | est_sysctl_helper_set, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | 1288 | est_sysctl_helper, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | |
1332 | goto err; | 1289 | goto err; | |
1333 | ||||
1334 | est_node_target = node->sysctl_num; | 1290 | est_node_target = node->sysctl_num; | |
1335 | 1291 | |||
1336 | if ((rc = sysctl_createv(NULL, 0, &freqnode, &node, | 1292 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, &freqnode, &node, | |
1337 | 0, CTLTYPE_INT, "current", NULL, | 1293 | 0, CTLTYPE_INT, "current", NULL, | |
1338 | est_sysctl_helper_get, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | 1294 | est_sysctl_helper, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | |
1339 | goto err; | 1295 | goto err; | |
1340 | ||||
1341 | est_node_current = node->sysctl_num; | 1296 | est_node_current = node->sysctl_num; | |
1342 | 1297 | |||
1343 | if ((rc = sysctl_createv(NULL, 0, &freqnode, &node, | 1298 | if ((rc = sysctl_createv(&cpu_freq_sysctllog, 0, &freqnode, &node, | |
1344 | CTLFLAG_READONLY, CTLTYPE_STRING, "available", NULL, | 1299 | CTLFLAG_READONLY, CTLTYPE_STRING, "available", NULL, | |
1345 | est_sysctl_helper_all, 0, NULL, 0, CTL_CREATE, CTL_EOL)) != 0) | 1300 | NULL, 0, freq_names, freq_len, CTL_CREATE, CTL_EOL)) != 0) | |
1346 | goto err; | 1301 | goto err; | |
1347 | 1302 | |||
1348 | return; | 1303 | return; | |
1349 | 1304 | |||
1350 | err: | 1305 | err: | |
1351 | free(freq_names, M_SYSCTLDATA); | 1306 | free(freq_names, M_SYSCTLDATA); | |
1352 | freq_names = NULL; | 1307 | ||
1308 | if (cpu_freq_sysctllog != NULL) | |||
1309 | sysctl_teardown(&cpu_freq_sysctllog); | |||
1310 | ||||
1311 | cpu_freq_init = NULL; | |||
1353 | 1312 | |||
1354 | aprint_error("%s: sysctl_createv failed (rc = %d)\n", __func__, rc); | 1313 | aprint_error("%s: sysctl_createv failed (rc = %d)\n", __func__, rc); | |
1355 | } | 1314 | } |
--- src/sys/arch/xen/x86/cpu.c 2010/07/24 00:45:56 1.47
+++ src/sys/arch/xen/x86/cpu.c 2010/08/09 15:46:18 1.48
@@ -1,14 +1,14 @@ | @@ -1,14 +1,14 @@ | |||
1 | /* $NetBSD: cpu.c,v 1.47 2010/07/24 00:45:56 jym Exp $ */ | 1 | /* $NetBSD: cpu.c,v 1.48 2010/08/09 15:46:18 jruoho Exp $ */ | |
2 | /* NetBSD: cpu.c,v 1.18 2004/02/20 17:35:01 yamt Exp */ | 2 | /* NetBSD: cpu.c,v 1.18 2004/02/20 17:35:01 yamt Exp */ | |
3 | 3 | |||
4 | /*- | 4 | /*- | |
5 | * Copyright (c) 2000 The NetBSD Foundation, Inc. | 5 | * Copyright (c) 2000 The NetBSD Foundation, Inc. | |
6 | * Copyright (c) 2002, 2006, 2007 YAMAMOTO Takashi, | 6 | * Copyright (c) 2002, 2006, 2007 YAMAMOTO Takashi, | |
7 | * All rights reserved. | 7 | * All rights reserved. | |
8 | * | 8 | * | |
9 | * This code is derived from software contributed to The NetBSD Foundation | 9 | * This code is derived from software contributed to The NetBSD Foundation | |
10 | * by RedBack Networks Inc. | 10 | * by RedBack Networks Inc. | |
11 | * | 11 | * | |
12 | * Author: Bill Sommerfeld | 12 | * Author: Bill Sommerfeld | |
13 | * | 13 | * | |
14 | * Redistribution and use in source and binary forms, with or without | 14 | * Redistribution and use in source and binary forms, with or without | |
@@ -56,27 +56,27 @@ | @@ -56,27 +56,27 @@ | |||
56 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | 56 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
57 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | 57 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
58 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR AND CONTRIBUTORS BE LIABLE | 58 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR AND CONTRIBUTORS BE LIABLE | |
59 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | 59 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |
60 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | 60 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |
61 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | 61 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |
62 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | 62 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |
63 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | 63 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |
64 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | 64 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
65 | * SUCH DAMAGE. | 65 | * SUCH DAMAGE. | |
66 | */ | 66 | */ | |
67 | 67 | |||
68 | #include <sys/cdefs.h> | 68 | #include <sys/cdefs.h> | |
69 | __KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.47 2010/07/24 00:45:56 jym Exp $"); | 69 | __KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.48 2010/08/09 15:46:18 jruoho Exp $"); | |
70 | 70 | |||
71 | #include "opt_ddb.h" | 71 | #include "opt_ddb.h" | |
72 | #include "opt_multiprocessor.h" | 72 | #include "opt_multiprocessor.h" | |
73 | #include "opt_mpbios.h" /* for MPDEBUG */ | 73 | #include "opt_mpbios.h" /* for MPDEBUG */ | |
74 | #include "opt_mtrr.h" | 74 | #include "opt_mtrr.h" | |
75 | #include "opt_xen.h" | 75 | #include "opt_xen.h" | |
76 | 76 | |||
77 | #include "lapic.h" | 77 | #include "lapic.h" | |
78 | #include "ioapic.h" | 78 | #include "ioapic.h" | |
79 | 79 | |||
80 | #include <sys/param.h> | 80 | #include <sys/param.h> | |
81 | #include <sys/proc.h> | 81 | #include <sys/proc.h> | |
82 | #include <sys/systm.h> | 82 | #include <sys/systm.h> | |
@@ -175,26 +175,29 @@ uint32_t phycpus_attached = 0; | @@ -175,26 +175,29 @@ uint32_t phycpus_attached = 0; | |||
175 | uint32_t phycpus_running = 0; | 175 | uint32_t phycpus_running = 0; | |
176 | 176 | |||
177 | uint32_t cpu_feature[5]; /* X86 CPUID feature bits | 177 | uint32_t cpu_feature[5]; /* X86 CPUID feature bits | |
178 | * [0] basic features %edx | 178 | * [0] basic features %edx | |
179 | * [1] basic features %ecx | 179 | * [1] basic features %ecx | |
180 | * [2] extended features %edx | 180 | * [2] extended features %edx | |
181 | * [3] extended features %ecx | 181 | * [3] extended features %ecx | |
182 | * [4] VIA padlock features | 182 | * [4] VIA padlock features | |
183 | */ | 183 | */ | |
184 | 184 | |||
185 | bool x86_mp_online; | 185 | bool x86_mp_online; | |
186 | paddr_t mp_trampoline_paddr = MP_TRAMPOLINE; | 186 | paddr_t mp_trampoline_paddr = MP_TRAMPOLINE; | |
187 | 187 | |||
188 | void (*cpu_freq_init)(int) = NULL; | |||
189 | struct sysctllog *cpu_freq_sysctllog = NULL; | |||
190 | ||||
188 | #if defined(MULTIPROCESSOR) | 191 | #if defined(MULTIPROCESSOR) | |
189 | void cpu_hatch(void *); | 192 | void cpu_hatch(void *); | |
190 | static void cpu_boot_secondary(struct cpu_info *ci); | 193 | static void cpu_boot_secondary(struct cpu_info *ci); | |
191 | static void cpu_start_secondary(struct cpu_info *ci); | 194 | static void cpu_start_secondary(struct cpu_info *ci); | |
192 | static void cpu_copy_trampoline(void); | 195 | static void cpu_copy_trampoline(void); | |
193 | 196 | |||
194 | /* | 197 | /* | |
195 | * Runs once per boot once multiprocessor goo has been detected and | 198 | * Runs once per boot once multiprocessor goo has been detected and | |
196 | * the local APIC on the boot processor has been mapped. | 199 | * the local APIC on the boot processor has been mapped. | |
197 | * | 200 | * | |
198 | * Called from lapic_boot_init() (from mpbios_scan()). | 201 | * Called from lapic_boot_init() (from mpbios_scan()). | |
199 | */ | 202 | */ | |
200 | void | 203 | void |