From: Hans de Goede hansg@kernel.org
[ Upstream commit e9dff11a7a50fcef23fe3e8314fafae6d5641826 ]
When deleting the previous walkstate operand stack acpi_ds_call_control_method() was deleting obj_desc->Method.param_count operands. But Method.param_count does not necessarily match this_walk_state->num_operands, it may be either less or more.
After correcting the for loop to check `i < this_walk_state->num_operands` the code is identical to acpi_ds_clear_operands(), so just outright replace the code with acpi_ds_clear_operands() to fix this.
Link: https://github.com/acpica/acpica/commit/53fc0220 Signed-off-by: Hans de Goede hansg@kernel.org Signed-off-by: Rafael J. Wysocki rafael.j.wysocki@intel.com Signed-off-by: Sasha Levin sashal@kernel.org ---
LLM Generated explanations, may be completely bogus:
YES - Current cleanup in `drivers/acpi/acpica/dsmethod.c:517` and `drivers/acpi/acpica/dsmethod.c:549` only drops `obj_desc->method.param_count` operands after a call, so when firmware supplies extra arguments the additional entries in `this_walk_state->operands[]` keep their references alive even though `num_operands` is reset—this leaks AML temporaries and can strand namespace refs on every invocation. - The call path copies every resolved operand up to the NULL terminator into the callee (`drivers/acpi/acpica/dsmthdat.c:175`), and ACPICA already anticipates AML that passes too many parameters (`drivers/acpi/acpica/nsarguments.c:222`-`245`), so the leak is triggered by real-world firmware and grows with each mis-specified call. - Replacing the open-coded loop with `acpi_ds_clear_operands(this_walk_state)` uses the existing helper that already removes all `num_operands` entries (`drivers/acpi/acpica/dsutils.c:383`-`400`) and matches the cleanup used in other dispatcher paths (`drivers/acpi/acpica/dswexec.c:440`-`452`); git history shows the buggy pattern has existed since the original ACPICA import, so the fix is self-contained and low risk for all supported branches.
Next step: queue this patch for the stable ACPICA backport stream so kernels inheriting the long-standing leak can be corrected.
drivers/acpi/acpica/dsmethod.c | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-)
diff --git a/drivers/acpi/acpica/dsmethod.c b/drivers/acpi/acpica/dsmethod.c index fef6fb29ece4d..e707a70368026 100644 --- a/drivers/acpi/acpica/dsmethod.c +++ b/drivers/acpi/acpica/dsmethod.c @@ -546,14 +546,7 @@ acpi_ds_call_control_method(struct acpi_thread_state *thread, * Delete the operands on the previous walkstate operand stack * (they were copied to new objects) */ - for (i = 0; i < obj_desc->method.param_count; i++) { - acpi_ut_remove_reference(this_walk_state->operands[i]); - this_walk_state->operands[i] = NULL; - } - - /* Clear the operand stack */ - - this_walk_state->num_operands = 0; + acpi_ds_clear_operands(this_walk_state);
ACPI_DEBUG_PRINT((ACPI_DB_DISPATCH, "**** Begin nested execution of [%4.4s] **** WalkState=%p\n",