diff options
-rw-r--r-- | libdrm/xf86drm.c | 2 | ||||
-rw-r--r-- | linux-core/drmP.h | 2 | ||||
-rw-r--r-- | linux-core/i810_dma.c | 24 | ||||
-rw-r--r-- | linux-core/i810_drm.h | 93 | ||||
-rw-r--r-- | linux-core/i810_drv.h | 1 | ||||
-rw-r--r-- | linux/Makefile.linux | 4 | ||||
-rw-r--r-- | linux/drm.h | 29 | ||||
-rw-r--r-- | linux/drmP.h | 2 | ||||
-rw-r--r-- | linux/i810_dma.c | 24 | ||||
-rw-r--r-- | linux/i810_drm.h | 93 | ||||
-rw-r--r-- | linux/i810_drm_public.h | 133 | ||||
-rw-r--r-- | linux/i810_drv.h | 1 | ||||
-rw-r--r-- | linux/mga_dma.c | 9 | ||||
-rw-r--r-- | linux/mga_drm.h (renamed from linux/mga_drm_public.h) | 132 | ||||
-rw-r--r-- | linux/mga_drv.h | 3 | ||||
-rw-r--r-- | linux/mga_state.c | 31 | ||||
-rw-r--r-- | shared-core/drm.h | 29 | ||||
-rw-r--r-- | shared/drm.h | 29 |
18 files changed, 409 insertions, 232 deletions
diff --git a/libdrm/xf86drm.c b/libdrm/xf86drm.c index 26c254af..8b97c7da 100644 --- a/libdrm/xf86drm.c +++ b/libdrm/xf86drm.c @@ -816,7 +816,7 @@ int drmAgpVersionMajor(int fd) { drm_agp_info_t i; - if (ioctl(fd, DRM_IOCTL_AGP_INFO, &i)) return 0; + if (ioctl(fd, DRM_IOCTL_AGP_INFO, &i)) return -errno; return i.agp_version_major; } diff --git a/linux-core/drmP.h b/linux-core/drmP.h index abf82e92..f8e78eab 100644 --- a/linux-core/drmP.h +++ b/linux-core/drmP.h @@ -53,7 +53,7 @@ #include <linux/agp_backend.h> #endif #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,1,0) -#include <linux/spinlock.h> +#include <linux/tqueue.h> #include <linux/poll.h> #endif #include "drm.h" diff --git a/linux-core/i810_dma.c b/linux-core/i810_dma.c index baece7a2..30fda5b8 100644 --- a/linux-core/i810_dma.c +++ b/linux-core/i810_dma.c @@ -33,7 +33,6 @@ #define __NO_VERSION__ #include "drmP.h" -#include "i810_drm_public.h" #include "i810_drv.h" #include <linux/interrupt.h> /* For task queue support */ @@ -406,7 +405,7 @@ static void i810_dma_dispatch_vertex(drm_device_t *dev, drm_i810_private_t *dev_priv = dev->dev_private; drm_i810_buf_priv_t *buf_priv = buf->dev_private; drm_i810_sarea_t *sarea_priv = dev_priv->sarea_priv; - xf86drmClipRectRec *box = sarea_priv->boxes; + drm_clip_rect_t *box = sarea_priv->boxes; int nbox = sarea_priv->nbox; unsigned long address = (unsigned long)buf->bus_address; unsigned long start = address - dev->agp->base; @@ -821,6 +820,11 @@ int i810_flush_ioctl(struct inode *inode, struct file *filp, drm_device_t *dev = priv->dev; DRM_DEBUG("i810_flush_ioctl\n"); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_flush_ioctl called without lock held\n"); + return -EINVAL; + } + i810_flush_queue(dev); return 0; } @@ -869,6 +873,11 @@ int i810_dma_general(struct inode *inode, struct file *filp, DRM_DEBUG("i810 dma general idx %d used %d\n", general.idx, general.used); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma_general called without lock held\n"); + return -EINVAL; + } + retcode = i810DmaGeneral(dev, &general); sarea_priv->last_enqueue = dev_priv->counter-1; sarea_priv->last_dispatch = (int) hw_status[5]; @@ -890,7 +899,11 @@ int i810_dma_vertex(struct inode *inode, struct file *filp, copy_from_user_ret(&vertex, (drm_i810_vertex_t *)arg, sizeof(vertex), -EFAULT); - + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma_vertex called without lock held\n"); + return -EINVAL; + } + DRM_DEBUG("i810 dma vertex, idx %d used %d discard %d\n", vertex.idx, vertex.used, vertex.discard); @@ -933,6 +946,11 @@ int i810_dma(struct inode *inode, struct file *filp, unsigned int cmd, copy_from_user_ret(&d, (drm_dma_t *)arg, sizeof(d), -EFAULT); DRM_DEBUG("%d %d: %d send, %d req\n", current->pid, d.context, d.send_count, d.request_count); + + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma called without lock held\n"); + return -EINVAL; + } /* Please don't send us buffers. */ diff --git a/linux-core/i810_drm.h b/linux-core/i810_drm.h new file mode 100644 index 00000000..0754874c --- /dev/null +++ b/linux-core/i810_drm.h @@ -0,0 +1,93 @@ +#ifndef _I810_DRM_H_ +#define _I810_DRM_H_ + +/* WARNING: These defines must be the same as what the Xserver uses. + * if you change them, you must change the defines in the Xserver. + */ + +/* Might one day want to support the client-side ringbuffer code again. + */ +#ifndef _I810_DEFINES_ +#define _I810_DEFINES_ + +#define I810_USE_BATCH 1 +#define I810_DMA_BUF_ORDER 12 +#define I810_DMA_BUF_SZ (1<<I810_DMA_BUF_ORDER) +#define I810_DMA_BUF_NR 256 +#define I810_NR_SAREA_CLIPRECTS 2 + +/* Each region is a minimum of 64k, and there are at most 64 of them. + */ + +#define I810_NR_TEX_REGIONS 64 +#define I810_LOG_MIN_TEX_REGION_SIZE 16 +#endif + +typedef struct _drm_i810_init { + enum { + I810_INIT_DMA = 0x01, + I810_CLEANUP_DMA = 0x02 + } func; + int ring_map_idx; + int buffer_map_idx; + int sarea_priv_offset; + unsigned long ring_start; + unsigned long ring_end; + unsigned long ring_size; +} drm_i810_init_t; + +/* Warning: If you change the SAREA structure you must change the Xserver + * structure as well */ + +typedef struct _drm_i810_tex_region { + unsigned char next, prev; /* indices to form a circular LRU */ + unsigned char in_use; /* owned by a client, or free? */ + int age; /* tracked by clients to update local LRU's */ +} drm_i810_tex_region_t; + +typedef struct _drm_i810_sarea { + unsigned int nbox; + drm_clip_rect_t boxes[I810_NR_SAREA_CLIPRECTS]; + + /* Maintain an LRU of contiguous regions of texture space. If + * you think you own a region of texture memory, and it has an + * age different to the one you set, then you are mistaken and + * it has been stolen by another client. If global texAge + * hasn't changed, there is no need to walk the list. + * + * These regions can be used as a proxy for the fine-grained + * texture information of other clients - by maintaining them + * in the same lru which is used to age their own textures, + * clients have an approximate lru for the whole of global + * texture space, and can make informed decisions as to which + * areas to kick out. There is no need to choose whether to + * kick out your own texture or someone else's - simply eject + * them all in LRU order. + */ + + drm_i810_tex_region_t texList[I810_NR_TEX_REGIONS+1]; + /* Last elt is sentinal */ + int texAge; /* last time texture was uploaded */ + int last_enqueue; /* last time a buffer was enqueued */ + int last_dispatch; /* age of the most recently dispatched buffer */ + int last_quiescent; /* */ + int ctxOwner; /* last context to upload state */ +} drm_i810_sarea_t; + +typedef struct _drm_i810_general { + int idx; + int used; +} drm_i810_general_t; + +/* These may be placeholders if we have more cliprects than + * I810_NR_SAREA_CLIPRECTS. In that case, the client sets discard to + * false, indicating that the buffer will be dispatched again with a + * new set of cliprects. + */ +typedef struct _drm_i810_vertex { + int idx; /* buffer index */ + int used; /* nr bytes in use */ + int discard; /* client is finished with the buffer? */ +} drm_i810_vertex_t; + +#endif /* _I810_DRM_H_ */ diff --git a/linux-core/i810_drv.h b/linux-core/i810_drv.h index 60c81c8b..1badd36b 100644 --- a/linux-core/i810_drv.h +++ b/linux-core/i810_drv.h @@ -31,7 +31,6 @@ #ifndef _I810_DRV_H_ #define _I810_DRV_H_ -#include "i810_drm_public.h" typedef struct _drm_i810_ring_buffer{ int tail_mask; diff --git a/linux/Makefile.linux b/linux/Makefile.linux index 20cfd5cc..1db7a81f 100644 --- a/linux/Makefile.linux +++ b/linux/Makefile.linux @@ -119,10 +119,10 @@ DRMOBJS += agpsupport.o MODS += mga.o i810.o MGAOBJS= mga_drv.o mga_dma.o mga_bufs.o mga_state.o mga_context.o -MGAHEADERS= mga_drv.h mga_drm_public.h $(DRMHEADERS) +MGAHEADERS= mga_drv.h $(DRMHEADERS) I810OBJS= i810_drv.o i810_dma.o i810_bufs.o i810_context.o -I810HEADERS= i810_drv.h i810_drm_public.h $(DRMHEADERS) +I810HEADERS= i810_drv.h $(DRMHEADERS) endif all::;@echo KERNEL HEADERS IN $(TREE): SMP=${SMP} MODVERSIONS=${MODVERSIONS} \ diff --git a/linux/drm.h b/linux/drm.h index ebc6f7e7..ae4c65ca 100644 --- a/linux/drm.h +++ b/linux/drm.h @@ -61,6 +61,19 @@ typedef unsigned int drm_context_t; typedef unsigned int drm_drawable_t; typedef unsigned int drm_magic_t; +/* Warning: If you change this structure, make sure you change + * XF86DRIClipRectRec in the server as well */ + +typedef struct drm_clip_rect { + unsigned short x1; + unsigned short y1; + unsigned short x2; + unsigned short y2; +} drm_clip_rect_t; + +/* Seperate include files for the i810/mga specific structures */ +#include "mga_drm.h" +#include "i810_drm.h" typedef struct drm_version { int version_major; /* Major version */ @@ -321,5 +334,19 @@ typedef struct drm_agp_info { #define DRM_IOCTL_AGP_BIND DRM_IOWR(0x36, drm_agp_binding_t) #define DRM_IOCTL_AGP_UNBIND DRM_IOW( 0x37, drm_agp_binding_t) -/* 0x40 is reserved for mga dma init */ +/* Mga specific ioctls */ +#define DRM_IOCTL_MGA_INIT DRM_IOW( 0x40, drm_mga_init_t) +#define DRM_IOCTL_MGA_SWAP DRM_IOW( 0x41, drm_mga_swap_t) +#define DRM_IOCTL_MGA_CLEAR DRM_IOW( 0x42, drm_mga_clear_t) +#define DRM_IOCTL_MGA_ILOAD DRM_IOW( 0x43, drm_mga_iload_t) +#define DRM_IOCTL_MGA_VERTEX DRM_IOW( 0x44, drm_mga_vertex_t) +#define DRM_IOCTL_MGA_FLUSH DRM_IOW( 0x45, drm_lock_t ) + +/* I810 specific ioctls */ +#define DRM_IOCTL_I810_INIT DRM_IOW( 0x40, drm_i810_init_t) +#define DRM_IOCTL_I810_VERTEX DRM_IOW( 0x41, drm_i810_vertex_t) +#define DRM_IOCTL_I810_DMA DRM_IOW( 0x42, drm_i810_general_t) +#define DRM_IOCTL_I810_FLUSH DRM_IO ( 0x43) +#define DRM_IOCTL_I810_GETAGE DRM_IO ( 0x44) + #endif diff --git a/linux/drmP.h b/linux/drmP.h index abf82e92..f8e78eab 100644 --- a/linux/drmP.h +++ b/linux/drmP.h @@ -53,7 +53,7 @@ #include <linux/agp_backend.h> #endif #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,1,0) -#include <linux/spinlock.h> +#include <linux/tqueue.h> #include <linux/poll.h> #endif #include "drm.h" diff --git a/linux/i810_dma.c b/linux/i810_dma.c index baece7a2..30fda5b8 100644 --- a/linux/i810_dma.c +++ b/linux/i810_dma.c @@ -33,7 +33,6 @@ #define __NO_VERSION__ #include "drmP.h" -#include "i810_drm_public.h" #include "i810_drv.h" #include <linux/interrupt.h> /* For task queue support */ @@ -406,7 +405,7 @@ static void i810_dma_dispatch_vertex(drm_device_t *dev, drm_i810_private_t *dev_priv = dev->dev_private; drm_i810_buf_priv_t *buf_priv = buf->dev_private; drm_i810_sarea_t *sarea_priv = dev_priv->sarea_priv; - xf86drmClipRectRec *box = sarea_priv->boxes; + drm_clip_rect_t *box = sarea_priv->boxes; int nbox = sarea_priv->nbox; unsigned long address = (unsigned long)buf->bus_address; unsigned long start = address - dev->agp->base; @@ -821,6 +820,11 @@ int i810_flush_ioctl(struct inode *inode, struct file *filp, drm_device_t *dev = priv->dev; DRM_DEBUG("i810_flush_ioctl\n"); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_flush_ioctl called without lock held\n"); + return -EINVAL; + } + i810_flush_queue(dev); return 0; } @@ -869,6 +873,11 @@ int i810_dma_general(struct inode *inode, struct file *filp, DRM_DEBUG("i810 dma general idx %d used %d\n", general.idx, general.used); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma_general called without lock held\n"); + return -EINVAL; + } + retcode = i810DmaGeneral(dev, &general); sarea_priv->last_enqueue = dev_priv->counter-1; sarea_priv->last_dispatch = (int) hw_status[5]; @@ -890,7 +899,11 @@ int i810_dma_vertex(struct inode *inode, struct file *filp, copy_from_user_ret(&vertex, (drm_i810_vertex_t *)arg, sizeof(vertex), -EFAULT); - + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma_vertex called without lock held\n"); + return -EINVAL; + } + DRM_DEBUG("i810 dma vertex, idx %d used %d discard %d\n", vertex.idx, vertex.used, vertex.discard); @@ -933,6 +946,11 @@ int i810_dma(struct inode *inode, struct file *filp, unsigned int cmd, copy_from_user_ret(&d, (drm_dma_t *)arg, sizeof(d), -EFAULT); DRM_DEBUG("%d %d: %d send, %d req\n", current->pid, d.context, d.send_count, d.request_count); + + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("i810_dma called without lock held\n"); + return -EINVAL; + } /* Please don't send us buffers. */ diff --git a/linux/i810_drm.h b/linux/i810_drm.h new file mode 100644 index 00000000..0754874c --- /dev/null +++ b/linux/i810_drm.h @@ -0,0 +1,93 @@ +#ifndef _I810_DRM_H_ +#define _I810_DRM_H_ + +/* WARNING: These defines must be the same as what the Xserver uses. + * if you change them, you must change the defines in the Xserver. + */ + +/* Might one day want to support the client-side ringbuffer code again. + */ +#ifndef _I810_DEFINES_ +#define _I810_DEFINES_ + +#define I810_USE_BATCH 1 +#define I810_DMA_BUF_ORDER 12 +#define I810_DMA_BUF_SZ (1<<I810_DMA_BUF_ORDER) +#define I810_DMA_BUF_NR 256 +#define I810_NR_SAREA_CLIPRECTS 2 + +/* Each region is a minimum of 64k, and there are at most 64 of them. + */ + +#define I810_NR_TEX_REGIONS 64 +#define I810_LOG_MIN_TEX_REGION_SIZE 16 +#endif + +typedef struct _drm_i810_init { + enum { + I810_INIT_DMA = 0x01, + I810_CLEANUP_DMA = 0x02 + } func; + int ring_map_idx; + int buffer_map_idx; + int sarea_priv_offset; + unsigned long ring_start; + unsigned long ring_end; + unsigned long ring_size; +} drm_i810_init_t; + +/* Warning: If you change the SAREA structure you must change the Xserver + * structure as well */ + +typedef struct _drm_i810_tex_region { + unsigned char next, prev; /* indices to form a circular LRU */ + unsigned char in_use; /* owned by a client, or free? */ + int age; /* tracked by clients to update local LRU's */ +} drm_i810_tex_region_t; + +typedef struct _drm_i810_sarea { + unsigned int nbox; + drm_clip_rect_t boxes[I810_NR_SAREA_CLIPRECTS]; + + /* Maintain an LRU of contiguous regions of texture space. If + * you think you own a region of texture memory, and it has an + * age different to the one you set, then you are mistaken and + * it has been stolen by another client. If global texAge + * hasn't changed, there is no need to walk the list. + * + * These regions can be used as a proxy for the fine-grained + * texture information of other clients - by maintaining them + * in the same lru which is used to age their own textures, + * clients have an approximate lru for the whole of global + * texture space, and can make informed decisions as to which + * areas to kick out. There is no need to choose whether to + * kick out your own texture or someone else's - simply eject + * them all in LRU order. + */ + + drm_i810_tex_region_t texList[I810_NR_TEX_REGIONS+1]; + /* Last elt is sentinal */ + int texAge; /* last time texture was uploaded */ + int last_enqueue; /* last time a buffer was enqueued */ + int last_dispatch; /* age of the most recently dispatched buffer */ + int last_quiescent; /* */ + int ctxOwner; /* last context to upload state */ +} drm_i810_sarea_t; + +typedef struct _drm_i810_general { + int idx; + int used; +} drm_i810_general_t; + +/* These may be placeholders if we have more cliprects than + * I810_NR_SAREA_CLIPRECTS. In that case, the client sets discard to + * false, indicating that the buffer will be dispatched again with a + * new set of cliprects. + */ +typedef struct _drm_i810_vertex { + int idx; /* buffer index */ + int used; /* nr bytes in use */ + int discard; /* client is finished with the buffer? */ +} drm_i810_vertex_t; + +#endif /* _I810_DRM_H_ */ diff --git a/linux/i810_drm_public.h b/linux/i810_drm_public.h deleted file mode 100644 index fb7814fb..00000000 --- a/linux/i810_drm_public.h +++ /dev/null @@ -1,133 +0,0 @@ -/* i810_drm_public.h -- Public header for the i810 driver -*- linux-c -*- - * Created: Mon Dec 13 01:50:01 1999 by jhartmann@precisioninsight.com - * - * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas. - * All rights reserved. - * - * Permission is hereby granted, free of charge, to any person obtaining a - * copy of this software and associated documentation files (the "Software"), - * to deal in the Software without restriction, including without limitation - * the rights to use, copy, modify, merge, publish, distribute, sublicense, - * and/or sell copies of the Software, and to permit persons to whom the - * Software is furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice (including the next - * paragraph) shall be included in all copies or substantial portions of the - * Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL - * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR - * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, - * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER - * DEALINGS IN THE SOFTWARE. - * - * Authors: Jeff Hartmann <jhartmann@precisioninsight.com> - * Keith Whitwell <keithw@precisioninsight.com> - * - * $XFree86$ - */ - -#ifndef _I810_DRM_H_ -#define _I810_DRM_H_ - -typedef struct drm_i810_init { - enum { - I810_INIT_DMA = 0x01, - I810_CLEANUP_DMA = 0x02 - } func; - int ring_map_idx; - int buffer_map_idx; - int sarea_priv_offset; - unsigned long ring_start; - unsigned long ring_end; - unsigned long ring_size; - -} drm_i810_init_t; - -typedef struct _xf86drmClipRectRec { - unsigned short x1; - unsigned short y1; - unsigned short x2; - unsigned short y2; -} xf86drmClipRectRec; - -/* Might one day want to support the client-side ringbuffer code again. - */ - -#define I810_USE_BATCH 1 - -#define I810_DMA_BUF_ORDER 12 -#define I810_DMA_BUF_SZ (1<<I810_DMA_BUF_ORDER) -#define I810_DMA_BUF_NR 256 - -#define I810_NR_SAREA_CLIPRECTS 2 - -/* Each region is a minimum of 64k, and there are at most 64 of them. - */ -#define I810_NR_TEX_REGIONS 64 -#define I810_LOG_MIN_TEX_REGION_SIZE 16 - -typedef struct { - unsigned char next, prev; /* indices to form a circular LRU */ - unsigned char in_use; /* owned by a client, or free? */ - int age; /* tracked by clients to update local LRU's */ -} i810TexRegion; - -typedef struct { - unsigned int nbox; - xf86drmClipRectRec boxes[I810_NR_SAREA_CLIPRECTS]; - - /* Maintain an LRU of contiguous regions of texture space. If - * you think you own a region of texture memory, and it has an - * age different to the one you set, then you are mistaken and - * it has been stolen by another client. If global texAge - * hasn't changed, there is no need to walk the list. - * - * These regions can be used as a proxy for the fine-grained - * texture information of other clients - by maintaining them - * in the same lru which is used to age their own textures, - * clients have an approximate lru for the whole of global - * texture space, and can make informed decisions as to which - * areas to kick out. There is no need to choose whether to - * kick out your own texture or someone else's - simply eject - * them all in LRU order. - */ - i810TexRegion texList[I810_NR_TEX_REGIONS+1]; /* Last elt is sentinal */ - - int texAge; /* last time texture was uploaded */ - - int last_enqueue; /* last time a buffer was enqueued */ - int last_dispatch; /* age of the most recently dispatched buffer */ - int last_quiescent; /* */ - - int ctxOwner; /* last context to upload state */ -} drm_i810_sarea_t; - - -typedef struct { - int idx; - int used; -} drm_i810_general_t; - - -/* These may be placeholders if we have more cliprects than - * I810_NR_SAREA_CLIPRECTS. In that case, the client sets discard to - * false, indicating that the buffer will be dispatched again with a - * new set of cliprects. - */ -typedef struct { - int idx; /* buffer index */ - int used; /* nr bytes in use */ - int discard; /* client is finished with the buffer? */ -} drm_i810_vertex_t; - - - -#define DRM_IOCTL_I810_INIT DRM_IOW( 0x40, drm_i810_init_t) -#define DRM_IOCTL_I810_VERTEX DRM_IOW( 0x41, drm_i810_vertex_t) -#define DRM_IOCTL_I810_DMA DRM_IOW( 0x42, drm_i810_general_t) -#define DRM_IOCTL_I810_FLUSH DRM_IO ( 0x43) -#define DRM_IOCTL_I810_GETAGE DRM_IO ( 0x44) -#endif /* _I810_DRM_H_ */ diff --git a/linux/i810_drv.h b/linux/i810_drv.h index 60c81c8b..1badd36b 100644 --- a/linux/i810_drv.h +++ b/linux/i810_drv.h @@ -31,7 +31,6 @@ #ifndef _I810_DRV_H_ #define _I810_DRV_H_ -#include "i810_drm_public.h" typedef struct _drm_i810_ring_buffer{ int tail_mask; diff --git a/linux/mga_dma.c b/linux/mga_dma.c index e08973f8..59cbad6b 100644 --- a/linux/mga_dma.c +++ b/linux/mga_dma.c @@ -787,7 +787,7 @@ static int mga_dma_initialize(drm_device_t *dev, drm_mga_init_t *init) { dev_priv->mAccess); memcpy(&dev_priv->WarpIndex, &init->WarpIndex, - sizeof(mgaWarpIndex) * MGA_MAX_WARP_PIPES); + sizeof(drm_mga_warp_index_t) * MGA_MAX_WARP_PIPES); for (i = 0 ; i < MGA_MAX_WARP_PIPES ; i++) DRM_DEBUG("warp pipe %d: installed: %d phys: %lx size: %x\n", @@ -1116,7 +1116,12 @@ int mga_flush_ioctl(struct inode *inode, struct file *filp, int i; copy_from_user_ret(&lock, (drm_lock_t *)arg, sizeof(lock), -EFAULT); - + + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_flush_ioctl called without lock held\n"); + return -EINVAL; + } + if(lock.flags & _DRM_LOCK_FLUSH || lock.flags & _DRM_LOCK_FLUSH_ALL) { mga_flush_queue(dev); diff --git a/linux/mga_drm_public.h b/linux/mga_drm.h index 29b06a11..12a858e7 100644 --- a/linux/mga_drm_public.h +++ b/linux/mga_drm.h @@ -1,4 +1,4 @@ -/* mga_drm_public.h -- Public header for the Matrox g200/g400 driver -*- linux-c -*- +/* mga_drm.h -- Public header for the Matrox g200/g400 driver -*- linux-c -*- * Created: Tue Jan 25 01:50:01 1999 by jhartmann@precisioninsight.com * * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas. @@ -29,9 +29,14 @@ * $XFree86$ */ -#ifndef _MGA_DRM_PUBLIC_H_ -#define _MGA_DRM_PUBLIC_H_ +#ifndef _MGA_DRM_H_ +#define _MGA_DRM_H_ +/* WARNING: If you change any of these defines, make sure to change the + * defines in the Xserver file (xf86drmMga.h) + */ +#ifndef _MGA_DEFINES_ +#define _MGA_DEFINES_ #define MGA_F 0x1 /* fog */ #define MGA_A 0x2 /* alpha */ #define MGA_S 0x4 /* specular */ @@ -61,52 +66,10 @@ #define MGA_CARD_TYPE_G200 1 #define MGA_CARD_TYPE_G400 2 - - -typedef struct _drm_mga_warp_index { - int installed; - unsigned long phys_addr; - int size; -} mgaWarpIndex; - -typedef struct drm_mga_init { - enum { - MGA_INIT_DMA = 0x01, - MGA_CLEANUP_DMA = 0x02 - } func; - int reserved_map_agpstart; - int reserved_map_idx; - int buffer_map_idx; - int sarea_priv_offset; - int primary_size; - int warp_ucode_size; - int frontOffset; - int backOffset; - int depthOffset; - int textureOffset; - int textureSize; - int agpTextureOffset; - int agpTextureSize; - int cpp; - int stride; - int sgram; - int chipset; - mgaWarpIndex WarpIndex[MGA_MAX_WARP_PIPES]; - int mAccess; -} drm_mga_init_t; - -typedef struct _xf86drmClipRectRec { - unsigned short x1; - unsigned short y1; - unsigned short x2; - unsigned short y2; -} xf86drmClipRectRec; - #define MGA_FRONT 0x1 #define MGA_BACK 0x2 #define MGA_DEPTH 0x4 - /* 3d state excluding texture units: */ #define MGA_CTXREG_DSTORG 0 /* validated */ @@ -155,42 +118,72 @@ typedef struct _xf86drmClipRectRec { #define MGA_DMA_FLUSH 0x200 /* set when someone gets the lock quiescent */ - /* 64 buffers of 16k each, total 1 meg. */ #define MGA_DMA_BUF_ORDER 14 #define MGA_DMA_BUF_SZ (1<<MGA_DMA_BUF_ORDER) #define MGA_DMA_BUF_NR 63 - /* Keep these small for testing. */ #define MGA_NR_SAREA_CLIPRECTS 8 - - /* 2 heaps (1 for card, 1 for agp), each divided into upto 128 * regions, subject to a minimum region size of (1<<16) == 64k. * * Clients may subdivide regions internally, but when sharing between * clients, the region size is the minimum granularity. */ + #define MGA_CARD_HEAP 0 #define MGA_AGP_HEAP 1 #define MGA_NR_TEX_HEAPS 2 #define MGA_NR_TEX_REGIONS 16 #define MGA_LOG_MIN_TEX_REGION_SIZE 16 +#endif + +typedef struct _drm_mga_warp_index { + int installed; + unsigned long phys_addr; + int size; +} drm_mga_warp_index_t; -typedef struct { +typedef struct drm_mga_init { + enum { + MGA_INIT_DMA = 0x01, + MGA_CLEANUP_DMA = 0x02 + } func; + int reserved_map_agpstart; + int reserved_map_idx; + int buffer_map_idx; + int sarea_priv_offset; + int primary_size; + int warp_ucode_size; + int frontOffset; + int backOffset; + int depthOffset; + int textureOffset; + int textureSize; + int agpTextureOffset; + int agpTextureSize; + int cpp; + int stride; + int sgram; + int chipset; + drm_mga_warp_index_t WarpIndex[MGA_MAX_WARP_PIPES]; + int mAccess; +} drm_mga_init_t; + +/* Warning: if you change the sarea structure, you must change the Xserver + * structures as well */ + +typedef struct _drm_mga_tex_region { unsigned char next, prev; unsigned char in_use; int age; -} mgaTexRegion; - +} drm_mga_tex_region_t; - -typedef struct -{ +typedef struct _drm_mga_sarea { /* The channel for communication of state information to the kernel * on firing a vertex dma buffer. */ @@ -201,7 +194,7 @@ typedef struct unsigned int dirty; unsigned int nbox; - xf86drmClipRectRec boxes[MGA_NR_SAREA_CLIPRECTS]; + drm_clip_rect_t boxes[MGA_NR_SAREA_CLIPRECTS]; /* Information about the most recently used 3d drawable. The @@ -222,7 +215,7 @@ typedef struct unsigned int exported_nback; int exported_back_x, exported_front_x, exported_w; int exported_back_y, exported_front_y, exported_h; - xf86drmClipRectRec exported_boxes[MGA_NR_SAREA_CLIPRECTS]; + drm_clip_rect_t exported_boxes[MGA_NR_SAREA_CLIPRECTS]; /* Counters for aging textures and for client-side throttling. */ @@ -233,47 +226,36 @@ typedef struct /* LRU lists for texture memory in agp space and on the card */ - mgaTexRegion texList[MGA_NR_TEX_HEAPS][MGA_NR_TEX_REGIONS+1]; - unsigned int texAge[MGA_NR_TEX_HEAPS]; + drm_mga_tex_region_t texList[MGA_NR_TEX_HEAPS][MGA_NR_TEX_REGIONS+1]; + unsigned int texAge[MGA_NR_TEX_HEAPS]; /* Mechanism to validate card state. */ - int ctxOwner; - - + int ctxOwner; } drm_mga_sarea_t; - /* Device specific ioctls: */ -typedef struct { +typedef struct _drm_mga_clear { int clear_color; int clear_depth; int flags; } drm_mga_clear_t; -typedef struct { +typedef struct _drm_mga_swap { int dummy; } drm_mga_swap_t; -typedef struct { +typedef struct _drm_mga_iload { int idx; int length; unsigned int destOrg; } drm_mga_iload_t; -typedef struct { +typedef struct _drm_mga_vertex { int idx; /* buffer to queue */ int used; /* bytes in use */ int discard; /* client finished with buffer? */ } drm_mga_vertex_t; - -#define DRM_IOCTL_MGA_INIT DRM_IOW( 0x40, drm_mga_init_t) -#define DRM_IOCTL_MGA_SWAP DRM_IOW( 0x41, drm_mga_swap_t) -#define DRM_IOCTL_MGA_CLEAR DRM_IOW( 0x42, drm_mga_clear_t) -#define DRM_IOCTL_MGA_ILOAD DRM_IOW( 0x43, drm_mga_iload_t) -#define DRM_IOCTL_MGA_VERTEX DRM_IOW( 0x44, drm_mga_vertex_t) -#define DRM_IOCTL_MGA_FLUSH DRM_IOW( 0x45, drm_lock_t ) - #endif diff --git a/linux/mga_drv.h b/linux/mga_drv.h index e32a0c87..43deb613 100644 --- a/linux/mga_drv.h +++ b/linux/mga_drv.h @@ -31,7 +31,6 @@ #ifndef _MGA_DRV_H_ #define _MGA_DRV_H_ -#include "mga_drm_public.h" typedef struct { unsigned int num_dwords; @@ -70,7 +69,7 @@ typedef struct _drm_mga_private { int stride; int sgram; int use_agp; - mgaWarpIndex WarpIndex[MGA_MAX_G400_PIPES]; + drm_mga_warp_index_t WarpIndex[MGA_MAX_G400_PIPES]; unsigned int WarpPipe; __volatile__ unsigned long softrap_age; u32 dispatch_lock; diff --git a/linux/mga_state.c b/linux/mga_state.c index f8cd3fd9..a70f86d2 100644 --- a/linux/mga_state.c +++ b/linux/mga_state.c @@ -36,7 +36,7 @@ #include "drm.h" static void mgaEmitClipRect( drm_mga_private_t *dev_priv, - xf86drmClipRectRec *box ) + drm_clip_rect_t *box ) { drm_mga_sarea_t *sarea_priv = dev_priv->sarea_priv; unsigned int *regs = sarea_priv->ContextState; @@ -546,7 +546,7 @@ static void mga_dma_dispatch_clear( drm_device_t *dev, int flags, drm_mga_sarea_t *sarea_priv = dev_priv->sarea_priv; unsigned int *regs = sarea_priv->ContextState; int nbox = sarea_priv->nbox; - xf86drmClipRectRec *pbox = sarea_priv->boxes; + drm_clip_rect_t *pbox = sarea_priv->boxes; unsigned int cmd; int i; int primary_needed; @@ -629,7 +629,7 @@ static void mga_dma_dispatch_swap( drm_device_t *dev ) drm_mga_sarea_t *sarea_priv = dev_priv->sarea_priv; unsigned int *regs = sarea_priv->ContextState; int nbox = sarea_priv->nbox; - xf86drmClipRectRec *pbox = sarea_priv->boxes; + drm_clip_rect_t *pbox = sarea_priv->boxes; int i; int primary_needed; PRIMLOCALS; @@ -687,11 +687,15 @@ int mga_clear_bufs(struct inode *inode, struct file *filp, drm_mga_sarea_t *sarea_priv = dev_priv->sarea_priv; __volatile__ unsigned int *status = (__volatile__ unsigned int *)dev_priv->status_page; - drm_mga_clear_t clear; copy_from_user_ret(&clear, (drm_mga_clear_t *)arg, sizeof(clear), -EFAULT); + + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_clear_bufs called without lock held\n"); + return -EINVAL; + } if (sarea_priv->nbox > MGA_NR_SAREA_CLIPRECTS) sarea_priv->nbox = MGA_NR_SAREA_CLIPRECTS; @@ -718,6 +722,11 @@ int mga_swap_bufs(struct inode *inode, struct file *filp, __volatile__ unsigned int *status = (__volatile__ unsigned int *)dev_priv->status_page; + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_swap_bufs called without lock held\n"); + return -EINVAL; + } + if (sarea_priv->nbox > MGA_NR_SAREA_CLIPRECTS) sarea_priv->nbox = MGA_NR_SAREA_CLIPRECTS; @@ -752,6 +761,11 @@ int mga_iload(struct inode *inode, struct file *filp, copy_from_user_ret(&iload, (drm_mga_iload_t *)arg, sizeof(iload), -EFAULT); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_iload called without lock held\n"); + return -EINVAL; + } + buf = dma->buflist[ iload.idx ]; buf_priv = buf->dev_private; bus_address = buf->bus_address; @@ -795,6 +809,10 @@ int mga_vertex(struct inode *inode, struct file *filp, copy_from_user_ret(&vertex, (drm_mga_vertex_t *)arg, sizeof(vertex), -EFAULT); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_vertex called without lock held\n"); + return -EINVAL; + } DRM_DEBUG("mga_vertex\n"); @@ -859,6 +877,11 @@ int mga_dma(struct inode *inode, struct file *filp, unsigned int cmd, DRM_DEBUG("%d %d: %d send, %d req\n", current->pid, d.context, d.send_count, d.request_count); + if(!_DRM_LOCK_IS_HELD(dev->lock.hw_lock->lock)) { + DRM_ERROR("mga_dma called without lock held\n"); + return -EINVAL; + } + /* Please don't send us buffers. */ if (d.send_count != 0) { diff --git a/shared-core/drm.h b/shared-core/drm.h index ebc6f7e7..ae4c65ca 100644 --- a/shared-core/drm.h +++ b/shared-core/drm.h @@ -61,6 +61,19 @@ typedef unsigned int drm_context_t; typedef unsigned int drm_drawable_t; typedef unsigned int drm_magic_t; +/* Warning: If you change this structure, make sure you change + * XF86DRIClipRectRec in the server as well */ + +typedef struct drm_clip_rect { + unsigned short x1; + unsigned short y1; + unsigned short x2; + unsigned short y2; +} drm_clip_rect_t; + +/* Seperate include files for the i810/mga specific structures */ +#include "mga_drm.h" +#include "i810_drm.h" typedef struct drm_version { int version_major; /* Major version */ @@ -321,5 +334,19 @@ typedef struct drm_agp_info { #define DRM_IOCTL_AGP_BIND DRM_IOWR(0x36, drm_agp_binding_t) #define DRM_IOCTL_AGP_UNBIND DRM_IOW( 0x37, drm_agp_binding_t) -/* 0x40 is reserved for mga dma init */ +/* Mga specific ioctls */ +#define DRM_IOCTL_MGA_INIT DRM_IOW( 0x40, drm_mga_init_t) +#define DRM_IOCTL_MGA_SWAP DRM_IOW( 0x41, drm_mga_swap_t) +#define DRM_IOCTL_MGA_CLEAR DRM_IOW( 0x42, drm_mga_clear_t) +#define DRM_IOCTL_MGA_ILOAD DRM_IOW( 0x43, drm_mga_iload_t) +#define DRM_IOCTL_MGA_VERTEX DRM_IOW( 0x44, drm_mga_vertex_t) +#define DRM_IOCTL_MGA_FLUSH DRM_IOW( 0x45, drm_lock_t ) + +/* I810 specific ioctls */ +#define DRM_IOCTL_I810_INIT DRM_IOW( 0x40, drm_i810_init_t) +#define DRM_IOCTL_I810_VERTEX DRM_IOW( 0x41, drm_i810_vertex_t) +#define DRM_IOCTL_I810_DMA DRM_IOW( 0x42, drm_i810_general_t) +#define DRM_IOCTL_I810_FLUSH DRM_IO ( 0x43) +#define DRM_IOCTL_I810_GETAGE DRM_IO ( 0x44) + #endif diff --git a/shared/drm.h b/shared/drm.h index ebc6f7e7..ae4c65ca 100644 --- a/shared/drm.h +++ b/shared/drm.h @@ -61,6 +61,19 @@ typedef unsigned int drm_context_t; typedef unsigned int drm_drawable_t; typedef unsigned int drm_magic_t; +/* Warning: If you change this structure, make sure you change + * XF86DRIClipRectRec in the server as well */ + +typedef struct drm_clip_rect { + unsigned short x1; + unsigned short y1; + unsigned short x2; + unsigned short y2; +} drm_clip_rect_t; + +/* Seperate include files for the i810/mga specific structures */ +#include "mga_drm.h" +#include "i810_drm.h" typedef struct drm_version { int version_major; /* Major version */ @@ -321,5 +334,19 @@ typedef struct drm_agp_info { #define DRM_IOCTL_AGP_BIND DRM_IOWR(0x36, drm_agp_binding_t) #define DRM_IOCTL_AGP_UNBIND DRM_IOW( 0x37, drm_agp_binding_t) -/* 0x40 is reserved for mga dma init */ +/* Mga specific ioctls */ +#define DRM_IOCTL_MGA_INIT DRM_IOW( 0x40, drm_mga_init_t) +#define DRM_IOCTL_MGA_SWAP DRM_IOW( 0x41, drm_mga_swap_t) +#define DRM_IOCTL_MGA_CLEAR DRM_IOW( 0x42, drm_mga_clear_t) +#define DRM_IOCTL_MGA_ILOAD DRM_IOW( 0x43, drm_mga_iload_t) +#define DRM_IOCTL_MGA_VERTEX DRM_IOW( 0x44, drm_mga_vertex_t) +#define DRM_IOCTL_MGA_FLUSH DRM_IOW( 0x45, drm_lock_t ) + +/* I810 specific ioctls */ +#define DRM_IOCTL_I810_INIT DRM_IOW( 0x40, drm_i810_init_t) +#define DRM_IOCTL_I810_VERTEX DRM_IOW( 0x41, drm_i810_vertex_t) +#define DRM_IOCTL_I810_DMA DRM_IOW( 0x42, drm_i810_general_t) +#define DRM_IOCTL_I810_FLUSH DRM_IO ( 0x43) +#define DRM_IOCTL_I810_GETAGE DRM_IO ( 0x44) + #endif |