Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 205181
b: refs/heads/master
c: 3fb688f
h: refs/heads/master
i:
  205179: aa088e4
v: v3
  • Loading branch information
Chris Wilson authored and Dave Airlie committed Aug 4, 2010
1 parent ccbe3f4 commit a662591
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 20 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: dc77de12dde95c8da39e4c417eb70c7d445cf84b
refs/heads/master: 3fb688fdc1890f9e8e97597f690c145ab888aec0
85 changes: 66 additions & 19 deletions trunk/drivers/gpu/drm/drm_ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,19 @@ int drm_getunique(struct drm_device *dev, void *data,
return 0;
}

static void
drm_unset_busid(struct drm_device *dev,
struct drm_master *master)
{
kfree(dev->devname);
dev->devname = NULL;

kfree(master->unique);
master->unique = NULL;
master->unique_len = 0;
master->unique_size = 0;
}

/**
* Set the bus id.
*
Expand Down Expand Up @@ -94,17 +107,24 @@ int drm_setunique(struct drm_device *dev, void *data,
master->unique_len = u->unique_len;
master->unique_size = u->unique_len + 1;
master->unique = kmalloc(master->unique_size, GFP_KERNEL);
if (!master->unique)
return -ENOMEM;
if (copy_from_user(master->unique, u->unique, master->unique_len))
return -EFAULT;
if (!master->unique) {
ret = -ENOMEM;
goto err;
}

if (copy_from_user(master->unique, u->unique, master->unique_len)) {
ret = -EFAULT;
goto err;
}

master->unique[master->unique_len] = '\0';

dev->devname = kmalloc(strlen(dev->driver->pci_driver.name) +
strlen(master->unique) + 2, GFP_KERNEL);
if (!dev->devname)
return -ENOMEM;
if (!dev->devname) {
ret = -ENOMEM;
goto err;
}

sprintf(dev->devname, "%s@%s", dev->driver->pci_driver.name,
master->unique);
Expand All @@ -113,24 +133,36 @@ int drm_setunique(struct drm_device *dev, void *data,
* busid.
*/
ret = sscanf(master->unique, "PCI:%d:%d:%d", &bus, &slot, &func);
if (ret != 3)
return -EINVAL;
if (ret != 3) {
ret = -EINVAL;
goto err;
}

domain = bus >> 8;
bus &= 0xff;

if ((domain != drm_get_pci_domain(dev)) ||
(bus != dev->pdev->bus->number) ||
(slot != PCI_SLOT(dev->pdev->devfn)) ||
(func != PCI_FUNC(dev->pdev->devfn)))
return -EINVAL;
(func != PCI_FUNC(dev->pdev->devfn))) {
ret = -EINVAL;
goto err;
}

return 0;

err:
drm_unset_busid(dev, master);
return ret;
}

static int drm_set_busid(struct drm_device *dev, struct drm_file *file_priv)
{
struct drm_master *master = file_priv->master;
int len;
int len, ret;

if (master->unique != NULL)
drm_unset_busid(dev, master);

if (drm_core_check_feature(dev, DRIVER_USE_PLATFORM_DEVICE)) {
master->unique_len = 10 + strlen(dev->platformdev->name);
Expand All @@ -142,15 +174,20 @@ static int drm_set_busid(struct drm_device *dev, struct drm_file *file_priv)
len = snprintf(master->unique, master->unique_len,
"platform:%s", dev->platformdev->name);

if (len > master->unique_len)
if (len > master->unique_len) {
DRM_ERROR("Unique buffer overflowed\n");
ret = -EINVAL;
goto err;
}

dev->devname =
kmalloc(strlen(dev->platformdev->name) +
master->unique_len + 2, GFP_KERNEL);

if (dev->devname == NULL)
return -ENOMEM;
if (dev->devname == NULL) {
ret = -ENOMEM;
goto err;
}

sprintf(dev->devname, "%s@%s", dev->platformdev->name,
master->unique);
Expand All @@ -168,23 +205,31 @@ static int drm_set_busid(struct drm_device *dev, struct drm_file *file_priv)
dev->pdev->bus->number,
PCI_SLOT(dev->pdev->devfn),
PCI_FUNC(dev->pdev->devfn));
if (len >= master->unique_len)
if (len >= master->unique_len) {
DRM_ERROR("buffer overflow");
else
ret = -EINVAL;
goto err;
} else
master->unique_len = len;

dev->devname =
kmalloc(strlen(dev->driver->pci_driver.name) +
master->unique_len + 2, GFP_KERNEL);

if (dev->devname == NULL)
return -ENOMEM;
if (dev->devname == NULL) {
ret = -ENOMEM;
goto err;
}

sprintf(dev->devname, "%s@%s", dev->driver->pci_driver.name,
master->unique);
}

return 0;

err:
drm_unset_busid(dev, master);
return ret;
}

/**
Expand Down Expand Up @@ -348,7 +393,9 @@ int drm_setversion(struct drm_device *dev, void *data, struct drm_file *file_pri
/*
* Version 1.1 includes tying of DRM to specific device
*/
drm_set_busid(dev, file_priv);
retcode = drm_set_busid(dev, file_priv);
if (retcode)
goto done;
}
}

Expand Down

0 comments on commit a662591

Please sign in to comment.