summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLijo Lazar <lijo.lazar@amd.com>2026-05-18 17:43:44 +0530
committerAlex Deucher <alexander.deucher@amd.com>2026-07-01 11:09:55 -0400
commit916867cd75dbbc383aa6cb724556de769912157a (patch)
treef66e13605f28fedb9992bfd961bb7b64f0ac3d7d
parentb978b7d43963bbb3e2d850288f7c21ac11c3b751 (diff)
downloadlinux-stable-916867cd75dbbc383aa6cb724556de769912157a.tar.gz
linux-stable-916867cd75dbbc383aa6cb724556de769912157a.zip
drm/amdgpu: Validate ATPX buffer length before use
Add amdgpu_atpx_buffer_validate() to check that the returned ACPI buffer is of type ACPI_TYPE_BUFFER, is large enough to hold the u16 size field, and that the BIOS-reported size does not exceed the actual allocation length or fall below the minimum required by the caller. Use it in VERIFY_INTERFACE and GET_PX_PARAMETERS callers. Signed-off-by: Lijo Lazar <lijo.lazar@amd.com> Assisted-by: Claude Sonnet (Cursor AI) Acked-by: Alex Deucher <alexander.deucher@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c33
1 files changed, 21 insertions, 12 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c
index 3893e6fc2f03..e2a4644896ca 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c
@@ -89,6 +89,15 @@ bool amdgpu_is_atpx_hybrid(void)
return amdgpu_atpx_priv.atpx.is_hybrid;
}
+static bool amdgpu_atpx_buffer_validate(const union acpi_object *obj,
+ size_t min_size)
+{
+ return obj && obj->type == ACPI_TYPE_BUFFER &&
+ obj->buffer.length >= sizeof(u16) &&
+ obj->buffer.length >= *(u16 *)obj->buffer.pointer &&
+ *(u16 *)obj->buffer.pointer >= min_size;
+}
+
/**
* amdgpu_atpx_call - call an ATPX method
*
@@ -179,15 +188,15 @@ static int amdgpu_atpx_validate(struct amdgpu_atpx *atpx)
if (!info)
return -EIO;
- memset(&output, 0, sizeof(output));
-
- size = *(u16 *) info->buffer.pointer;
- if (size < 10) {
- pr_err("ATPX buffer is too small: %zu\n", size);
+ if (!amdgpu_atpx_buffer_validate(info, sizeof(output))) {
+ pr_err("Invalid ATPX GET_PX_PARAMETERS response\n");
kfree(info);
return -EINVAL;
}
- size = min(sizeof(output), size);
+
+ memset(&output, 0, sizeof(output));
+
+ size = min(sizeof(output), (size_t)*(u16 *)info->buffer.pointer);
memcpy(&output, info->buffer.pointer, size);
@@ -258,15 +267,15 @@ static int amdgpu_atpx_verify_interface(struct amdgpu_atpx *atpx)
if (!info)
return -EIO;
- memset(&output, 0, sizeof(output));
-
- size = *(u16 *) info->buffer.pointer;
- if (size < 8) {
- pr_err("ATPX buffer is too small: %zu\n", size);
+ if (!amdgpu_atpx_buffer_validate(info, sizeof(output))) {
+ pr_err("Invalid ATPX VERIFY_INTERFACE response\n");
err = -EINVAL;
goto out;
}
- size = min(sizeof(output), size);
+
+ memset(&output, 0, sizeof(output));
+
+ size = min(sizeof(output), (size_t)*(u16 *)info->buffer.pointer);
memcpy(&output, info->buffer.pointer, size);