Commit b7d0949f authored by Martin Krastev's avatar Martin Krastev Committed by Zack Rusin

drm/vmwgfx: Refactor vmw_mksstat_remove_ioctl to expect pgid match with...

drm/vmwgfx: Refactor vmw_mksstat_remove_ioctl to expect pgid match with vmw_mksstat_add_ioctl to authorise removal.

Original vmw_mksstat_remove_ioctl expected pid to match the corresponding vmw_mksstat_add_ioctl.
That made impossible en-masse removals by one pid, which is a valid use case, so pid match was
discarded. Current change enforces a broader pgid match as a form of protection from arbitrary
processes interrupting an ongoing mks-guest-stats.
Reviewed-by: default avatarZack Rusin <zackr@vmware.com>
Signed-off-by: default avatarMartin Krastev <krastevm@vmware.com>
Signed-off-by: default avatarZack Rusin <zackr@vmware.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20210609172307.131929-8-zackr@vmware.com
parent 8d9a8d9b
......@@ -1111,7 +1111,7 @@ int vmw_mksstat_add_ioctl(struct drm_device *dev, void *data,
hypervisor_ppn_add((PPN64)page_to_pfn(page));
dev_priv->mksstat_user_pages[slot] = page;
atomic_set(&dev_priv->mksstat_user_pids[slot], current->pid);
atomic_set(&dev_priv->mksstat_user_pids[slot], task_pgrp_vnr(current));
arg->id = slot;
......@@ -1158,37 +1158,31 @@ int vmw_mksstat_remove_ioctl(struct drm_device *dev, void *data,
struct vmw_private *const dev_priv = vmw_priv(dev);
const size_t slot = arg->id;
pid_t pid0;
pid_t pgid, pid;
if (slot >= ARRAY_SIZE(dev_priv->mksstat_user_pids))
return -EINVAL;
DRM_DEV_INFO(dev->dev, "pid=%d arg.id=%lu\n", current->pid, slot);
pid0 = atomic_read(&dev_priv->mksstat_user_pids[slot]);
pgid = task_pgrp_vnr(current);
pid = atomic_cmpxchg(&dev_priv->mksstat_user_pids[slot], pgid, MKSSTAT_PID_RESERVED);
if (!pid0)
if (!pid)
return 0;
if (pid0 != MKSSTAT_PID_RESERVED) {
const pid_t pid1 = atomic_cmpxchg(&dev_priv->mksstat_user_pids[slot], pid0, MKSSTAT_PID_RESERVED);
if (pid == pgid) {
struct page *const page = dev_priv->mksstat_user_pages[slot];
if (!pid1)
return 0;
if (pid1 == pid0) {
struct page *const page = dev_priv->mksstat_user_pages[slot];
BUG_ON(!page);
BUG_ON(!page);
dev_priv->mksstat_user_pages[slot] = NULL;
atomic_set(&dev_priv->mksstat_user_pids[slot], 0);
dev_priv->mksstat_user_pages[slot] = NULL;
atomic_set(&dev_priv->mksstat_user_pids[slot], 0);
hypervisor_ppn_remove((PPN64)page_to_pfn(page));
hypervisor_ppn_remove((PPN64)page_to_pfn(page));
vmw_mksstat_cleanup_descriptor(page);
return 0;
}
vmw_mksstat_cleanup_descriptor(page);
return 0;
}
return -EAGAIN;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment