From: Jon S. <jon...@gm...> - 2005-08-03 17:02:44
Attachments:
drm.patch
|
This patch removes the need for root to run DRM. It is attached too in case gmail destroys the formatting. Major highlights: 1) removal of the general root check on the IOCTLs, added root check in Add= Map 1) permanent SAREA map 2) user space can AddMap AGP maps, AGP maps are restricted to creation in AGP space. 3) Deprecation of some radeon variables now calculated by the driver I haven't converted PCI GART support. You still need to be root for it to w= ork. Please look it over and tell me if I have created any security holes. --=20 Jon Smirl jon...@gm... diff --git a/linux-core/drmP.h b/linux-core/drmP.h --- a/linux-core/drmP.h +++ b/linux-core/drmP.h @@ -280,7 +280,7 @@ typedef int drm_ioctl_compat_t(struct fi typedef struct drm_ioctl_desc { =09drm_ioctl_t *func; =09int auth_needed; -=09int root_only; +=09int master; } drm_ioctl_desc_t; =20 typedef struct drm_devstate { @@ -375,6 +375,7 @@ typedef struct drm_buf_entry { /** File private data */ typedef struct drm_file { =09int authenticated; +=09int master; =09int minor; =09pid_t pid; =09uid_t uid; diff --git a/linux-core/drm_bufs.c b/linux-core/drm_bufs.c --- a/linux-core/drm_bufs.c +++ b/linux-core/drm_bufs.c @@ -56,7 +56,8 @@ static drm_local_map_t *drm_find_matchin =09list_for_each(list, &dev->maplist->head) { =09=09drm_map_list_t *entry =3D list_entry(list, drm_map_list_t, head); =09=09if (entry->map && map->type =3D=3D entry->map->type && -=09=09 entry->map->offset =3D=3D map->offset) { +=09=09 ((entry->map->offset =3D=3D map->offset) || +=09=09 (map->type =3D=3D _DRM_SHM))) { =09=09=09return entry->map; =09=09} =09} @@ -163,6 +164,19 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09map->handle =3D drm_ioremap(map->offset, map->size, dev); =09=09break; =09case _DRM_SHM: +=09=09found_map =3D drm_find_matching_map(dev, map); +=09=09if (found_map !=3D NULL) { +=09=09=09if (found_map->size !=3D map->size) { +=09=09=09=09DRM_DEBUG("Matching maps of type %d with " +=09=09=09=09 "mismatched sizes, (%ld vs %ld)\n", +=09=09=09=09 map->type, map->size, found_map->size); +=09=09=09=09found_map->size =3D map->size; +=09=09=09} + +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09*map_ptr =3D found_map; +=09=09=09return 0; +=09=09} =09=09map->handle =3D vmalloc_32(map->size); =09=09DRM_DEBUG("%lu %d %p\n", =09=09=09 map->size, drm_order(map->size), map->handle); @@ -181,15 +195,34 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09dev->sigdata.lock =3D dev->lock.hw_lock =3D map->handle;=09/* Po= inter to lock */ =09=09} =09=09break; -=09case _DRM_AGP: -=09=09if (drm_core_has_AGP(dev)) { +=09case _DRM_AGP: { +=09=09drm_agp_mem_t *entry; +=09=09int valid =3D 0; + +=09=09if (!drm_core_has_AGP(dev)) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EINVAL; +=09=09} #ifdef __alpha__ -=09=09=09map->offset +=3D dev->hose->mem_space->start; +=09=09map->offset +=3D dev->hose->mem_space->start; #endif -=09=09=09map->offset +=3D dev->agp->base; -=09=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ +=09=09map->offset +=3D dev->agp->base; +=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ + +=09=09for (entry =3D dev->agp->memory; entry; entry =3D entry->next) { +=09=09=09if ((map->offset >=3D entry->bound) && +=09=09=09 (map->offset + map->offset <=3D entry->bound + entry->pages * PAGE_SIZE)) { +=09=09=09=09valid =3D 1; +=09=09=09=09break; +=09=09=09} +=09=09} +=09=09if (!valid) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EPERM; =09=09} +=09=09DRM_DEBUG("AGP offset =3D 0x%08lx, size =3D 0x%08lx\n", map->offset,= map->size); =09=09break; +=09} =09case _DRM_SCATTER_GATHER: =09=09if (!dev->sg) { =09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); @@ -258,6 +291,9 @@ int drm_addmap_ioctl(struct inode *inode =09=09return -EFAULT; =09} =20 +=09if (!(capable(CAP_SYS_ADMIN) || map.type =3D=3D _DRM_AGP)) +=09=09return -EPERM; + =09err =3D drm_addmap( dev, map.offset, map.size, map.type, map.flags, =09=09=09 & map_ptr ); =20 diff --git a/linux-core/drm_drv.c b/linux-core/drm_drv.c --- a/linux-core/drm_drv.c +++ b/linux-core/drm_drv.c @@ -545,13 +545,14 @@ int drm_ioctl(struct inode *inode, struc =09if (!func) { =09=09DRM_DEBUG("no function\n"); =09=09retcode =3D -EINVAL; -=09} else if ((ioctl->root_only && !capable(CAP_SYS_ADMIN)) || -=09=09 (ioctl->auth_needed && !priv->authenticated)) { +=09} else if (((ioctl->master && !priv->master) || +=09=09 (ioctl->auth_needed && !priv->authenticated)) && +=09=09 (!capable(CAP_SYS_ADMIN))) { =09=09retcode =3D -EACCES; =09} else { =09=09retcode =3D func(inode, filp, cmd, arg); =09} - err_i1: +err_i1: =09atomic_dec(&dev->ioctl_count); =09if (retcode) =09=09DRM_DEBUG("ret =3D %x\n", retcode); diff --git a/linux-core/drm_fops.c b/linux-core/drm_fops.c --- a/linux-core/drm_fops.c +++ b/linux-core/drm_fops.c @@ -34,18 +34,26 @@ * OTHER DEALINGS IN THE SOFTWARE. */ =20 -#include "drmP.h" #include <linux/poll.h> =20 +#include "drmP.h" +#include "drm_sarea.h" + static int drm_open_helper(struct inode *inode, struct file *filp, drm_device_t * dev); =20 static int drm_setup(drm_device_t * dev) { +=09drm_local_map_t *map; =09int i; =20 =09if (dev->driver->presetup) =09=09dev->driver->presetup(dev); =20 +=09/* prebuild the SAREA */ +=09i =3D drm_addmap(dev, 0, SAREA_MAX, _DRM_SHM, _DRM_CONTAINS_LOCK, &map)= ; +=09if (i !=3D 0) +=09=09return i; + =09atomic_set(&dev->ioctl_count, 0); =09atomic_set(&dev->vma_count, 0); =09dev->buf_use =3D 0; @@ -244,6 +252,7 @@ static int drm_open_helper(struct inode=20 =09priv->minor =3D minor; =09priv->head =3D drm_heads[minor]; =09priv->ioctl_count =3D 0; +=09/* for compatibility root is always authenticated */ =09priv->authenticated =3D capable(CAP_SYS_ADMIN); =09priv->lock_count =3D 0; =20 @@ -259,6 +268,9 @@ static int drm_open_helper(struct inode=20 =09=09priv->prev =3D NULL; =09=09dev->file_first =3D priv; =09=09dev->file_last =3D priv; +=09=09/* first opener automatically becomes master and authenticated */ +=09=09priv->master =3D 1; +=09=09priv->authenticated =3D 1; =09} else { =09=09priv->next =3D NULL; =09=09priv->prev =3D dev->file_last; diff --git a/linux-core/drm_stub.c b/linux-core/drm_stub.c diff --git a/shared-core/drm.h b/shared-core/drm.h --- a/shared-core/drm.h +++ b/shared-core/drm.h @@ -62,6 +62,12 @@ #define __user #endif =20 +#ifdef __GNUC__ +# define DEPRECATED __attribute__ ((deprecated)) +#else +# define DEPRECATED +#endif + #if defined(__linux__) #if defined(__KERNEL__) #include <linux/config.h> diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c --- a/shared-core/radeon_cp.c +++ b/shared-core/radeon_cp.c @@ -1245,7 +1245,7 @@ static void radeon_set_pciegart(drm_rade =09u32 tmp =3D RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL); =09if (on) { =20 -=09=09DRM_DEBUG("programming pcie %08X %08lX %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); +=09=09DRM_DEBUG("programming pcie %08X %08X %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_DISCARD_RD_ADDR_LO, dev_priv->gart_vm_start); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_BASE, dev_priv->bus_pci_gart); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_START_LO, dev_priv->gart_vm_st= art); @@ -1398,8 +1398,6 @@ static int radeon_do_init_cp(drm_device_ =20 =09DRM_GETSAREA(); =20 -=09dev_priv->fb_offset =3D init->fb_offset; -=09dev_priv->mmio_offset =3D init->mmio_offset; =09dev_priv->ring_offset =3D init->ring_offset; =09dev_priv->ring_rptr_offset =3D init->ring_rptr_offset; =09dev_priv->buffers_offset =3D init->buffers_offset; @@ -1411,12 +1409,6 @@ static int radeon_do_init_cp(drm_device_ =09=09return DRM_ERR(EINVAL); =09} =20 -=09dev_priv->mmio =3D drm_core_findmap(dev, init->mmio_offset); -=09if (!dev_priv->mmio) { -=09=09DRM_ERROR("could not find mmio region!\n"); -=09=09radeon_do_cleanup_cp(dev); -=09=09return DRM_ERR(EINVAL); -=09} =09dev_priv->cp_ring =3D drm_core_findmap(dev, init->ring_offset); =09if (!dev_priv->cp_ring) { =09=09DRM_ERROR("could not find cp ring region!\n"); diff --git a/shared-core/radeon_drm.h b/shared-core/radeon_drm.h --- a/shared-core/radeon_drm.h +++ b/shared-core/radeon_drm.h @@ -492,7 +492,7 @@ typedef struct drm_radeon_init { =09=09RADEON_INIT_R300_CP =3D 0x04 =09} func; =09unsigned long sarea_priv_offset; -=09int is_pci;=09=09/* not used, driver asks hardware */ +=09int is_pci DEPRECATED;=09=09=09/* deprecated, driver asks hardware */ =09int cp_mode; =09int gart_size; =09int ring_size; @@ -504,8 +504,8 @@ typedef struct drm_radeon_init { =09unsigned int depth_bpp; =09unsigned int depth_offset, depth_pitch; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; +=09unsigned long fb_offset DEPRECATED;=09/* deprecated, driver asks hardwa= re */ +=09unsigned long mmio_offset DEPRECATED;=09/* deprecated, driver asks hard= ware */ =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_drv.h b/shared-core/radeon_drv.h --- a/shared-core/radeon_drv.h +++ b/shared-core/radeon_drv.h @@ -242,8 +242,6 @@ typedef struct drm_radeon_private { =20 =09drm_radeon_depth_clear_t depth_clear; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_state.c b/shared-core/radeon_state.c --- a/shared-core/radeon_state.c +++ b/shared-core/radeon_state.c @@ -2917,7 +2917,7 @@ static int radeon_cp_getparam(DRM_IOCTL_ =09=09value =3D dev_priv->gart_vm_start; =09=09break; =09case RADEON_PARAM_REGISTER_HANDLE: -=09=09value =3D dev_priv->mmio_offset; +=09=09value =3D dev_priv->mmio->offset; =09=09break; =09case RADEON_PARAM_STATUS_HANDLE: =09=09value =3D dev_priv->ring_rptr_offset; |
From: Eric A. <et...@lc...> - 2005-08-03 17:45:18
|
On Wed, 2005-08-03 at 12:58 -0400, Jon Smirl wrote: > This patch removes the need for root to run DRM. It is attached too in > case gmail destroys the formatting. > > Major highlights: > 1) removal of the general root check on the IOCTLs, added root check in AddMap > 1) permanent SAREA map I like that the SAREA setup was in the setup hook. Thanks. > 2) user space can AddMap AGP maps, AGP maps are restricted to creation > in AGP space. > 3) Deprecation of some radeon variables now calculated by the driver > > I haven't converted PCI GART support. You still need to be root for it to work. > > Please look it over and tell me if I have created any security holes. > > -- > Jon Smirl > jon...@gm... > @@ -163,6 +164,19 @@ int drm_addmap(drm_device_t * dev, unsig > map->handle = drm_ioremap(map->offset, map->size, dev); > break; > case _DRM_SHM: > + found_map = drm_find_matching_map(dev, map); > + if (found_map != NULL) { > + if (found_map->size != map->size) { > + DRM_DEBUG("Matching maps of type %d with " > + "mismatched sizes, (%ld vs %ld)\n", > + map->type, map->size, found_map->size); > + found_map->size = map->size; > + } > + > + drm_free(map, sizeof(*map), DRM_MEM_MAPS); > + *map_ptr = found_map; > + return 0; > + } I'm uncomfortable with this "matching maps with mismatched sizes" code that now exists in 2 places, and would like to see what the reasoning is behind it. > diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c > --- a/shared-core/radeon_cp.c > +++ b/shared-core/radeon_cp.c > @@ -1245,7 +1245,7 @@ static void radeon_set_pciegart(drm_rade > u32 tmp = RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL); > if (on) { > > - DRM_DEBUG("programming pcie %08X %08lX %08X\n", > dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); > + DRM_DEBUG("programming pcie %08X %08X %08X\n", > dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); > RADEON_WRITE_PCIE(RADEON_PCIE_TX_DISCARD_RD_ADDR_LO, > dev_priv->gart_vm_start); > RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_BASE, dev_priv->bus_pci_gart); > RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_START_LO, dev_priv->gart_vm_start); A dma_addr_t (dev_priv->bus_pci_gart) is a long on at least some systems. While we may know that it's 32 bits here, a cast will be needed to avoid warnings. ioctls where removing the root check introduces privelege escalation for users with read access to the DRM device (at least): - DRM_R128_INDIRECT - DRM_RADEON_INDIRECT -- Eric Anholt et...@lc... http://people.freebsd.org/~anholt/ anholt@FreeBSD.org |
From: Jon S. <jon...@gm...> - 2005-08-03 18:59:58
Attachments:
drm.patch
|
I forgot to add this in the first patch, you will GPF without it. The attachment includes it. @@ -72,7 +80,7 @@ static int drm_setup(drm_device_t * dev) =09INIT_LIST_HEAD(&dev->ctxlist->head); =20 =09dev->vmalist =3D NULL; -=09dev->sigdata.lock =3D dev->lock.hw_lock =3D NULL; +=09dev->sigdata.lock =3D NULL; =09init_waitqueue_head(&dev->lock.lock_queue); =09dev->queue_count =3D 0; =09dev->queue_reserved =3D 0; --=20 Jon Smirl jon...@gm... |
From: Jon S. <jon...@gm...> - 2005-08-03 18:39:36
|
On 8/3/05, Eric Anholt <et...@lc...> wrote: > > @@ -163,6 +164,19 @@ int drm_addmap(drm_device_t * dev, unsig > > map->handle =3D drm_ioremap(map->offset, map->siz= e, dev); > > break; > > case _DRM_SHM: > > + found_map =3D drm_find_matching_map(dev, map); > > + if (found_map !=3D NULL) { > > + if (found_map->size !=3D map->size) { > > + DRM_DEBUG("Matching maps of type %d with = " > > + "mismatched sizes, (%ld vs %ld)\n", > > + map->type, map->size, found_map->size= ); > > + found_map->size =3D map->size; > > + } > > + > > + drm_free(map, sizeof(*map), DRM_MEM_MAPS); > > + *map_ptr =3D found_map; > > + return 0; > > + } >=20 > I'm uncomfortable with this "matching maps with mismatched sizes" code > that now exists in 2 places, and would like to see what the reasoning is > behind it. Existing Xservers ask for maps that are not the correct size. This lets them keep working. >=20 > > diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c > > --- a/shared-core/radeon_cp.c > > +++ b/shared-core/radeon_cp.c > > @@ -1245,7 +1245,7 @@ static void radeon_set_pciegart(drm_rade > > u32 tmp =3D RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL); > > if (on) { > > > > - DRM_DEBUG("programming pcie %08X %08lX %08X\n", > > dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); > > + DRM_DEBUG("programming pcie %08X %08X %08X\n", > > dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); > > RADEON_WRITE_PCIE(RADEON_PCIE_TX_DISCARD_RD_ADDR_LO, > > dev_priv->gart_vm_start); > > RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_BASE, dev_priv->bus= _pci_gart); > > RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_START_LO, dev_priv-= >gart_vm_start); >=20 > A dma_addr_t (dev_priv->bus_pci_gart) is a long on at least some > systems. While we may know that it's 32 bits here, a cast will be > needed to avoid warnings. I was getting a warning in my build. >=20 > ioctls where removing the root check introduces privelege escalation for > users with read access to the DRM device (at least): > - DRM_R128_INDIRECT > - DRM_RADEON_INDIRECT How do we secure these? --=20 Jon Smirl jon...@gm... |
From: Eric A. <et...@lc...> - 2005-08-03 19:00:44
|
On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > ioctls where removing the root check introduces privelege escalation for > > users with read access to the DRM device (at least): > > - DRM_R128_INDIRECT > > - DRM_RADEON_INDIRECT > > How do we secure these? By requiring root. But I didn't review all the ioctls, so these might not be all of the root-requiring ioctls that continue to need it. -- Eric Anholt et...@lc... http://people.freebsd.org/~anholt/ anholt@FreeBSD.org |
From: Jon S. <jon...@gm...> - 2005-08-03 19:03:14
|
On 8/3/05, Eric Anholt <et...@lc...> wrote: > On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > > ioctls where removing the root check introduces privelege escalation = for > > > users with read access to the DRM device (at least): > > > - DRM_R128_INDIRECT > > > - DRM_RADEON_INDIRECT > > > > How do we secure these? >=20 > By requiring root. But I didn't review all the ioctls, so these might > not be all of the root-requiring ioctls that continue to need it. I thought we built a command verifier to check things like this. Does DRM need to copy, verify, then execute? >=20 > -- > Eric Anholt et...@lc... > http://people.freebsd.org/~anholt/ anholt@FreeBSD.org >=20 --=20 Jon Smirl jon...@gm... |
From: Eric A. <et...@lc...> - 2005-08-03 19:05:56
|
On Wed, 2005-08-03 at 15:02 -0400, Jon Smirl wrote: > On 8/3/05, Eric Anholt <et...@lc...> wrote: > > On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > > > ioctls where removing the root check introduces privelege escalation for > > > > users with read access to the DRM device (at least): > > > > - DRM_R128_INDIRECT > > > > - DRM_RADEON_INDIRECT > > > > > > How do we secure these? > > > > By requiring root. But I didn't review all the ioctls, so these might > > not be all of the root-requiring ioctls that continue to need it. > > I thought we built a command verifier to check things like this. Does > DRM need to copy, verify, then These are the indirect ioctls, which allow the X Server to submit a buffer of any commands it wants. You could probably build a (or extend the current) verifier for the all the things the X Server has done through that ioctl, but that hasn't been done. -- Eric Anholt et...@lc... http://people.freebsd.org/~anholt/ anholt@FreeBSD.org |
From: Jon S. <jon...@gm...> - 2005-08-03 19:14:44
|
On 8/3/05, Eric Anholt <et...@lc...> wrote: > On Wed, 2005-08-03 at 15:02 -0400, Jon Smirl wrote: > > On 8/3/05, Eric Anholt <et...@lc...> wrote: > > > On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > > > > ioctls where removing the root check introduces privelege escalat= ion for > > > > > users with read access to the DRM device (at least): > > > > > - DRM_R128_INDIRECT > > > > > - DRM_RADEON_INDIRECT > > > > > > > > How do we secure these? > > > > > > By requiring root. But I didn't review all the ioctls, so these migh= t > > > not be all of the root-requiring ioctls that continue to need it. > > > > I thought we built a command verifier to check things like this. Does > > DRM need to copy, verify, then >=20 > These are the indirect ioctls, which allow the X Server to submit a > buffer of any commands it wants. You could probably build a (or extend > the current) verifier for the all the things the X Server has done > through that ioctl, but that hasn't been done. So there is probably a general security hole here if I can convice the Xserver to use the buffer addresses I want. Who uses these? They aren't used in the mesa tree. >=20 > -- > Eric Anholt et...@lc... > http://people.freebsd.org/~anholt/ anholt@FreeBSD.org >=20 --=20 Jon Smirl jon...@gm... |
From: Michel <mi...@da...> - 2005-08-03 19:21:52
|
On Wed, 2005-08-03 at 15:14 -0400, Jon Smirl wrote: > On 8/3/05, Eric Anholt <et...@lc...> wrote: > >=20 > > These are the indirect ioctls, which allow the X Server to submit a > > buffer of any commands it wants. You could probably build a (or extend > > the current) verifier for the all the things the X Server has done > > through that ioctl, but that hasn't been done. >=20 > So there is probably a general security hole here if I can convice the > Xserver to use the buffer addresses I want. That would require a security hole in the X server. The attacker is root already in that case. > Who uses these?=20 The current DDX drivers. > They aren't used in the mesa tree. So why did you change their requiring root? --=20 Earthling Michel D=C3=A4nzer | Debian (powerpc), X and DRI develop= er Libre software enthusiast | http://svcs.affero.net/rm.php?r=3Ddaenzer |
From: Jon S. <jon...@gm...> - 2005-08-03 20:19:39
|
On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > On Wed, 2005-08-03 at 15:14 -0400, Jon Smirl wrote: > > On 8/3/05, Eric Anholt <et...@lc...> wrote: > > > > > > These are the indirect ioctls, which allow the X Server to submit a > > > buffer of any commands it wants. You could probably build a (or exte= nd > > > the current) verifier for the all the things the X Server has done > > > through that ioctl, but that hasn't been done. > > > > So there is probably a general security hole here if I can convice the > > Xserver to use the buffer addresses I want. >=20 > That would require a security hole in the X server. The attacker is root > already in that case. >=20 > > Who uses these? >=20 > The current DDX drivers. >=20 > > They aren't used in the mesa tree. >=20 > So why did you change their requiring root? The version of Xegl I am making does not run as root. It handles multiuser by letting each user run their own instance of Xegl as a normal app. To make this work I have to modify DRM to not need root priv to run. I removed the general root priv check that covered all ioctls. Now we need to review and add it back individually on the ones that need it. For example AddMap was modified to allow mesa to work without root but some of the things X does still need root. The indirect ioctls are not used by mesa. In a little while I'll put together a new patch that adds the root requirement back on those ioctls. --=20 Jon Smirl jon...@gm... |
From: Michel <mi...@da...> - 2005-08-03 20:30:14
|
On Wed, 2005-08-03 at 16:18 -0400, Jon Smirl wrote: > On 8/3/05, Michel D=C3=A4nzer <mi...@da...> wrote: > > > > > > They aren't used in the mesa tree. > >=20 > > So why did you change their requiring root? >=20 > The version of Xegl I am making does not run as root. [...] I know. You missed my question: Why do you change the behaviour of code that doesn't affect what you're trying to achieve? --=20 Earthling Michel D=C3=A4nzer | Debian (powerpc), X and DRI develop= er Libre software enthusiast | http://svcs.affero.net/rm.php?r=3Ddaenzer |
From: Jon S. <jon...@gm...> - 2005-08-03 21:10:55
|
On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > On Wed, 2005-08-03 at 16:18 -0400, Jon Smirl wrote: > > On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > > > > > > > > They aren't used in the mesa tree. > > > > > > So why did you change their requiring root? > > > > The version of Xegl I am making does not run as root. [...] >=20 > I know. You missed my question: Why do you change the behaviour of code > that doesn't affect what you're trying to achieve? The original code did not separate the concept of auth and root, they were implemented as the same bit. I had to separate the concepts. I kept all of the code implementing auth unchanged. There was a single check looking for root across all IOCTLs. I had to remove that check. Now we have have to identify the IOCTLs that really require root and add the check specifically to them. So far there are only two: addmap and indirect. I could have made three bits: auth_needed, root_only, master. But that was a lot of deltas to implement a root_only bit which is only needed for indirect. Instead it is easier to just add a capability root check in the ioctl. You can't uses a root only bit on addmap since the root requirement is a function of the parameters passed in. --=20 Jon Smirl jon...@gm... |
From: Eric A. <et...@lc...> - 2005-08-03 23:37:45
|
On Wed, 2005-08-03 at 17:10 -0400, Jon Smirl wrote: > On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > > On Wed, 2005-08-03 at 16:18 -0400, Jon Smirl wrote: > > > On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > > > > > > > > > > They aren't used in the mesa tree. > > > > > > > > So why did you change their requiring root? > > > > > > The version of Xegl I am making does not run as root. [...] > >=20 > > I know. You missed my question: Why do you change the behaviour of code > > that doesn't affect what you're trying to achieve? >=20 > The original code did not separate the concept of auth and root, they > were implemented as the same bit. I had to separate the concepts. I > kept all of the code implementing auth unchanged. >=20 > There was a single check looking for root across all IOCTLs. I had to > remove that check. Now we have have to identify the IOCTLs that > really require root and add the check specifically to them. So far > there are only two: addmap and indirect. >=20 > I could have made three bits: auth_needed, root_only, master. But > that was a lot of deltas to implement a root_only bit which is only > needed for indirect. Instead it is easier to just add a capability > root check in the ioctl. In your previous patch you removed the root check entirely, even though that lead to vulnerabilities. I pointed out two cases, but I didn't review all the ioctls. Before a patch based on this goes in, I would like a review of every previously root-requiring ioctl to explain why it's okay to not require root on it now. Alternatively, you could do what Michel suggested: make only the changes that are required for your nonroot case, so that the security implications are (relatively) obvious. --=20 Eric Anholt et...@lc... http://people.freebsd.org/~anholt/ anholt@FreeBSD.org |
From: Jon S. <jon...@gm...> - 2005-08-03 22:53:51
|
On 8/3/05, Eric Anholt <et...@lc...> wrote: > On Wed, 2005-08-03 at 17:10 -0400, Jon Smirl wrote: > > On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > > > On Wed, 2005-08-03 at 16:18 -0400, Jon Smirl wrote: > > > > On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > > > > > > > > > > > > They aren't used in the mesa tree. > > > > > > > > > > So why did you change their requiring root? > > > > > > > > The version of Xegl I am making does not run as root. [...] > > > > > > I know. You missed my question: Why do you change the behaviour of co= de > > > that doesn't affect what you're trying to achieve? > > > > The original code did not separate the concept of auth and root, they > > were implemented as the same bit. I had to separate the concepts. I > > kept all of the code implementing auth unchanged. > > > > There was a single check looking for root across all IOCTLs. I had to > > remove that check. Now we have have to identify the IOCTLs that > > really require root and add the check specifically to them. So far > > there are only two: addmap and indirect. > > > > I could have made three bits: auth_needed, root_only, master. But > > that was a lot of deltas to implement a root_only bit which is only > > needed for indirect. Instead it is easier to just add a capability > > root check in the ioctl. >=20 > In your previous patch you removed the root check entirely, even though > that lead to vulnerabilities. I pointed out two cases, but I didn't > review all the ioctls. Before a patch based on this goes in, I would > like a review of every previously root-requiring ioctl to explain why > it's okay to not require root on it now. I have been asking on this list for a month now for everyone to help locate where there are vulnerabilities with dropping root priv. Multiple people have told me that AddMap was the only problem. You just pointed out another one with radeon/r128 indirect. > Alternatively, you could do what Michel suggested: make only the changes > that are required for your nonroot case, so that the security > implications are (relatively) obvious. Mesa hits every main DRM entry point. I believe the problem is now with the drivers. Are there other X only driver entry points? It is more reliable if you can just tell me what are the likely problem areas than it is for me to go grepping around xorg trying to figure out what it uses. Any ioctl that is X only can be set to require root priv. >=20 > -- > Eric Anholt et...@lc... > http://people.freebsd.org/~anholt/ anholt@FreeBSD.org >=20 --=20 Jon Smirl jon...@gm... |
From: Jon S. <jon...@gm...> - 2005-08-03 23:12:04
|
Here are the main IOCTLs that used to require root. Now they are restricted to the first process that opens the DRM device. Of couse that process may not be an Xserver. Can people add notes about possible security problems with each of these? DRM_IOCTL_IRQ_BUSID DRM_IOCTL_SET_VERSION DRM_IOCTL_SET_UNIQUE DRM_IOCTL_BLOCK DRM_IOCTL_UNBLOCK DRM_IOCTL_AUTH_MAGIC DRM_IOCTL_ADD_MAP - still does in most cases DRM_IOCTL_SET_SAREA_CTX DRM_IOCTL_ADD_CTX DRM_IOCTL_RM_CTX DRM_IOCTL_MOD_CTX DRM_IOCTL_SWITCH_CTX DRM_IOCTL_NEW_CTX DRM_IOCTL_ADD_DRAW DRM_IOCTL_RM_DRAW DRM_IOCTL_ADD_BUFS DRM_IOCTL_MARK_BUFS DRM_IOCTL_CONTROL DRM_IOCTL_AGP_ACQUIRE DRM_IOCTL_AGP_RELEASE DRM_IOCTL_AGP_ENABLE DRM_IOCTL_AGP_ALLOC DRM_IOCTL_AGP_FREE DRM_IOCTL_AGP_BIND DRM_IOCTL_AGP_UNBIND DRM_IOCTL_SG_ALLOC DRM_IOCTL_SG_FREE --=20 Jon Smirl jon...@gm... |
From: Jon S. <jon...@gm...> - 2005-08-03 21:24:11
Attachments:
drm.patch
|
New version that protects r128 and radeon IOCTLs with root capablity check. Please review this patch. We need everyone's eyes to make sure there are no accidental security holes. --=20 Jon Smirl jon...@gm... diff --git a/linux-core/drmP.h b/linux-core/drmP.h --- a/linux-core/drmP.h +++ b/linux-core/drmP.h @@ -280,7 +280,7 @@ typedef int drm_ioctl_compat_t(struct fi typedef struct drm_ioctl_desc { =09drm_ioctl_t *func; =09int auth_needed; -=09int root_only; +=09int master; } drm_ioctl_desc_t; =20 typedef struct drm_devstate { @@ -375,6 +375,7 @@ typedef struct drm_buf_entry { /** File private data */ typedef struct drm_file { =09int authenticated; +=09int master; =09int minor; =09pid_t pid; =09uid_t uid; diff --git a/linux-core/drm_bufs.c b/linux-core/drm_bufs.c --- a/linux-core/drm_bufs.c +++ b/linux-core/drm_bufs.c @@ -56,7 +56,8 @@ static drm_local_map_t *drm_find_matchin =09list_for_each(list, &dev->maplist->head) { =09=09drm_map_list_t *entry =3D list_entry(list, drm_map_list_t, head); =09=09if (entry->map && map->type =3D=3D entry->map->type && -=09=09 entry->map->offset =3D=3D map->offset) { +=09=09 ((entry->map->offset =3D=3D map->offset) || +=09=09 (map->type =3D=3D _DRM_SHM))) { =09=09=09return entry->map; =09=09} =09} @@ -163,6 +164,19 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09map->handle =3D drm_ioremap(map->offset, map->size, dev); =09=09break; =09case _DRM_SHM: +=09=09found_map =3D drm_find_matching_map(dev, map); +=09=09if (found_map !=3D NULL) { +=09=09=09if (found_map->size !=3D map->size) { +=09=09=09=09DRM_DEBUG("Matching maps of type %d with " +=09=09=09=09 "mismatched sizes, (%ld vs %ld)\n", +=09=09=09=09 map->type, map->size, found_map->size); +=09=09=09=09found_map->size =3D map->size; +=09=09=09} + +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09*map_ptr =3D found_map; +=09=09=09return 0; +=09=09} =09=09map->handle =3D vmalloc_32(map->size); =09=09DRM_DEBUG("%lu %d %p\n", =09=09=09 map->size, drm_order(map->size), map->handle); @@ -181,15 +195,34 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09dev->sigdata.lock =3D dev->lock.hw_lock =3D map->handle;=09/* Poi= nter to lock */ =09=09} =09=09break; -=09case _DRM_AGP: -=09=09if (drm_core_has_AGP(dev)) { +=09case _DRM_AGP: { +=09=09drm_agp_mem_t *entry; +=09=09int valid =3D 0; + +=09=09if (!drm_core_has_AGP(dev)) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EINVAL; +=09=09} #ifdef __alpha__ -=09=09=09map->offset +=3D dev->hose->mem_space->start; +=09=09map->offset +=3D dev->hose->mem_space->start; #endif -=09=09=09map->offset +=3D dev->agp->base; -=09=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ +=09=09map->offset +=3D dev->agp->base; +=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ + +=09=09for (entry =3D dev->agp->memory; entry; entry =3D entry->next) { +=09=09=09if ((map->offset >=3D entry->bound) && +=09=09=09 (map->offset + map->offset <=3D entry->bound + entry->pages * PAGE_SIZE)) { +=09=09=09=09valid =3D 1; +=09=09=09=09break; +=09=09=09} +=09=09} +=09=09if (!valid) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EPERM; =09=09} +=09=09DRM_DEBUG("AGP offset =3D 0x%08lx, size =3D 0x%08lx\n", map->offset,= map->size); =09=09break; +=09} =09case _DRM_SCATTER_GATHER: =09=09if (!dev->sg) { =09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); @@ -258,6 +291,9 @@ int drm_addmap_ioctl(struct inode *inode =09=09return -EFAULT; =09} =20 +=09if (!(capable(CAP_SYS_ADMIN) || map.type =3D=3D _DRM_AGP)) +=09=09return -EPERM; + =09err =3D drm_addmap( dev, map.offset, map.size, map.type, map.flags, =09=09=09 & map_ptr ); =20 diff --git a/linux-core/drm_drv.c b/linux-core/drm_drv.c --- a/linux-core/drm_drv.c +++ b/linux-core/drm_drv.c @@ -545,13 +545,14 @@ int drm_ioctl(struct inode *inode, struc =09if (!func) { =09=09DRM_DEBUG("no function\n"); =09=09retcode =3D -EINVAL; -=09} else if ((ioctl->root_only && !capable(CAP_SYS_ADMIN)) || -=09=09 (ioctl->auth_needed && !priv->authenticated)) { +=09} else if (((ioctl->master && !priv->master) || +=09=09 (ioctl->auth_needed && !priv->authenticated)) && +=09=09 (!capable(CAP_SYS_ADMIN))) { =09=09retcode =3D -EACCES; =09} else { =09=09retcode =3D func(inode, filp, cmd, arg); =09} - err_i1: +err_i1: =09atomic_dec(&dev->ioctl_count); =09if (retcode) =09=09DRM_DEBUG("ret =3D %x\n", retcode); diff --git a/linux-core/drm_fops.c b/linux-core/drm_fops.c --- a/linux-core/drm_fops.c +++ b/linux-core/drm_fops.c @@ -34,18 +34,26 @@ * OTHER DEALINGS IN THE SOFTWARE. */ =20 -#include "drmP.h" #include <linux/poll.h> =20 +#include "drmP.h" +#include "drm_sarea.h" + static int drm_open_helper(struct inode *inode, struct file *filp, drm_device_t * dev); =20 static int drm_setup(drm_device_t * dev) { +=09drm_local_map_t *map; =09int i; =20 =09if (dev->driver->presetup) =09=09dev->driver->presetup(dev); =20 +=09/* prebuild the SAREA */ +=09i =3D drm_addmap(dev, 0, SAREA_MAX, _DRM_SHM, _DRM_CONTAINS_LOCK, &map)= ; +=09if (i !=3D 0) +=09=09return i; + =09atomic_set(&dev->ioctl_count, 0); =09atomic_set(&dev->vma_count, 0); =09dev->buf_use =3D 0; @@ -72,7 +80,7 @@ static int drm_setup(drm_device_t * dev) =09INIT_LIST_HEAD(&dev->ctxlist->head); =20 =09dev->vmalist =3D NULL; -=09dev->sigdata.lock =3D dev->lock.hw_lock =3D NULL; +=09dev->sigdata.lock =3D NULL; =09init_waitqueue_head(&dev->lock.lock_queue); =09dev->queue_count =3D 0; =09dev->queue_reserved =3D 0; @@ -244,6 +252,7 @@ static int drm_open_helper(struct inode=20 =09priv->minor =3D minor; =09priv->head =3D drm_heads[minor]; =09priv->ioctl_count =3D 0; +=09/* for compatibility root is always authenticated */ =09priv->authenticated =3D capable(CAP_SYS_ADMIN); =09priv->lock_count =3D 0; =20 @@ -259,6 +268,9 @@ static int drm_open_helper(struct inode=20 =09=09priv->prev =3D NULL; =09=09dev->file_first =3D priv; =09=09dev->file_last =3D priv; +=09=09/* first opener automatically becomes master and authenticated */ +=09=09priv->master =3D 1; +=09=09priv->authenticated =3D 1; =09} else { =09=09priv->next =3D NULL; =09=09priv->prev =3D dev->file_last; diff --git a/shared-core/drm.h b/shared-core/drm.h --- a/shared-core/drm.h +++ b/shared-core/drm.h @@ -62,6 +62,12 @@ #define __user #endif =20 +#ifdef __GNUC__ +# define DEPRECATED __attribute__ ((deprecated)) +#else +# define DEPRECATED +#endif + #if defined(__linux__) #if defined(__KERNEL__) #include <linux/config.h> diff --git a/shared-core/r128_state.c b/shared-core/r128_state.c --- a/shared-core/r128_state.c +++ b/shared-core/r128_state.c @@ -1576,6 +1576,9 @@ static int r128_cce_indirect(DRM_IOCTL_A =20 =09LOCK_TEST_WITH_RETURN(dev, filp); =20 +=09if (!(capable(CAP_SYS_ADMIN))) +=09=09return DRM_ERR(EPERM); + =09if (!dev_priv) { =09=09DRM_ERROR("%s called with no initialization\n", __FUNCTION__); =09=09return DRM_ERR(EINVAL); diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c --- a/shared-core/radeon_cp.c +++ b/shared-core/radeon_cp.c @@ -1245,7 +1245,7 @@ static void radeon_set_pciegart(drm_rade =09u32 tmp =3D RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL); =09if (on) { =20 -=09=09DRM_DEBUG("programming pcie %08X %08lX %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); +=09=09DRM_DEBUG("programming pcie %08X %08X %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_DISCARD_RD_ADDR_LO, dev_priv->gart_vm_start); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_BASE, dev_priv->bus_pci_gart); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_START_LO, dev_priv->gart_vm_st= art); @@ -1398,8 +1398,6 @@ static int radeon_do_init_cp(drm_device_ =20 =09DRM_GETSAREA(); =20 -=09dev_priv->fb_offset =3D init->fb_offset; -=09dev_priv->mmio_offset =3D init->mmio_offset; =09dev_priv->ring_offset =3D init->ring_offset; =09dev_priv->ring_rptr_offset =3D init->ring_rptr_offset; =09dev_priv->buffers_offset =3D init->buffers_offset; @@ -1411,12 +1409,6 @@ static int radeon_do_init_cp(drm_device_ =09=09return DRM_ERR(EINVAL); =09} =20 -=09dev_priv->mmio =3D drm_core_findmap(dev, init->mmio_offset); -=09if (!dev_priv->mmio) { -=09=09DRM_ERROR("could not find mmio region!\n"); -=09=09radeon_do_cleanup_cp(dev); -=09=09return DRM_ERR(EINVAL); -=09} =09dev_priv->cp_ring =3D drm_core_findmap(dev, init->ring_offset); =09if (!dev_priv->cp_ring) { =09=09DRM_ERROR("could not find cp ring region!\n"); diff --git a/shared-core/radeon_drm.h b/shared-core/radeon_drm.h --- a/shared-core/radeon_drm.h +++ b/shared-core/radeon_drm.h @@ -492,7 +492,7 @@ typedef struct drm_radeon_init { =09=09RADEON_INIT_R300_CP =3D 0x04 =09} func; =09unsigned long sarea_priv_offset; -=09int is_pci;=09=09/* not used, driver asks hardware */ +=09int is_pci DEPRECATED;=09=09=09/* deprecated, driver asks hardware */ =09int cp_mode; =09int gart_size; =09int ring_size; @@ -504,8 +504,8 @@ typedef struct drm_radeon_init { =09unsigned int depth_bpp; =09unsigned int depth_offset, depth_pitch; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; +=09unsigned long fb_offset DEPRECATED;=09/* deprecated, driver asks hardwa= re */ +=09unsigned long mmio_offset DEPRECATED;=09/* deprecated, driver asks hard= ware */ =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_drv.h b/shared-core/radeon_drv.h --- a/shared-core/radeon_drv.h +++ b/shared-core/radeon_drv.h @@ -242,8 +242,6 @@ typedef struct drm_radeon_private { =20 =09drm_radeon_depth_clear_t depth_clear; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_state.c b/shared-core/radeon_state.c --- a/shared-core/radeon_state.c +++ b/shared-core/radeon_state.c @@ -2330,6 +2330,9 @@ static int radeon_cp_indirect(DRM_IOCTL_ =20 =09LOCK_TEST_WITH_RETURN(dev, filp); =20 +=09if (!(capable(CAP_SYS_ADMIN))) +=09=09return DRM_ERR(EPERM); + =09if (!dev_priv) { =09=09DRM_ERROR("%s called with no initialization\n", __FUNCTION__); =09=09return DRM_ERR(EINVAL); @@ -2917,7 +2920,7 @@ static int radeon_cp_getparam(DRM_IOCTL_ =09=09value =3D dev_priv->gart_vm_start; =09=09break; =09case RADEON_PARAM_REGISTER_HANDLE: -=09=09value =3D dev_priv->mmio_offset; +=09=09value =3D dev_priv->mmio->offset; =09=09break; =09case RADEON_PARAM_STATUS_HANDLE: =09=09value =3D dev_priv->ring_rptr_offset; |
From: Michel <mi...@da...> - 2005-08-03 19:11:26
|
On Wed, 2005-08-03 at 15:02 -0400, Jon Smirl wrote: > On 8/3/05, Eric Anholt <et...@lc...> wrote: > > On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > > > ioctls where removing the root check introduces privelege escalatio= n for > > > > users with read access to the DRM device (at least): > > > > - DRM_R128_INDIRECT > > > > - DRM_RADEON_INDIRECT > > > > > > How do we secure these? > >=20 > > By requiring root. But I didn't review all the ioctls, so these might > > not be all of the root-requiring ioctls that continue to need it. >=20 > I thought we built a command verifier to check things like this. These ioctls are designed for privileged clients like the current DDX drivers and thus unchecked. --=20 Earthling Michel D=C3=A4nzer | Debian (powerpc), X and DRI develop= er Libre software enthusiast | http://svcs.affero.net/rm.php?r=3Ddaenzer |
From: Jon S. <jon...@gm...> - 2005-08-03 21:14:14
|
On 8/3/05, Michel D=E4nzer <mi...@da...> wrote: > On Wed, 2005-08-03 at 15:02 -0400, Jon Smirl wrote: > > On 8/3/05, Eric Anholt <et...@lc...> wrote: > > > On Wed, 2005-08-03 at 14:39 -0400, Jon Smirl wrote: > > > > > ioctls where removing the root check introduces privelege escalat= ion for > > > > > users with read access to the DRM device (at least): > > > > > - DRM_R128_INDIRECT > > > > > - DRM_RADEON_INDIRECT > > > > > > > > How do we secure these? > > > > > > By requiring root. But I didn't review all the ioctls, so these migh= t > > > not be all of the root-requiring ioctls that continue to need it. > > > > I thought we built a command verifier to check things like this. >=20 > These ioctls are designed for privileged clients like the current DDX > drivers and thus unchecked. Ok, that's not inconsistent with what I am trying to do. I can just add a root capability check on those two IOCTLs. From IRC see I see that they are only used by the Xserver internally. Mesa doesn't need them. --=20 Jon Smirl jon...@gm... |
From: Dave A. <ai...@li...> - 2005-08-03 23:45:07
|
> restricted to the first process that opens the DRM device. Of couse > that process may not be an Xserver. > > Can people add notes about possible security problems with each of these? > You've missed all the driver ioctls.. please make a list of current driver ioctls that need root as well.. I'm not over-the-moon about this approach of changing the system to be default allow anything and adding root checks, I'd rather it was default root check and overrideable to allow non-root... Dave. -- David Airlie, Software Engineer http://www.skynet.ie/~airlied / airlied at skynet.ie Linux kernel - DRI, VAX / pam_smb / ILUG |
From: Jon S. <jon...@gm...> - 2005-08-04 00:45:59
|
On 8/3/05, Dave Airlie <ai...@li...> wrote: > > restricted to the first process that opens the DRM device. Of couse > > that process may not be an Xserver. > > > > Can people add notes about possible security problems with each of thes= e? > > >=20 > You've missed all the driver ioctls.. please make a list of current drive= r > ioctls that need root as well.. I was saving them until we went through the base ones first. >=20 > I'm not over-the-moon about this approach of changing the system to be > default allow anything and adding root checks, I'd rather it was default > root check and overrideable to allow non-root... I started off that way but then I figured out that very few ioctl need to require root. That would require adding about 70 root checks and then turning around and eliminating most of them immediately since mesa uses almost all of the ioctls (indirect is the only exception I know of) We can get the same effect just by inspecting the list of ioctls. >=20 > Dave. >=20 > -- > David Airlie, Software Engineer > http://www.skynet.ie/~airlied / airlied at skynet.ie > Linux kernel - DRI, VAX / pam_smb / ILUG >=20 >=20 >=20 > ------------------------------------------------------- > SF.Net email is Sponsored by the Better Software Conference & EXPO > September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practic= es > Agile & Plan-Driven Development * Managing Projects & Teams * Testing & Q= A > Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf > -- > _______________________________________________ > Dri-devel mailing list > Dri...@li... > https://lists.sourceforge.net/lists/listinfo/dri-devel >=20 --=20 Jon Smirl jon...@gm... |
From: Eric A. <et...@lc...> - 2005-08-04 04:47:25
|
On Thu, 2005-08-04 at 00:44 +0100, Dave Airlie wrote: > > restricted to the first process that opens the DRM device. Of couse > > that process may not be an Xserver. > > > > Can people add notes about possible security problems with each of these? > > > > You've missed all the driver ioctls.. please make a list of current driver > ioctls that need root as well.. > > I'm not over-the-moon about this approach of changing the system to be > default allow anything and adding root checks, I'd rather it was default > root check and overrideable to allow non-root... I'm mixed. I'm fine with having the root checks be special cases in the few ioctls that need it, when I've seen a review of every one from which the root check is being removed. The two flags in the ioctl descriptions currently are pretty unreadable, 3 would be even more confusing. Oh, and also this is as long as those root checks in the shared code get wrapped in an appropriate macro/function (taking no arguments). -- Eric Anholt et...@lc... http://people.freebsd.org/~anholt/ anholt@FreeBSD.org |
From: Ian R. <id...@us...> - 2005-08-04 00:58:06
|
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1 Jon Smirl wrote: > On 8/3/05, Dave Airlie <ai...@li...> wrote: > >>I'm not over-the-moon about this approach of changing the system to be >>default allow anything and adding root checks, I'd rather it was default >>root check and overrideable to allow non-root... > > I started off that way but then I figured out that very few ioctl need > to require root. That would require adding about 70 root checks and > then turning around and eliminating most of them immediately since > mesa uses almost all of the ioctls (indirect is the only exception I > know of) We can get the same effect just by inspecting the list of > ioctls. The difference being that you can incrementally remove root-checks without compromising the system. The same cannot be said for incrementally adding them. -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.2.6 (GNU/Linux) Comment: Using GnuPG with Fedora - http://enigmail.mozdev.org iD8DBQFC8WfyX1gOwKyEAw8RAsl8AJ9BpLonnpNTdETFS/C5zmHAxr/9gwCcD0wa mab3pazwkd13LCmYcDgFAUM= =C9NI -----END PGP SIGNATURE----- |
From: Jon S. <jon...@gm...> - 2005-08-04 01:44:16
|
On 8/3/05, Ian Romanick <id...@us...> wrote: > -----BEGIN PGP SIGNED MESSAGE----- > Hash: SHA1 >=20 > Jon Smirl wrote: > > On 8/3/05, Dave Airlie <ai...@li...> wrote: > > > >>I'm not over-the-moon about this approach of changing the system to be > >>default allow anything and adding root checks, I'd rather it was defaul= t > >>root check and overrideable to allow non-root... > > > > I started off that way but then I figured out that very few ioctl need > > to require root. That would require adding about 70 root checks and > > then turning around and eliminating most of them immediately since > > mesa uses almost all of the ioctls (indirect is the only exception I > > know of) We can get the same effect just by inspecting the list of > > ioctls. >=20 > The difference being that you can incrementally remove root-checks > without compromising the system. The same cannot be said for > incrementally adding them. Alright I will add them, but I am not convinced we will learn anything about where the vulnerabilities are. But it will have the effect of leaving the non-radeon drivers as root only until they are converted for EGL use. > -----BEGIN PGP SIGNATURE----- > Version: GnuPG v1.2.6 (GNU/Linux) > Comment: Using GnuPG with Fedora - http://enigmail.mozdev.org >=20 > iD8DBQFC8WfyX1gOwKyEAw8RAsl8AJ9BpLonnpNTdETFS/C5zmHAxr/9gwCcD0wa > mab3pazwkd13LCmYcDgFAUM=3D > =3DC9NI > -----END PGP SIGNATURE----- >=20 --=20 Jon Smirl jon...@gm... |
From: Jon S. <jon...@gm...> - 2005-08-04 02:08:38
Attachments:
drm.patch
|
New patch that makes each IOCTL individually controllable with root priv. Everything requires the same privs are the original DRM -- last two numbers on IOCTL definition are always the same. Is this ok to go in? Then we can start turing them off one by one. It still includes permanent sarea. Someone beside me should test this a little too just to make sure I didn't do anything dumb. --=20 Jon Smirl jon...@gm... diff --git a/linux-core/drmP.h b/linux-core/drmP.h --- a/linux-core/drmP.h +++ b/linux-core/drmP.h @@ -280,6 +280,7 @@ typedef int drm_ioctl_compat_t(struct fi typedef struct drm_ioctl_desc { =09drm_ioctl_t *func; =09int auth_needed; +=09int master; =09int root_only; } drm_ioctl_desc_t; =20 @@ -375,6 +376,7 @@ typedef struct drm_buf_entry { /** File private data */ typedef struct drm_file { =09int authenticated; +=09int master; =09int minor; =09pid_t pid; =09uid_t uid; diff --git a/linux-core/drm_bufs.c b/linux-core/drm_bufs.c --- a/linux-core/drm_bufs.c +++ b/linux-core/drm_bufs.c @@ -56,7 +56,8 @@ static drm_local_map_t *drm_find_matchin =09list_for_each(list, &dev->maplist->head) { =09=09drm_map_list_t *entry =3D list_entry(list, drm_map_list_t, head); =09=09if (entry->map && map->type =3D=3D entry->map->type && -=09=09 entry->map->offset =3D=3D map->offset) { +=09=09 ((entry->map->offset =3D=3D map->offset) || +=09=09 (map->type =3D=3D _DRM_SHM))) { =09=09=09return entry->map; =09=09} =09} @@ -163,6 +164,19 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09map->handle =3D drm_ioremap(map->offset, map->size, dev); =09=09break; =09case _DRM_SHM: +=09=09found_map =3D drm_find_matching_map(dev, map); +=09=09if (found_map !=3D NULL) { +=09=09=09if (found_map->size !=3D map->size) { +=09=09=09=09DRM_DEBUG("Matching maps of type %d with " +=09=09=09=09 "mismatched sizes, (%ld vs %ld)\n", +=09=09=09=09 map->type, map->size, found_map->size); +=09=09=09=09found_map->size =3D map->size; +=09=09=09} + +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09*map_ptr =3D found_map; +=09=09=09return 0; +=09=09} =09=09map->handle =3D vmalloc_32(map->size); =09=09DRM_DEBUG("%lu %d %p\n", =09=09=09 map->size, drm_order(map->size), map->handle); @@ -181,15 +195,34 @@ int drm_addmap(drm_device_t * dev, unsig =09=09=09dev->sigdata.lock =3D dev->lock.hw_lock =3D map->handle;=09/* Poi= nter to lock */ =09=09} =09=09break; -=09case _DRM_AGP: -=09=09if (drm_core_has_AGP(dev)) { +=09case _DRM_AGP: { +=09=09drm_agp_mem_t *entry; +=09=09int valid =3D 0; + +=09=09if (!drm_core_has_AGP(dev)) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EINVAL; +=09=09} #ifdef __alpha__ -=09=09=09map->offset +=3D dev->hose->mem_space->start; +=09=09map->offset +=3D dev->hose->mem_space->start; #endif -=09=09=09map->offset +=3D dev->agp->base; -=09=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ +=09=09map->offset +=3D dev->agp->base; +=09=09map->mtrr =3D dev->agp->agp_mtrr;=09/* for getmap */ + +=09=09for (entry =3D dev->agp->memory; entry; entry =3D entry->next) { +=09=09=09if ((map->offset >=3D entry->bound) && +=09=09=09 (map->offset + map->offset <=3D entry->bound + entry->pages * PAGE_SIZE)) { +=09=09=09=09valid =3D 1; +=09=09=09=09break; +=09=09=09} +=09=09} +=09=09if (!valid) { +=09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); +=09=09=09return -EPERM; =09=09} +=09=09DRM_DEBUG("AGP offset =3D 0x%08lx, size =3D 0x%08lx\n", map->offset,= map->size); =09=09break; +=09} =09case _DRM_SCATTER_GATHER: =09=09if (!dev->sg) { =09=09=09drm_free(map, sizeof(*map), DRM_MEM_MAPS); @@ -258,6 +291,9 @@ int drm_addmap_ioctl(struct inode *inode =09=09return -EFAULT; =09} =20 +=09if (!(capable(CAP_SYS_ADMIN) || map.type =3D=3D _DRM_AGP)) +=09=09return -EPERM; + =09err =3D drm_addmap( dev, map.offset, map.size, map.type, map.flags, =09=09=09 & map_ptr ); =20 diff --git a/linux-core/drm_drv.c b/linux-core/drm_drv.c --- a/linux-core/drm_drv.c +++ b/linux-core/drm_drv.c @@ -58,67 +58,67 @@ static int drm_version(struct inode *ino =20 /** Ioctl table */ drm_ioctl_desc_t drm_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_IOCTL_VERSION)] =3D {drm_version, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_UNIQUE)] =3D {drm_getunique, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_MAGIC)] =3D {drm_getmagic, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_IRQ_BUSID)] =3D {drm_irq_by_busid, 0, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_MAP)] =3D {drm_getmap, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_CLIENT)] =3D {drm_getclient, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_STATS)] =3D {drm_getstats, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_SET_VERSION)] =3D {drm_setversion, 0, 1}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_SET_UNIQUE)] =3D {drm_setunique, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_BLOCK)] =3D {drm_noop, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_UNBLOCK)] =3D {drm_noop, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AUTH_MAGIC)] =3D {drm_authmagic, 1, 1}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_MAP)] =3D {drm_addmap_ioctl, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RM_MAP)] =3D {drm_rmmap_ioctl, 1, 0}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_SET_SAREA_CTX)] =3D {drm_setsareactx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_SAREA_CTX)] =3D {drm_getsareactx, 1, 0}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] =3D {drm_addctx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] =3D {drm_rmctx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_MOD_CTX)] =3D {drm_modctx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_GET_CTX)] =3D {drm_getctx, 1, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_SWITCH_CTX)] =3D {drm_switchctx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_NEW_CTX)] =3D {drm_newctx, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RES_CTX)] =3D {drm_resctx, 1, 0}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_DRAW)] =3D {drm_adddraw, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RM_DRAW)] =3D {drm_rmdraw, 1, 1}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_LOCK)] =3D {drm_lock, 1, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_UNLOCK)] =3D {drm_unlock, 1, 0}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_FINISH)] =3D {drm_noop, 1, 0}, - -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_BUFS)] =3D {drm_addbufs, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_MARK_BUFS)] =3D {drm_markbufs, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_INFO_BUFS)] =3D {drm_infobufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_MAP_BUFS)] =3D {drm_mapbufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_FREE_BUFS)] =3D {drm_freebufs, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_VERSION)] =3D {drm_version, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_UNIQUE)] =3D {drm_getunique, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_MAGIC)] =3D {drm_getmagic, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_IRQ_BUSID)] =3D {drm_irq_by_busid, 0, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_MAP)] =3D {drm_getmap, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_CLIENT)] =3D {drm_getclient, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_STATS)] =3D {drm_getstats, 0, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_SET_VERSION)] =3D {drm_setversion, 0, 1, 1}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_SET_UNIQUE)] =3D {drm_setunique, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_BLOCK)] =3D {drm_noop, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_UNBLOCK)] =3D {drm_noop, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AUTH_MAGIC)] =3D {drm_authmagic, 1, 1, 1}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_MAP)] =3D {drm_addmap_ioctl, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RM_MAP)] =3D {drm_rmmap_ioctl, 1, 0, 0}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_SET_SAREA_CTX)] =3D {drm_setsareactx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_SAREA_CTX)] =3D {drm_getsareactx, 1, 0, 0}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] =3D {drm_addctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] =3D {drm_rmctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_MOD_CTX)] =3D {drm_modctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_GET_CTX)] =3D {drm_getctx, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_SWITCH_CTX)] =3D {drm_switchctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_NEW_CTX)] =3D {drm_newctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RES_CTX)] =3D {drm_resctx, 1, 0, 0}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_DRAW)] =3D {drm_adddraw, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RM_DRAW)] =3D {drm_rmdraw, 1, 1, 1}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_LOCK)] =3D {drm_lock, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_UNLOCK)] =3D {drm_unlock, 1, 0, 0}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_FINISH)] =3D {drm_noop, 1, 0, 0}, + +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_BUFS)] =3D {drm_addbufs, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_MARK_BUFS)] =3D {drm_markbufs, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_INFO_BUFS)] =3D {drm_infobufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_MAP_BUFS)] =3D {drm_mapbufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_FREE_BUFS)] =3D {drm_freebufs, 1, 0, 0}, =09/* The DRM_IOCTL_DMA ioctl should be defined by the driver. */ -=09[DRM_IOCTL_NR(DRM_IOCTL_DMA)] =3D {NULL, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_DMA)] =3D {NULL, 1, 0, 0}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_CONTROL)] =3D {drm_control, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_CONTROL)] =3D {drm_control, 1, 1, 1}, =20 #if __OS_HAS_AGP -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ACQUIRE)] =3D {drm_agp_acquire_ioctl, 1, 1}= , -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_RELEASE)] =3D {drm_agp_release_ioctl, 1, 1}= , -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ENABLE)] =3D {drm_agp_enable_ioctl, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_INFO)] =3D {drm_agp_info_ioctl, 1, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ALLOC)] =3D {drm_agp_alloc, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_FREE)] =3D {drm_agp_free, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_BIND)] =3D {drm_agp_bind, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_UNBIND)] =3D {drm_agp_unbind, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ACQUIRE)] =3D {drm_agp_acquire_ioctl, 1, 1,= 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_RELEASE)] =3D {drm_agp_release_ioctl, 1, 1,= 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ENABLE)] =3D {drm_agp_enable_ioctl, 1, 1, 1= }, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_INFO)] =3D {drm_agp_info_ioctl, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ALLOC)] =3D {drm_agp_alloc, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_FREE)] =3D {drm_agp_free, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_BIND)] =3D {drm_agp_bind, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_UNBIND)] =3D {drm_agp_unbind, 1, 1, 1}, #endif =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_SG_ALLOC)] =3D {drm_sg_alloc, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_SG_FREE)] =3D {drm_sg_free, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_SG_ALLOC)] =3D {drm_sg_alloc, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_SG_FREE)] =3D {drm_sg_free, 1, 1, 1}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_WAIT_VBLANK)] =3D {drm_wait_vblank, 0, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_WAIT_VBLANK)] =3D {drm_wait_vblank, 0, 0, 0}, }; =20 #define DRIVER_IOCTL_COUNT=09DRM_ARRAY_SIZE( drm_ioctls ) @@ -546,12 +546,13 @@ int drm_ioctl(struct inode *inode, struc =09=09DRM_DEBUG("no function\n"); =09=09retcode =3D -EINVAL; =09} else if ((ioctl->root_only && !capable(CAP_SYS_ADMIN)) || -=09=09 (ioctl->auth_needed && !priv->authenticated)) { +=09=09 (ioctl->auth_needed && !priv->authenticated) || +=09=09 (ioctl->master && !priv->master)) { =09=09retcode =3D -EACCES; =09} else { =09=09retcode =3D func(inode, filp, cmd, arg); =09} - err_i1: +err_i1: =09atomic_dec(&dev->ioctl_count); =09if (retcode) =09=09DRM_DEBUG("ret =3D %x\n", retcode); diff --git a/linux-core/drm_fops.c b/linux-core/drm_fops.c --- a/linux-core/drm_fops.c +++ b/linux-core/drm_fops.c @@ -34,18 +34,26 @@ * OTHER DEALINGS IN THE SOFTWARE. */ =20 -#include "drmP.h" #include <linux/poll.h> =20 +#include "drmP.h" +#include "drm_sarea.h" + static int drm_open_helper(struct inode *inode, struct file *filp, drm_device_t * dev); =20 static int drm_setup(drm_device_t * dev) { +=09drm_local_map_t *map; =09int i; =20 =09if (dev->driver->presetup) =09=09dev->driver->presetup(dev); =20 +=09/* prebuild the SAREA */ +=09i =3D drm_addmap(dev, 0, SAREA_MAX, _DRM_SHM, _DRM_CONTAINS_LOCK, &map)= ; +=09if (i !=3D 0) +=09=09return i; + =09atomic_set(&dev->ioctl_count, 0); =09atomic_set(&dev->vma_count, 0); =09dev->buf_use =3D 0; @@ -72,7 +80,7 @@ static int drm_setup(drm_device_t * dev) =09INIT_LIST_HEAD(&dev->ctxlist->head); =20 =09dev->vmalist =3D NULL; -=09dev->sigdata.lock =3D dev->lock.hw_lock =3D NULL; +=09dev->sigdata.lock =3D NULL; =09init_waitqueue_head(&dev->lock.lock_queue); =09dev->queue_count =3D 0; =09dev->queue_reserved =3D 0; @@ -244,6 +252,7 @@ static int drm_open_helper(struct inode=20 =09priv->minor =3D minor; =09priv->head =3D drm_heads[minor]; =09priv->ioctl_count =3D 0; +=09/* for compatibility root is always authenticated */ =09priv->authenticated =3D capable(CAP_SYS_ADMIN); =09priv->lock_count =3D 0; =20 @@ -259,6 +268,9 @@ static int drm_open_helper(struct inode=20 =09=09priv->prev =3D NULL; =09=09dev->file_first =3D priv; =09=09dev->file_last =3D priv; +=09=09/* first opener automatically becomes master and authenticated */ +=09=09priv->master =3D 1; +=09=09priv->authenticated =3D 1; =09} else { =09=09priv->next =3D NULL; =09=09priv->prev =3D dev->file_last; diff --git a/linux-core/i810_dma.c b/linux-core/i810_dma.c --- a/linux-core/i810_dma.c +++ b/linux-core/i810_dma.c @@ -1368,21 +1368,21 @@ int i810_driver_dma_quiescent(drm_device } =20 drm_ioctl_desc_t i810_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_I810_INIT)] =3D {i810_dma_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I810_VERTEX)] =3D {i810_dma_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_CLEAR)] =3D {i810_clear_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_FLUSH)] =3D {i810_flush_ioctl, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_GETAGE)] =3D {i810_getage, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_GETBUF)] =3D {i810_getbuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_SWAP)] =3D {i810_swap_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_COPY)] =3D {i810_copybuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_DOCOPY)] =3D {i810_docopy, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_OV0INFO)] =3D {i810_ov0_info, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_FSTATUS)] =3D {i810_fstatus, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_OV0FLIP)] =3D {i810_ov0_flip, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_MC)] =3D {i810_dma_mc, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I810_RSTATUS)] =3D {i810_rstatus, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I810_FLIP)] =3D {i810_flip_bufs, 1, 0} +=09[DRM_IOCTL_NR(DRM_I810_INIT)] =3D {i810_dma_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I810_VERTEX)] =3D {i810_dma_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_CLEAR)] =3D {i810_clear_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_FLUSH)] =3D {i810_flush_ioctl, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_GETAGE)] =3D {i810_getage, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_GETBUF)] =3D {i810_getbuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_SWAP)] =3D {i810_swap_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_COPY)] =3D {i810_copybuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_DOCOPY)] =3D {i810_docopy, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_OV0INFO)] =3D {i810_ov0_info, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_FSTATUS)] =3D {i810_fstatus, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_OV0FLIP)] =3D {i810_ov0_flip, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_MC)] =3D {i810_dma_mc, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I810_RSTATUS)] =3D {i810_rstatus, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I810_FLIP)] =3D {i810_flip_bufs, 1, 0, 0} }; =20 int i810_max_ioctl =3D DRM_ARRAY_SIZE(i810_ioctls); diff --git a/linux-core/i830_dma.c b/linux-core/i830_dma.c --- a/linux-core/i830_dma.c +++ b/linux-core/i830_dma.c @@ -1551,20 +1551,20 @@ int i830_driver_dma_quiescent(drm_device } =20 drm_ioctl_desc_t i830_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_I830_INIT)] =3D {i830_dma_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I830_VERTEX)] =3D {i830_dma_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_CLEAR)] =3D {i830_clear_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_FLUSH)] =3D {i830_flush_ioctl, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_GETAGE)] =3D {i830_getage, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_GETBUF)] =3D {i830_getbuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_SWAP)] =3D {i830_swap_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_COPY)] =3D {i830_copybuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_DOCOPY)] =3D {i830_docopy, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_FLIP)] =3D {i830_flip_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_IRQ_EMIT)] =3D {i830_irq_emit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_IRQ_WAIT)] =3D {i830_irq_wait, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_GETPARAM)] =3D {i830_getparam, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I830_SETPARAM)] =3D {i830_setparam, 1, 0} +=09[DRM_IOCTL_NR(DRM_I830_INIT)] =3D {i830_dma_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I830_VERTEX)] =3D {i830_dma_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_CLEAR)] =3D {i830_clear_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_FLUSH)] =3D {i830_flush_ioctl, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_GETAGE)] =3D {i830_getage, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_GETBUF)] =3D {i830_getbuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_SWAP)] =3D {i830_swap_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_COPY)] =3D {i830_copybuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_DOCOPY)] =3D {i830_docopy, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_FLIP)] =3D {i830_flip_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_IRQ_EMIT)] =3D {i830_irq_emit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_IRQ_WAIT)] =3D {i830_irq_wait, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_GETPARAM)] =3D {i830_getparam, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I830_SETPARAM)] =3D {i830_setparam, 1, 0, 0} }; =20 int i830_max_ioctl =3D DRM_ARRAY_SIZE(i830_ioctls); diff --git a/linux-core/savage_drv.c b/linux-core/savage_drv.c --- a/linux-core/savage_drv.c +++ b/linux-core/savage_drv.c @@ -62,10 +62,10 @@ static struct pci_device_id pciidlist[]=20 }; =20 static drm_ioctl_desc_t ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_INIT)] =3D {savage_bci_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_CMDBUF)] =3D {savage_bci_cmdbuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_EVENT_EMIT)] =3D {savage_bci_event_emit, 1= , 0}, -=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_EVENT_WAIT)] =3D {savage_bci_event_wait, 1= , 0}, +=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_INIT)] =3D {savage_bci_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_CMDBUF)] =3D {savage_bci_cmdbuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_EVENT_EMIT)] =3D {savage_bci_event_emit, 1= , 0, 0}, +=09[DRM_IOCTL_NR(DRM_SAVAGE_BCI_EVENT_WAIT)] =3D {savage_bci_event_wait, 1= , 0, 0}, }; =20 static int probe(struct pci_dev *pdev, const struct pci_device_id *ent); diff --git a/shared-core/drm.h b/shared-core/drm.h --- a/shared-core/drm.h +++ b/shared-core/drm.h @@ -62,6 +62,12 @@ #define __user #endif =20 +#ifdef __GNUC__ +# define DEPRECATED __attribute__ ((deprecated)) +#else +# define DEPRECATED +#endif + #if defined(__linux__) #if defined(__KERNEL__) #include <linux/config.h> diff --git a/shared-core/i915_dma.c b/shared-core/i915_dma.c --- a/shared-core/i915_dma.c +++ b/shared-core/i915_dma.c @@ -731,18 +731,18 @@ void i915_driver_prerelease(drm_device_t } =20 drm_ioctl_desc_t i915_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_I915_INIT)] =3D {i915_dma_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I915_FLUSH)] =3D {i915_flush_ioctl, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_FLIP)] =3D {i915_flip_bufs, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_BATCHBUFFER)] =3D {i915_batchbuffer, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_IRQ_EMIT)] =3D {i915_irq_emit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_IRQ_WAIT)] =3D {i915_irq_wait, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_GETPARAM)] =3D {i915_getparam, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_SETPARAM)] =3D {i915_setparam, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I915_ALLOC)] =3D {i915_mem_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_FREE)] =3D {i915_mem_free, 1, 0}, -=09[DRM_IOCTL_NR(DRM_I915_INIT_HEAP)] =3D {i915_mem_init_heap, 1, 1}, -=09[DRM_IOCTL_NR(DRM_I915_CMDBUFFER)] =3D {i915_cmdbuffer, 1, 0} +=09[DRM_IOCTL_NR(DRM_I915_INIT)] =3D {i915_dma_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I915_FLUSH)] =3D {i915_flush_ioctl, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_FLIP)] =3D {i915_flip_bufs, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_BATCHBUFFER)] =3D {i915_batchbuffer, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_IRQ_EMIT)] =3D {i915_irq_emit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_IRQ_WAIT)] =3D {i915_irq_wait, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_GETPARAM)] =3D {i915_getparam, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_SETPARAM)] =3D {i915_setparam, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I915_ALLOC)] =3D {i915_mem_alloc, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_FREE)] =3D {i915_mem_free, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_I915_INIT_HEAP)] =3D {i915_mem_init_heap, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_I915_CMDBUFFER)] =3D {i915_cmdbuffer, 1, 0, 0} }; =20 int i915_max_ioctl =3D DRM_ARRAY_SIZE(i915_ioctls); diff --git a/shared-core/mach64_state.c b/shared-core/mach64_state.c --- a/shared-core/mach64_state.c +++ b/shared-core/mach64_state.c @@ -40,15 +40,15 @@ * */ drm_ioctl_desc_t mach64_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_MACH64_INIT)] =3D {mach64_dma_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_MACH64_CLEAR)] =3D {mach64_dma_clear, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_SWAP)] =3D {mach64_dma_swap, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_IDLE)] =3D {mach64_dma_idle, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_RESET)] =3D {mach64_engine_reset, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_VERTEX)] =3D {mach64_dma_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_BLIT)] =3D {mach64_dma_blit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_FLUSH)] =3D {mach64_dma_flush, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MACH64_GETPARAM)] =3D {mach64_get_param, 1, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_INIT)] =3D {mach64_dma_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_MACH64_CLEAR)] =3D {mach64_dma_clear, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_SWAP)] =3D {mach64_dma_swap, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_IDLE)] =3D {mach64_dma_idle, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_RESET)] =3D {mach64_engine_reset, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_VERTEX)] =3D {mach64_dma_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_BLIT)] =3D {mach64_dma_blit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_FLUSH)] =3D {mach64_dma_flush, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MACH64_GETPARAM)] =3D {mach64_get_param, 1, 0, 0}, }; =20 int mach64_max_ioctl =3D DRM_ARRAY_SIZE(mach64_ioctls); diff --git a/shared-core/mga_state.c b/shared-core/mga_state.c --- a/shared-core/mga_state.c +++ b/shared-core/mga_state.c @@ -1164,19 +1164,19 @@ static int mga_wait_fence(DRM_IOCTL_ARGS } =20 drm_ioctl_desc_t mga_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_MGA_INIT)] =3D {mga_dma_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_MGA_FLUSH)] =3D {mga_dma_flush, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_RESET)] =3D {mga_dma_reset, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_SWAP)] =3D {mga_dma_swap, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_CLEAR)] =3D {mga_dma_clear, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_VERTEX)] =3D {mga_dma_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_INDICES)] =3D {mga_dma_indices, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_ILOAD)] =3D {mga_dma_iload, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_BLIT)] =3D {mga_dma_blit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_GETPARAM)] =3D {mga_getparam, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_SET_FENCE)] =3D {mga_set_fence, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_WAIT_FENCE)] =3D {mga_wait_fence, 1, 0}, -=09[DRM_IOCTL_NR(DRM_MGA_DMA_BOOTSTRAP)] =3D {mga_dma_bootstrap, 1, 1}, +=09[DRM_IOCTL_NR(DRM_MGA_INIT)] =3D {mga_dma_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_MGA_FLUSH)] =3D {mga_dma_flush, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_RESET)] =3D {mga_dma_reset, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_SWAP)] =3D {mga_dma_swap, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_CLEAR)] =3D {mga_dma_clear, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_VERTEX)] =3D {mga_dma_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_INDICES)] =3D {mga_dma_indices, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_ILOAD)] =3D {mga_dma_iload, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_BLIT)] =3D {mga_dma_blit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_GETPARAM)] =3D {mga_getparam, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_SET_FENCE)] =3D {mga_set_fence, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_WAIT_FENCE)] =3D {mga_wait_fence, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_MGA_DMA_BOOTSTRAP)] =3D {mga_dma_bootstrap, 1, 1, 1}, =20 }; =20 diff --git a/shared-core/r128_state.c b/shared-core/r128_state.c --- a/shared-core/r128_state.c +++ b/shared-core/r128_state.c @@ -1576,6 +1576,9 @@ static int r128_cce_indirect(DRM_IOCTL_A =20 =09LOCK_TEST_WITH_RETURN(dev, filp); =20 +=09if (!(capable(CAP_SYS_ADMIN))) +=09=09return DRM_ERR(EPERM); + =09if (!dev_priv) { =09=09DRM_ERROR("%s called with no initialization\n", __FUNCTION__); =09=09return DRM_ERR(EINVAL); @@ -1686,23 +1689,23 @@ void r128_driver_pretakedown(drm_device_ } =20 drm_ioctl_desc_t r128_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_R128_INIT)] =3D {r128_cce_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_R128_CCE_START)] =3D {r128_cce_start, 1, 1}, -=09[DRM_IOCTL_NR(DRM_R128_CCE_STOP)] =3D {r128_cce_stop, 1, 1}, -=09[DRM_IOCTL_NR(DRM_R128_CCE_RESET)] =3D {r128_cce_reset, 1, 1}, -=09[DRM_IOCTL_NR(DRM_R128_CCE_IDLE)] =3D {r128_cce_idle, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_RESET)] =3D {r128_engine_reset, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_FULLSCREEN)] =3D {r128_fullscreen, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_SWAP)] =3D {r128_cce_swap, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_FLIP)] =3D {r128_cce_flip, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_CLEAR)] =3D {r128_cce_clear, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_VERTEX)] =3D {r128_cce_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_INDICES)] =3D {r128_cce_indices, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_BLIT)] =3D {r128_cce_blit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_DEPTH)] =3D {r128_cce_depth, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_STIPPLE)] =3D {r128_cce_stipple, 1, 0}, -=09[DRM_IOCTL_NR(DRM_R128_INDIRECT)] =3D {r128_cce_indirect, 1, 1}, -=09[DRM_IOCTL_NR(DRM_R128_GETPARAM)] =3D {r128_getparam, 1, 0}, +=09[DRM_IOCTL_NR(DRM_R128_INIT)] =3D {r128_cce_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_R128_CCE_START)] =3D {r128_cce_start, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_R128_CCE_STOP)] =3D {r128_cce_stop, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_R128_CCE_RESET)] =3D {r128_cce_reset, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_R128_CCE_IDLE)] =3D {r128_cce_idle, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_RESET)] =3D {r128_engine_reset, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_FULLSCREEN)] =3D {r128_fullscreen, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_SWAP)] =3D {r128_cce_swap, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_FLIP)] =3D {r128_cce_flip, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_CLEAR)] =3D {r128_cce_clear, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_VERTEX)] =3D {r128_cce_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_INDICES)] =3D {r128_cce_indices, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_BLIT)] =3D {r128_cce_blit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_DEPTH)] =3D {r128_cce_depth, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_STIPPLE)] =3D {r128_cce_stipple, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_R128_INDIRECT)] =3D {r128_cce_indirect, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_R128_GETPARAM)] =3D {r128_getparam, 1, 0, 0}, }; =20 int r128_max_ioctl =3D DRM_ARRAY_SIZE(r128_ioctls); diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c --- a/shared-core/radeon_cp.c +++ b/shared-core/radeon_cp.c @@ -1245,7 +1245,7 @@ static void radeon_set_pciegart(drm_rade =09u32 tmp =3D RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL); =09if (on) { =20 -=09=09DRM_DEBUG("programming pcie %08X %08lX %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); +=09=09DRM_DEBUG("programming pcie %08X %08X %08X\n", dev_priv->gart_vm_start, dev_priv->bus_pci_gart,dev_priv->gart_size); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_DISCARD_RD_ADDR_LO, dev_priv->gart_vm_start); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_BASE, dev_priv->bus_pci_gart); =09=09RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_START_LO, dev_priv->gart_vm_st= art); @@ -1398,8 +1398,6 @@ static int radeon_do_init_cp(drm_device_ =20 =09DRM_GETSAREA(); =20 -=09dev_priv->fb_offset =3D init->fb_offset; -=09dev_priv->mmio_offset =3D init->mmio_offset; =09dev_priv->ring_offset =3D init->ring_offset; =09dev_priv->ring_rptr_offset =3D init->ring_rptr_offset; =09dev_priv->buffers_offset =3D init->buffers_offset; @@ -1411,12 +1409,6 @@ static int radeon_do_init_cp(drm_device_ =09=09return DRM_ERR(EINVAL); =09} =20 -=09dev_priv->mmio =3D drm_core_findmap(dev, init->mmio_offset); -=09if (!dev_priv->mmio) { -=09=09DRM_ERROR("could not find mmio region!\n"); -=09=09radeon_do_cleanup_cp(dev); -=09=09return DRM_ERR(EINVAL); -=09} =09dev_priv->cp_ring =3D drm_core_findmap(dev, init->ring_offset); =09if (!dev_priv->cp_ring) { =09=09DRM_ERROR("could not find cp ring region!\n"); diff --git a/shared-core/radeon_drm.h b/shared-core/radeon_drm.h --- a/shared-core/radeon_drm.h +++ b/shared-core/radeon_drm.h @@ -492,7 +492,7 @@ typedef struct drm_radeon_init { =09=09RADEON_INIT_R300_CP =3D 0x04 =09} func; =09unsigned long sarea_priv_offset; -=09int is_pci;=09=09/* not used, driver asks hardware */ +=09int is_pci DEPRECATED;=09=09=09/* deprecated, driver asks hardware */ =09int cp_mode; =09int gart_size; =09int ring_size; @@ -504,8 +504,8 @@ typedef struct drm_radeon_init { =09unsigned int depth_bpp; =09unsigned int depth_offset, depth_pitch; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; +=09unsigned long fb_offset DEPRECATED;=09/* deprecated, driver asks hardwa= re */ +=09unsigned long mmio_offset DEPRECATED;=09/* deprecated, driver asks hard= ware */ =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_drv.h b/shared-core/radeon_drv.h --- a/shared-core/radeon_drv.h +++ b/shared-core/radeon_drv.h @@ -242,8 +242,6 @@ typedef struct drm_radeon_private { =20 =09drm_radeon_depth_clear_t depth_clear; =20 -=09unsigned long fb_offset; -=09unsigned long mmio_offset; =09unsigned long ring_offset; =09unsigned long ring_rptr_offset; =09unsigned long buffers_offset; diff --git a/shared-core/radeon_state.c b/shared-core/radeon_state.c --- a/shared-core/radeon_state.c +++ b/shared-core/radeon_state.c @@ -2330,6 +2330,9 @@ static int radeon_cp_indirect(DRM_IOCTL_ =20 =09LOCK_TEST_WITH_RETURN(dev, filp); =20 +=09if (!(capable(CAP_SYS_ADMIN))) +=09=09return DRM_ERR(EPERM); + =09if (!dev_priv) { =09=09DRM_ERROR("%s called with no initialization\n", __FUNCTION__); =09=09return DRM_ERR(EINVAL); @@ -2917,7 +2920,7 @@ static int radeon_cp_getparam(DRM_IOCTL_ =09=09value =3D dev_priv->gart_vm_start; =09=09break; =09case RADEON_PARAM_REGISTER_HANDLE: -=09=09value =3D dev_priv->mmio_offset; +=09=09value =3D dev_priv->mmio->offset; =09=09break; =09case RADEON_PARAM_STATUS_HANDLE: =09=09value =3D dev_priv->ring_rptr_offset; @@ -3053,33 +3056,33 @@ void radeon_driver_free_filp_priv(drm_de } =20 drm_ioctl_desc_t radeon_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_RADEON_CP_INIT)] =3D {radeon_cp_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_START)] =3D {radeon_cp_start, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_STOP)] =3D {radeon_cp_stop, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_RESET)] =3D {radeon_cp_reset, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_IDLE)] =3D {radeon_cp_idle, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_RESUME)] =3D {radeon_cp_resume, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_RESET)] =3D {radeon_engine_reset, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_FULLSCREEN)] =3D {radeon_fullscreen, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_SWAP)] =3D {radeon_cp_swap, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_CLEAR)] =3D {radeon_cp_clear, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_VERTEX)] =3D {radeon_cp_vertex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_INDICES)] =3D {radeon_cp_indices, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_TEXTURE)] =3D {radeon_cp_texture, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_STIPPLE)] =3D {radeon_cp_stipple, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_INDIRECT)] =3D {radeon_cp_indirect, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_VERTEX2)] =3D {radeon_cp_vertex2, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_CMDBUF)] =3D {radeon_cp_cmdbuf, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_GETPARAM)] =3D {radeon_cp_getparam, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_FLIP)] =3D {radeon_cp_flip, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_ALLOC)] =3D {radeon_mem_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_FREE)] =3D {radeon_mem_free, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_INIT_HEAP)] =3D {radeon_mem_init_heap, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_IRQ_EMIT)] =3D {radeon_irq_emit, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_IRQ_WAIT)] =3D {radeon_irq_wait, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_SETPARAM)] =3D {radeon_cp_setparam, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_SURF_ALLOC)] =3D {radeon_surface_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_SURF_FREE)] =3D {radeon_surface_free, 1, 0} +=09[DRM_IOCTL_NR(DRM_RADEON_CP_INIT)] =3D {radeon_cp_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_START)] =3D {radeon_cp_start, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_STOP)] =3D {radeon_cp_stop, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_RESET)] =3D {radeon_cp_reset, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_IDLE)] =3D {radeon_cp_idle, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_RESUME)] =3D {radeon_cp_resume, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_RESET)] =3D {radeon_engine_reset, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_FULLSCREEN)] =3D {radeon_fullscreen, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_SWAP)] =3D {radeon_cp_swap, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_CLEAR)] =3D {radeon_cp_clear, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_VERTEX)] =3D {radeon_cp_vertex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_INDICES)] =3D {radeon_cp_indices, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_TEXTURE)] =3D {radeon_cp_texture, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_STIPPLE)] =3D {radeon_cp_stipple, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_INDIRECT)] =3D {radeon_cp_indirect, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_VERTEX2)] =3D {radeon_cp_vertex2, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_CMDBUF)] =3D {radeon_cp_cmdbuf, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_GETPARAM)] =3D {radeon_cp_getparam, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_FLIP)] =3D {radeon_cp_flip, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_ALLOC)] =3D {radeon_mem_alloc, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_FREE)] =3D {radeon_mem_free, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_INIT_HEAP)] =3D {radeon_mem_init_heap, 1, 1, 1= }, +=09[DRM_IOCTL_NR(DRM_RADEON_IRQ_EMIT)] =3D {radeon_irq_emit, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_IRQ_WAIT)] =3D {radeon_irq_wait, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_SETPARAM)] =3D {radeon_cp_setparam, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_SURF_ALLOC)] =3D {radeon_surface_alloc, 1, 0, = 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_SURF_FREE)] =3D {radeon_surface_free, 1, 0, 0} }; =20 int radeon_max_ioctl =3D DRM_ARRAY_SIZE(radeon_ioctls); diff --git a/shared-core/sis_mm.c b/shared-core/sis_mm.c --- a/shared-core/sis_mm.c +++ b/shared-core/sis_mm.c @@ -407,12 +407,12 @@ int sis_final_context(struct drm_device=20 } =20 drm_ioctl_desc_t sis_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_SIS_FB_ALLOC)] =3D {sis_fb_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_SIS_FB_FREE)] =3D {sis_fb_free, 1, 0}, -=09[DRM_IOCTL_NR(DRM_SIS_AGP_INIT)] =3D {sis_ioctl_agp_init, 1, 1}, -=09[DRM_IOCTL_NR(DRM_SIS_AGP_ALLOC)] =3D {sis_ioctl_agp_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_SIS_AGP_FREE)] =3D {sis_ioctl_agp_free, 1, 0}, -=09[DRM_IOCTL_NR(DRM_SIS_FB_INIT)] =3D {sis_fb_init, 1, 1} +=09[DRM_IOCTL_NR(DRM_SIS_FB_ALLOC)] =3D {sis_fb_alloc, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_SIS_FB_FREE)] =3D {sis_fb_free, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_SIS_AGP_INIT)] =3D {sis_ioctl_agp_init, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_SIS_AGP_ALLOC)] =3D {sis_ioctl_agp_alloc, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_SIS_AGP_FREE)] =3D {sis_ioctl_agp_free, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_SIS_FB_INIT)] =3D {sis_fb_init, 1, 1, 1} }; =20 int sis_max_ioctl =3D DRM_ARRAY_SIZE(sis_ioctls); diff --git a/shared-core/via_drv.c b/shared-core/via_drv.c --- a/shared-core/via_drv.c +++ b/shared-core/via_drv.c @@ -64,18 +64,18 @@ static struct pci_device_id pciidlist[]=20 }; =20 static drm_ioctl_desc_t ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_VIA_ALLOCMEM)] =3D {via_mem_alloc, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_FREEMEM)] =3D {via_mem_free, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_AGP_INIT)] =3D {via_agp_init, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_FB_INIT)] =3D {via_fb_init, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_MAP_INIT)] =3D {via_map_init, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_DEC_FUTEX)] =3D {via_decoder_futex, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_DMA_INIT)] =3D {via_dma_init, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_CMDBUFFER)] =3D {via_cmdbuffer, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_FLUSH)] =3D {via_flush_ioctl, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_PCICMD)] =3D {via_pci_cmdbuffer, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_CMDBUF_SIZE)] =3D {via_cmdbuf_size, 1, 0}, -=09[DRM_IOCTL_NR(DRM_VIA_WAIT_IRQ)] =3D {via_wait_irq, 1, 0} +=09[DRM_IOCTL_NR(DRM_VIA_ALLOCMEM)] =3D {via_mem_alloc, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_FREEMEM)] =3D {via_mem_free, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_AGP_INIT)] =3D {via_agp_init, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_FB_INIT)] =3D {via_fb_init, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_MAP_INIT)] =3D {via_map_init, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_DEC_FUTEX)] =3D {via_decoder_futex, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_DMA_INIT)] =3D {via_dma_init, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_CMDBUFFER)] =3D {via_cmdbuffer, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_FLUSH)] =3D {via_flush_ioctl, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_PCICMD)] =3D {via_pci_cmdbuffer, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_CMDBUF_SIZE)] =3D {via_cmdbuf_size, 1, 0, 0}, +=09[DRM_IOCTL_NR(DRM_VIA_WAIT_IRQ)] =3D {via_wait_irq, 1, 0, 0} }; =20 static int probe(struct pci_dev *pdev, const struct pci_device_id *ent); |
From: Jon S. <jon...@gm...> - 2005-08-04 03:19:53
|
Root IOCTLs used by my first test program. --=20 Jon Smirl jon...@gm... diff --git a/linux-core/drm_drv.c b/linux-core/drm_drv.c --- a/linux-core/drm_drv.c +++ b/linux-core/drm_drv.c @@ -65,36 +65,36 @@ drm_ioctl_desc_t drm_ioctls[] =3D { =09[DRM_IOCTL_NR(DRM_IOCTL_GET_MAP)] =3D {drm_getmap, 0, 0, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_GET_CLIENT)] =3D {drm_getclient, 0, 0, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_GET_STATS)] =3D {drm_getstats, 0, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_SET_VERSION)] =3D {drm_setversion, 0, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_SET_VERSION)] =3D {drm_setversion, 0, 1, 0}, =20 =09[DRM_IOCTL_NR(DRM_IOCTL_SET_UNIQUE)] =3D {drm_setunique, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_BLOCK)] =3D {drm_noop, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_UNBLOCK)] =3D {drm_noop, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_AUTH_MAGIC)] =3D {drm_authmagic, 1, 1, 1}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_MAP)] =3D {drm_addmap_ioctl, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_MAP)] =3D {drm_addmap_ioctl, 1, 1, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_RM_MAP)] =3D {drm_rmmap_ioctl, 1, 0, 0}, =20 =09[DRM_IOCTL_NR(DRM_IOCTL_SET_SAREA_CTX)] =3D {drm_setsareactx, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_GET_SAREA_CTX)] =3D {drm_getsareactx, 1, 0, 0}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] =3D {drm_addctx, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] =3D {drm_rmctx, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] =3D {drm_addctx, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] =3D {drm_rmctx, 1, 1, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_MOD_CTX)] =3D {drm_modctx, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_GET_CTX)] =3D {drm_getctx, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_SWITCH_CTX)] =3D {drm_switchctx, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_NEW_CTX)] =3D {drm_newctx, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_RES_CTX)] =3D {drm_resctx, 1, 0, 0}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_DRAW)] =3D {drm_adddraw, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_RM_DRAW)] =3D {drm_rmdraw, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_DRAW)] =3D {drm_adddraw, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_RM_DRAW)] =3D {drm_rmdraw, 1, 1, 0}, =20 =09[DRM_IOCTL_NR(DRM_IOCTL_LOCK)] =3D {drm_lock, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_UNLOCK)] =3D {drm_unlock, 1, 0, 0}, =20 =09[DRM_IOCTL_NR(DRM_IOCTL_FINISH)] =3D {drm_noop, 1, 0, 0}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_BUFS)] =3D {drm_addbufs, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_ADD_BUFS)] =3D {drm_addbufs, 1, 1, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_MARK_BUFS)] =3D {drm_markbufs, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_IOCTL_INFO_BUFS)] =3D {drm_infobufs, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_IOCTL_MAP_BUFS)] =3D {drm_mapbufs, 1, 0, 0}, @@ -102,17 +102,17 @@ drm_ioctl_desc_t drm_ioctls[] =3D { =09/* The DRM_IOCTL_DMA ioctl should be defined by the driver. */ =09[DRM_IOCTL_NR(DRM_IOCTL_DMA)] =3D {NULL, 1, 0, 0}, =20 -=09[DRM_IOCTL_NR(DRM_IOCTL_CONTROL)] =3D {drm_control, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_CONTROL)] =3D {drm_control, 1, 1, 0}, =20 #if __OS_HAS_AGP -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ACQUIRE)] =3D {drm_agp_acquire_ioctl, 1, 1,= 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_RELEASE)] =3D {drm_agp_release_ioctl, 1, 1,= 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ENABLE)] =3D {drm_agp_enable_ioctl, 1, 1, 1= }, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ACQUIRE)] =3D {drm_agp_acquire_ioctl, 1, 1,= 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_RELEASE)] =3D {drm_agp_release_ioctl, 1, 1,= 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ENABLE)] =3D {drm_agp_enable_ioctl, 1, 1, 0= }, =09[DRM_IOCTL_NR(DRM_IOCTL_AGP_INFO)] =3D {drm_agp_info_ioctl, 1, 0, 0}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ALLOC)] =3D {drm_agp_alloc, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_FREE)] =3D {drm_agp_free, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_BIND)] =3D {drm_agp_bind, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_UNBIND)] =3D {drm_agp_unbind, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_ALLOC)] =3D {drm_agp_alloc, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_FREE)] =3D {drm_agp_free, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_BIND)] =3D {drm_agp_bind, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_IOCTL_AGP_UNBIND)] =3D {drm_agp_unbind, 1, 1, 0}, #endif =20 =09[DRM_IOCTL_NR(DRM_IOCTL_SG_ALLOC)] =3D {drm_sg_alloc, 1, 1, 1}, diff --git a/shared-core/radeon_state.c b/shared-core/radeon_state.c --- a/shared-core/radeon_state.c +++ b/shared-core/radeon_state.c @@ -3056,9 +3056,9 @@ void radeon_driver_free_filp_priv(drm_de } =20 drm_ioctl_desc_t radeon_ioctls[] =3D { -=09[DRM_IOCTL_NR(DRM_RADEON_CP_INIT)] =3D {radeon_cp_init, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_START)] =3D {radeon_cp_start, 1, 1, 1}, -=09[DRM_IOCTL_NR(DRM_RADEON_CP_STOP)] =3D {radeon_cp_stop, 1, 1, 1}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_INIT)] =3D {radeon_cp_init, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_START)] =3D {radeon_cp_start, 1, 1, 0}, +=09[DRM_IOCTL_NR(DRM_RADEON_CP_STOP)] =3D {radeon_cp_stop, 1, 1, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_CP_RESET)] =3D {radeon_cp_reset, 1, 1, 1}, =09[DRM_IOCTL_NR(DRM_RADEON_CP_IDLE)] =3D {radeon_cp_idle, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_CP_RESUME)] =3D {radeon_cp_resume, 1, 0, 0}, @@ -3077,7 +3077,7 @@ drm_ioctl_desc_t radeon_ioctls[] =3D { =09[DRM_IOCTL_NR(DRM_RADEON_FLIP)] =3D {radeon_cp_flip, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_ALLOC)] =3D {radeon_mem_alloc, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_FREE)] =3D {radeon_mem_free, 1, 0, 0}, -=09[DRM_IOCTL_NR(DRM_RADEON_INIT_HEAP)] =3D {radeon_mem_init_heap, 1, 1, 1= }, +=09[DRM_IOCTL_NR(DRM_RADEON_INIT_HEAP)] =3D {radeon_mem_init_heap, 1, 1, 0= }, =09[DRM_IOCTL_NR(DRM_RADEON_IRQ_EMIT)] =3D {radeon_irq_emit, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_IRQ_WAIT)] =3D {radeon_irq_wait, 1, 0, 0}, =09[DRM_IOCTL_NR(DRM_RADEON_SETPARAM)] =3D {radeon_cp_setparam, 1, 0, 0}, |