-/* $OpenBSD: est.c,v 1.39 2016/03/06 22:41:24 naddy Exp $ */
+/* $OpenBSD: est.c,v 1.40 2021/08/11 18:15:50 tb Exp $ */
/*
* Copyright (c) 2003 Michael Eriksson.
* All rights reserved.
struct est_op {
uint16_t ctrl;
uint16_t mhz;
+ uint16_t pct;
};
struct fqlist {
struct acpicpu_pss *pss;
struct fqlist *acpilist;
int nstates, i;
+ int high, low;
if ((nstates = acpicpu_fetch_pss(&pss)) == 0)
goto nolist;
+ high = pss[0].pss_core_freq;
+ low = pss[nstates - 1].pss_core_freq;
+ if (high - low <= 0)
+ goto nolist;
+
if ((acpilist = malloc(sizeof(struct fqlist), M_DEVBUF, M_NOWAIT))
== NULL)
goto nolist;
for (i = 0; i < nstates; i++) {
acpilist->table[i].mhz = pss[i].pss_core_freq;
acpilist->table[i].ctrl = pss[i].pss_ctrl;
+ acpilist->table[i].pct =
+ (pss[i].pss_core_freq - low) * 100 / (high - low);
}
acpicpu_set_notify(est_acpi_pss_changed);
{
struct fqlist *acpilist;
int needtran = 1, i;
+ int high, low;
u_int64_t msr;
u_int16_t cur;
msr = rdmsr(MSR_PERF_STATUS);
cur = msr & 0xffff;
+ high = pss[0].pss_core_freq;
+ low = pss[npss - 1].pss_core_freq;
+ if (high - low <= 0) {
+ printf("est_acpi_pss_changed: new est state has no "
+ "speed step\n");
+ return;
+ }
+
if ((acpilist = malloc(sizeof(struct fqlist), M_DEVBUF, M_NOWAIT))
== NULL) {
printf("est_acpi_pss_changed: cannot allocate memory for new "
for (i = 0; i < npss; i++) {
acpilist->table[i].mhz = pss[i].pss_core_freq;
acpilist->table[i].ctrl = pss[i].pss_ctrl;
+ acpilist->table[i].pct =
+ (pss[i].pss_core_freq - low) * 100 / (high - low);
if (pss[i].pss_ctrl == cur)
needtran = 0;
}
printf("%s: using only highest and lowest power "
"states\n", cpu_device);
+ fake_table[0].pct = 51;
+
fake_table[1].ctrl = idlo;
fake_table[1].mhz = MSR2MHZ(idlo, bus_clock);
+ fake_table[1].pct = 0;
fake_fqlist->n = 2;
} else {
printf("%s: using only highest, current and lowest "
"power states\n", cpu_device);
+ fake_table[0].pct = 67;
+
fake_table[1].ctrl = cur;
fake_table[1].mhz = MSR2MHZ(cur, bus_clock);
+ fake_table[1].pct = 34;
fake_table[2].ctrl = idlo;
fake_table[2].mhz = MSR2MHZ(idlo, bus_clock);
+ fake_table[2].pct = 0;
fake_fqlist->n = 3;
}
if (est_fqlist == NULL)
return;
- i = ((level * est_fqlist->n) + 1) / 101;
- if (i >= est_fqlist->n)
- i = est_fqlist->n - 1;
- i = est_fqlist->n - 1 - i;
+ for (i = 0; i < est_fqlist->n; i++) {
+ if (level >= est_fqlist->table[i].pct)
+ break;
+ }
msr = rdmsr(MSR_PERF_CTL);
msr &= ~0xffffULL;