In xe_oa_add_config_ioctl(), we accessed oa_config->id after dropping metrics_lock. Since this lock protects the lifetime of oa_config, an attacker could guess the id and call xe_oa_remove_config_ioctl() with perfect timing, freeing oa_config before we dereference it, leading to a potential use-after-free.
Fix this by caching the id in a local variable while holding the lock.
Closes: https://gitlab.freedesktop.org/drm/xe/kernel/-/issues/6614 Fixes: cdf02fe1a94a7 ("drm/xe/oa/uapi: Add/remove OA config perf ops") Cc: stable@vger.kernel.org # v6.11+ Suggested-by: Matthew Auld matthew.auld@intel.com Signed-off-by: Sanjay Yadav sanjay.kumar.yadav@intel.com --- drivers/gpu/drm/xe/xe_oa.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-)
diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c index 87a2bf53d661..8f954bc3eed5 100644 --- a/drivers/gpu/drm/xe/xe_oa.c +++ b/drivers/gpu/drm/xe/xe_oa.c @@ -2403,11 +2403,13 @@ int xe_oa_add_config_ioctl(struct drm_device *dev, u64 data, struct drm_file *fi goto sysfs_err; }
- mutex_unlock(&oa->metrics_lock); + id = oa_config->id; + + drm_dbg(&oa->xe->drm, "Added config %s id=%i\n", oa_config->uuid, id);
- drm_dbg(&oa->xe->drm, "Added config %s id=%i\n", oa_config->uuid, oa_config->id); + mutex_unlock(&oa->metrics_lock);
- return oa_config->id; + return id;
sysfs_err: mutex_unlock(&oa->metrics_lock); @@ -2461,10 +2463,10 @@ int xe_oa_remove_config_ioctl(struct drm_device *dev, u64 data, struct drm_file sysfs_remove_group(oa->metrics_kobj, &oa_config->sysfs_metric); idr_remove(&oa->metrics_idr, arg);
- mutex_unlock(&oa->metrics_lock); - drm_dbg(&oa->xe->drm, "Removed config %s id=%i\n", oa_config->uuid, oa_config->id);
+ mutex_unlock(&oa->metrics_lock); + xe_oa_config_put(oa_config);
return 0;
On 17/11/2025 14:44, Sanjay Yadav wrote:
In xe_oa_add_config_ioctl(), we accessed oa_config->id after dropping metrics_lock. Since this lock protects the lifetime of oa_config, an attacker could guess the id and call xe_oa_remove_config_ioctl() with perfect timing, freeing oa_config before we dereference it, leading to a potential use-after-free.
Fix this by caching the id in a local variable while holding the lock.
Closes: https://gitlab.freedesktop.org/drm/xe/kernel/-/issues/6614 Fixes: cdf02fe1a94a7 ("drm/xe/oa/uapi: Add/remove OA config perf ops") Cc: stable@vger.kernel.org # v6.11+ Suggested-by: Matthew Auld matthew.auld@intel.com Signed-off-by: Sanjay Yadav sanjay.kumar.yadav@intel.com
drivers/gpu/drm/xe/xe_oa.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-)
diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c index 87a2bf53d661..8f954bc3eed5 100644 --- a/drivers/gpu/drm/xe/xe_oa.c +++ b/drivers/gpu/drm/xe/xe_oa.c @@ -2403,11 +2403,13 @@ int xe_oa_add_config_ioctl(struct drm_device *dev, u64 data, struct drm_file *fi goto sysfs_err; }
- mutex_unlock(&oa->metrics_lock);
- id = oa_config->id;
- drm_dbg(&oa->xe->drm, "Added config %s id=%i\n", oa_config->uuid, id);
- drm_dbg(&oa->xe->drm, "Added config %s id=%i\n", oa_config->uuid, oa_config->id);
- mutex_unlock(&oa->metrics_lock);
- return oa_config->id;
- return id;
sysfs_err: mutex_unlock(&oa->metrics_lock); @@ -2461,10 +2463,10 @@ int xe_oa_remove_config_ioctl(struct drm_device *dev, u64 data, struct drm_file sysfs_remove_group(oa->metrics_kobj, &oa_config->sysfs_metric); idr_remove(&oa->metrics_idr, arg);
- mutex_unlock(&oa->metrics_lock);
- drm_dbg(&oa->xe->drm, "Removed config %s id=%i\n", oa_config->uuid, oa_config->id);
- mutex_unlock(&oa->metrics_lock);
AFAICT there is not need for this change, since this path is holding a reference to the config which is only dropped below?
xe_oa_config_put(oa_config); return 0;
linux-stable-mirror@lists.linaro.org