diff options
author | Sumeet Pawnikar <sumeet.r.pawnikar@intel.com> | 2022-06-08 17:43:36 +0530 |
---|---|---|
committer | Felix Held <felix-coreboot@felixheld.de> | 2023-04-12 14:11:45 +0000 |
commit | 2f7fa5543308e83787b7cef6e83e20e1e3f379d9 (patch) | |
tree | 94a4d6dbe8092e729392ae1459b150f060fc4109 /src/acpi | |
parent | 0c06dbb1a4aaf6506b769fb36e8a694e91ab411b (diff) |
Reland "drivers/intel/dptf: Add multiple fan support under dptf"
This reverts commit 4dba71fd25c91a9e610287c61238a8fe24452e4e.
Add multiple fan support for dptf policies.
This also fixes the Google Meet resolution drop issue as per
b:246535768 comment#12. When system starts Google Meet video call,
it uses the hardware accelerated encoder as expected. But, as soon as
another system connects to the call, an immediate fallback is observed
from hardware to software encoder. Due to this, Google Meet resolution
dropped from 720p to 180p. This issue is observed on Alder Lake-N SoC
based fanless platforms. This same issue was not seen on fan based
systems. With the fix in dptf driver where fan configures appropriate
setting for only fan participant, not for other device participants,
able to see consistent 720p resolution.
BUG=b:246535768,b:235254828
BRANCH=None
TEST=Built and tested on Alder Lake-P Redrix system for two fans
support and on Alder Lake-N fanless systems. With this code change
Google Meet resolution drop not observed.
Signed-off-by: Sumeet Pawnikar <sumeet.r.pawnikar@intel.com>
Change-Id: Id07d279ff962253c22be9d395ed7be0d732aeaa7
Reviewed-on: https://review.coreboot.org/c/coreboot/+/73249
Reviewed-by: Lean Sheng Tan <sheng.tan@9elements.com>
Reviewed-by: Paul Menzel <paulepanter@mailbox.org>
Reviewed-by: Reka Norman <rekanorman@chromium.org>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
Diffstat (limited to 'src/acpi')
-rw-r--r-- | src/acpi/acpigen_dptf.c | 85 |
1 files changed, 67 insertions, 18 deletions
diff --git a/src/acpi/acpigen_dptf.c b/src/acpi/acpigen_dptf.c index a458a5599b..d1a79d18e2 100644 --- a/src/acpi/acpigen_dptf.c +++ b/src/acpi/acpigen_dptf.c @@ -62,6 +62,8 @@ static const char *namestring_of(enum dptf_participant participant) return "TCHG"; case DPTF_FAN: return "TFN1"; + case DPTF_FAN_2: + return "TFN2"; case DPTF_TEMP_SENSOR_0: return "TSR0"; case DPTF_TEMP_SENSOR_1: @@ -123,7 +125,7 @@ void dptf_write_scope(enum dptf_participant participant) * are used to increase the speed of the fan in order to speed up cooling. */ static void write_active_relationship_table(const struct dptf_active_policy *policies, - int max_count) + int max_count, bool dptf_multifan_support) { char *pkg_count; int i, j; @@ -154,7 +156,11 @@ static void write_active_relationship_table(const struct dptf_active_policy *pol /* Source, Target, Percent, Fan % for each of _AC0 ... _AC9 */ acpigen_write_package(13); - acpigen_emit_namestring(path_of(DPTF_FAN)); + if (dptf_multifan_support) + acpigen_emit_namestring(path_of(policies[i].source)); + else + acpigen_emit_namestring(path_of(DPTF_FAN)); + acpigen_emit_namestring(path_of(policies[i].target)); acpigen_write_integer(DEFAULT_IF_0(policies[i].weight, DEFAULT_WEIGHT)); @@ -205,9 +211,10 @@ static void write_active_cooling_methods(const struct dptf_active_policy *polici } } -void dptf_write_active_policies(const struct dptf_active_policy *policies, int max_count) +void dptf_write_active_policies(const struct dptf_active_policy *policies, + int max_count, bool dptf_multifan_support) { - write_active_relationship_table(policies, max_count); + write_active_relationship_table(policies, max_count, dptf_multifan_support); write_active_cooling_methods(policies, max_count); } @@ -352,7 +359,29 @@ void dptf_write_charger_perf(const struct dptf_charger_perf *states, int max_cou acpigen_pop_len(); /* Scope */ } -void dptf_write_fan_perf(const struct dptf_fan_perf *states, int max_count) +int dptf_write_fan_perf_fps(uint8_t percent, uint16_t power, uint16_t speed, + uint16_t noise_level) +{ + /* + * Some _FPS tables do include a last entry where Percent is 0, but Power is + * called out, so this table is finished when both are zero. + */ + if (!percent && !power) + return 1; + + acpigen_write_package(5); + acpigen_write_integer(percent); + acpigen_write_integer(DEFAULT_TRIP_POINT); + acpigen_write_integer(speed); + acpigen_write_integer(noise_level); + acpigen_write_integer(power); + acpigen_pop_len(); /* inner Package */ + + return 0; +} + +void dptf_write_fan_perf(const struct dptf_fan_perf *states, int max_count, + enum dptf_participant participant) { char *pkg_count; int i; @@ -360,29 +389,49 @@ void dptf_write_fan_perf(const struct dptf_fan_perf *states, int max_count) if (!max_count || !states[0].percent) return; - dptf_write_scope(DPTF_FAN); + dptf_write_scope(participant); /* _FPS - Fan Performance States */ acpigen_write_name("_FPS"); + pkg_count = acpigen_write_package(1); /* 1 for Revision */ acpigen_write_integer(FPS_REVISION); /* revision */ for (i = 0; i < max_count; ++i) { - /* - * Some _FPS tables do include a last entry where Percent is 0, but Power is - * called out, so this table is finished when both are zero. - */ - if (!states[i].percent && !states[i].power) + (*pkg_count)++; + if (dptf_write_fan_perf_fps(states[i].percent, states[i].power, + states[i].speed, states[i].noise_level)) break; + } + + acpigen_pop_len(); /* Package */ + acpigen_pop_len(); /* Scope */ +} +void dptf_write_multifan_perf( + const struct dptf_multifan_perf + states[DPTF_MAX_FAN_PARTICIPANTS][DPTF_MAX_FAN_PERF_STATES], + int max_count, enum dptf_participant participant, int fan_num) +{ + char *pkg_count; + int i; + + if (!max_count || !states[fan_num][0].percent) + return; + + dptf_write_scope(participant); + + /* _FPS - Fan Performance States */ + acpigen_write_name("_FPS"); + + pkg_count = acpigen_write_package(1); /* 1 for Revision */ + acpigen_write_integer(FPS_REVISION); /* revision */ + + for (i = 0; i < max_count; ++i) { (*pkg_count)++; - acpigen_write_package(5); - acpigen_write_integer(states[i].percent); - acpigen_write_integer(DEFAULT_TRIP_POINT); - acpigen_write_integer(states[i].speed); - acpigen_write_integer(states[i].noise_level); - acpigen_write_integer(states[i].power); - acpigen_pop_len(); /* inner Package */ + if (dptf_write_fan_perf_fps(states[fan_num][i].percent, states[fan_num][i].power, + states[fan_num][i].speed, states[fan_num][i].noise_level)) + break; } acpigen_pop_len(); /* Package */ |