1 /* SPDX-License-Identifier: GPL-2.0-only */
3 #include <console/console.h>
5 #include <cpu/intel/turbo.h>
6 #include <cpu/x86/msr.h>
8 #if CONFIG(CPU_INTEL_TURBO_NOT_PACKAGE_SCOPED)
9 static inline int get_global_turbo_state(void)
14 static inline void set_global_turbo_state(int state
)
18 static int g_turbo_state
= TURBO_UNKNOWN
;
20 static inline int get_global_turbo_state(void)
25 static inline void set_global_turbo_state(int state
)
27 g_turbo_state
= state
;
31 static const char *const turbo_state_desc
[] = {
32 [TURBO_UNKNOWN
] = "unknown",
33 [TURBO_UNAVAILABLE
] = "unavailable",
34 [TURBO_DISABLED
] = "available but hidden",
35 [TURBO_ENABLED
] = "available and visible"
39 * Try to update the global Turbo state.
41 static int update_turbo_state(void)
43 struct cpuid_result cpuid_regs
;
44 int turbo_en
, turbo_cap
;
46 int turbo_state
= get_global_turbo_state();
48 cpuid_regs
= cpuid(CPUID_LEAF_PM
);
49 turbo_cap
= !!(cpuid_regs
.eax
& PM_CAP_TURBO_MODE
);
51 msr
= rdmsr(IA32_MISC_ENABLE
);
52 turbo_en
= !(msr
.hi
& H_MISC_DISABLE_TURBO
);
54 if (!turbo_cap
&& turbo_en
) {
56 turbo_state
= TURBO_UNAVAILABLE
;
57 } else if (!turbo_cap
&& !turbo_en
) {
58 /* Available but disabled */
59 turbo_state
= TURBO_DISABLED
;
60 } else if (turbo_cap
&& turbo_en
) {
62 turbo_state
= TURBO_ENABLED
;
65 set_global_turbo_state(turbo_state
);
66 printk(BIOS_INFO
, "Turbo is %s\n", turbo_state_desc
[turbo_state
]);
72 * Determine the current state of Turbo and cache it for later. Turbo is package
73 * level config so it does not need to be enabled on every core.
75 int get_turbo_state(void)
77 int turbo_state
= get_global_turbo_state();
79 /* Return cached state if available */
80 if (turbo_state
== TURBO_UNKNOWN
)
81 turbo_state
= update_turbo_state();
87 * Try to enable Turbo mode.
89 void enable_turbo(void)
93 /* Only possible if turbo is available but hidden */
94 if (get_turbo_state() == TURBO_DISABLED
) {
95 /* Clear Turbo Disable bit in Misc Enables */
96 msr
= rdmsr(IA32_MISC_ENABLE
);
97 msr
.hi
&= ~H_MISC_DISABLE_TURBO
;
98 wrmsr(IA32_MISC_ENABLE
, msr
);
100 /* Update cached turbo state */
101 update_turbo_state();
106 * Try to disable Turbo mode.
108 void disable_turbo(void)
112 /* Only possible if turbo is available and visible */
113 if (get_turbo_state() == TURBO_ENABLED
) {
114 /* Set Turbo Disable bit in Misc Enables */
115 msr
= rdmsr(IA32_MISC_ENABLE
);
116 msr
.hi
|= H_MISC_DISABLE_TURBO
;
117 wrmsr(IA32_MISC_ENABLE
, msr
);
119 /* Update cached turbo state */
120 update_turbo_state();