Index: dev/drm/drmP.h
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drmP.h,v
retrieving revision 1.32
diff -u -b -r1.32 drmP.h
--- dev/drm/drmP.h	7 Jul 2008 00:33:23 -0000	1.32
+++ dev/drm/drmP.h	10 Aug 2008 00:57:11 -0000
@@ -59,6 +59,7 @@
 #include <sys/param.h>
 #include <sys/queue.h>
 #include <sys/malloc.h>
+#include <sys/vmem.h>
 #include <sys/kernel.h>
 #ifdef __FreeBSD__
 #include <sys/module.h>
@@ -71,6 +72,7 @@
 #endif
 #include <sys/proc.h>
 #include <sys/lock.h>
+#include <sys/condvar.h>
 #include <sys/fcntl.h>
 #include <sys/uio.h>
 #include <sys/filio.h>
@@ -136,6 +138,7 @@
 #include "drm.h"
 #include "drm_linux_list.h"
 #include "drm_atomic.h"
+#include "drm_netbsd.h"
 
 #if defined(__FreeBSD__) || defined(__NetBSD__)
 #if defined(_KERNEL_OPT)
@@ -206,10 +209,31 @@
 #define DRM_DEV_UID	0
 #define DRM_DEV_GID	0
 
-#define wait_queue_head_t	atomic_t
-#define DRM_WAKEUP(w)		wakeup((void *)w)
-#define DRM_WAKEUP_INT(w)	wakeup(w)
-#define DRM_INIT_WAITQUEUE(queue) do {(void)(queue);} while (0)
+typedef struct drm_wait_queue {
+	kcondvar_t	cv;
+	kmutex_t	lock;
+} wait_queue_head_t;
+
+#define	DRM_INIT_WAITQUEUE(q)	\
+{ \
+	mutex_init(&(q)->lock, MUTEX_DEFAULT, IPL_VM); \
+	cv_init(&(q)->cv, "drmwtq");	\
+}
+
+#define	DRM_DESTROY_WAITQUEUE(q)	\
+{ \
+	mutex_destroy(&(q)->lock);	\
+	cv_destroy(&(q)->cv);	\
+}
+
+#define	DRM_WAKEUP(q)	\
+{ \
+	mutex_enter(&(q)->lock); \
+	cv_broadcast(&(q)->cv);	\
+	mutex_exit(&(q)->lock);	\
+}
+
+#define	DRM_WAKEUP_INT DRM_WAKEUP
 
 #if defined(__FreeBSD__) && __FreeBSD_version < 502109
 #define bus_alloc_resource_any(dev, type, rid, flags) \
@@ -238,7 +262,7 @@
 #define DRM_STRUCTPROC		struct proc
 #define DRM_STRUCTCDEVPROC	struct lwp
 #define DRM_SPINTYPE		kmutex_t
-#define DRM_SPININIT(l,name)	mutex_init(l, MUTEX_DEFAULT, IPL_VM)
+#define DRM_SPININIT(l,name)	mutex_init(l, MUTEX_DEFAULT, IPL_NONE)
 #define DRM_SPINUNINIT(l)	mutex_destroy(l)
 #define DRM_SPINLOCK(l)		mutex_enter(l)
 #define DRM_SPINUNLOCK(u)	mutex_exit(u)
@@ -276,7 +300,7 @@
 #define IRQ_NONE		/* nothing */
 #elif defined(__NetBSD__)
 typedef int			irqreturn_t;
-#define IRQ_HANDLED		0
+#define IRQ_HANDLED		1
 #define IRQ_NONE		0
 #endif
 
@@ -314,8 +338,8 @@
 	drm_device_t *dev = (minor(kdev) < DRM_MAXUNITS) ?		\
 		drm_units[minor(kdev)] : NULL
 #ifdef __x86_64__
-#define DRM_NETBSD_ADDR2HANDLE(addr)	(addr   & 0x7fffffffffffffff)
-#define DRM_NETBSD_HANDLE2ADDR(handle)	(handle | 0x8000000000000000)
+#define DRM_NETBSD_ADDR2HANDLE(addr)	((vaddr_t)(addr) - vm_map_min(kernel_map))
+#define DRM_NETBSD_HANDLE2ADDR(handle)	((vaddr_t)(handle) + vm_map_min(kernel_map))
 #else
 #define DRM_NETBSD_ADDR2HANDLE(addr)	(addr)
 #define DRM_NETBSD_HANDLE2ADDR(handle)	(handle)
@@ -389,7 +413,6 @@
 					"lock; addl $0,0(%%rsp)" : : : "memory");
 #endif
 
-#ifdef __FreeBSD__
 #define DRM_READ8(map, offset)						\
 	*(volatile u_int8_t *) (((unsigned long)(map)->handle) + (offset))
 #define DRM_READ16(map, offset)						\
@@ -404,29 +427,10 @@
 	*(volatile u_int32_t *)(((unsigned long)(map)->handle) + (offset)) = val
 
 #define DRM_VERIFYAREA_READ( uaddr, size )		\
-	(!useracc(__DECONST(char *, uaddr), size, VM_PROT_READ))
-
-#else /* __FreeBSD__ */
-
-typedef vaddr_t vm_offset_t;
-
-#define DRM_READ8(map, offset)		\
-	bus_space_read_1( (map)->bst, (map)->bsh, (offset))
-#define DRM_READ16(map, offset)		\
-	bus_space_read_2( (map)->bst, (map)->bsh, (offset))
-#define DRM_READ32(map, offset)		\
-	bus_space_read_4( (map)->bst, (map)->bsh, (offset))
-#define DRM_WRITE8(map, offset, val)	\
-	bus_space_write_1((map)->bst, (map)->bsh, (offset), (val))
-#define DRM_WRITE16(map, offset, val)	\
-	bus_space_write_2((map)->bst, (map)->bsh, (offset), (val))
-#define DRM_WRITE32(map, offset, val)	\
-	bus_space_write_4((map)->bst, (map)->bsh, (offset), (val))
-
-#define DRM_VERIFYAREA_READ( uaddr, size )				\
 	(!uvm_map_checkprot(&(curproc->p_vmspace->vm_map),		\
 			    (vaddr_t)uaddr, (vaddr_t)uaddr+size, UVM_PROT_READ))
-#endif /* !__FreeBSD__ */
+
+typedef vaddr_t vm_offset_t;
 
 #define DRM_COPY_TO_USER_IOCTL(user, kern, size)	\
 	if ( IOCPARM_LEN(cmd) != size)			\
@@ -456,7 +460,7 @@
 #define le32_to_cpu(x) le32toh(x)
 
 #define DRM_ERR(v)		v
-#define DRM_HZ			hz
+#define DRM_HZ			hz /* XXX maybe mstohz(something) */
 #define DRM_UDELAY(udelay)	DELAY(udelay)
 #define DRM_TIME_SLICE		(hz/20)  /* Time slice for GLXContexts	  */
 
@@ -512,16 +516,29 @@
 	DRM_LOCK();						\
 }
 #elif defined(__NetBSD__)
-#define DRM_WAIT_ON( ret, queue, timeout, condition )		\
-for ( ret = 0 ; !ret && !(condition) ; ) {			\
-	DRM_UNLOCK();						\
-	mutex_enter(&dev->irq_lock);				\
-	if (!(condition))					\
-	   ret = mtsleep(&(queue), PZERO | PCATCH, 		\
-			 "drmwtq", (timeout), &dev->irq_lock);	\
-	mutex_exit(&dev->irq_lock);				\
-	DRM_LOCK();						\
-}
+#define	DRM_WAIT_ON(ret, q, timeout, condition)  		\
+mutex_enter(&(q)->lock);					\
+while (!(condition)) {						\
+	ret = cv_timedwait_sig(&(q)->cv, &(q)->lock, (timeout)); \
+	if (ret == EWOULDBLOCK) {				\
+		ret = EBUSY;  					\
+		break; 						\
+	} else if (ret) {					\
+		ret = EINTR;					\
+		break;						\
+	} else {						\
+		ret = 0; 					\
+	} 							\
+} 								\
+mutex_exit(&(q)->lock);
+#define	DRM_LOCAL_WAIT_ON(ret, mutex, cv) 			\
+do {								\
+	mutex_enter(mutex);					\
+	ret = cv_wait_sig(cv, mutex);				\
+	if (ret)						\
+		ret = EINTR;					\
+	mutex_exit(mutex); 					\
+} while (0); 
 #else
 #define DRM_WAIT_ON( ret, queue, timeout, condition )		\
 for ( ret = 0 ; !ret && !(condition) ; ) {			\
@@ -614,13 +631,10 @@
 typedef struct drm_dma_handle {
 	void *vaddr;
 	bus_addr_t busaddr;
-	bus_dma_tag_t dmat;
-	bus_dmamap_t map;
-	bus_dma_segment_t segs[1];
+
 	size_t size;
-	void *addr;
+	struct drm_dmamem	*mem;
 } drm_dma_handle_t;
-#define DRM_PCI_DMAADDR(p)   ((p)->map->dm_segs[0].ds_addr)
 
 typedef struct drm_buf_entry {
 	int		  buf_size;
@@ -650,7 +664,8 @@
 typedef struct drm_lock_data {
 	drm_hw_lock_t	  *hw_lock;	/* Hardware lock		   */
 	DRMFILE		  filp;	        /* Unique identifier of holding process (NULL is kernel)*/
-	int		  lock_queue;	/* Queue of blocked processes	   */
+	kmutex_t	  lock_mutex;
+	kcondvar_t	  lock_cv;	/* Queue of blocked processes	   */
 	unsigned long	  lock_time;	/* Time of last lock in jiffies	   */
 } drm_lock_data_t;
 
@@ -702,7 +717,11 @@
 	void            *virtual;
 	int             pages;
 	dma_addr_t	*busaddr;
-	drm_dma_handle_t *dmah;	/* Handle to PCI memory for ATI PCIGART table */
+/*
+ * Handle to PCI memory for GART table
+ */
+	drm_dma_handle_t 	*dmah;
+	struct drm_dmamem 	*mem;
 } drm_sg_mem_t;
 
 typedef TAILQ_HEAD(drm_map_list, drm_local_map) drm_map_list_t;
@@ -726,6 +745,8 @@
 #ifdef __NetBSD__
 	int		*cnt;
 	bus_size_t	mapsize;
+	u_long		cookie;   /* mmap cookie */
+	struct drm_dmamem *mem;
 #endif
 	TAILQ_ENTRY(drm_local_map) link;
 } drm_local_map_t;
@@ -916,7 +937,8 @@
 
 	atomic_t	  context_flag;	/* Context swapping flag	   */
 	int		  last_context;	/* Last current context		   */
-   	int		  vbl_queue;	/* vbl wait channel */
+	wait_queue_head_t  vbl_queue;	/* vbl wait channel */
+
    	atomic_t          vbl_received;
 
 #ifdef __FreeBSD__
@@ -934,6 +956,8 @@
 	void		  *dev_private;
 	unsigned int	  agp_buffer_token;
 	drm_local_map_t   *agp_buffer_map;
+
+	vmem_t	  	*vmem;	/* vmem cookie arena */
 };
 
 extern int	drm_debug_flag;
@@ -979,8 +1003,14 @@
 #endif /* __NetBSD__ || __OpenBSD__ */
 
 /* Memory management support (drm_memory.c) */
-void	drm_mem_init(void);
-void	drm_mem_uninit(void);
+
+/*
+ * XXX The drm_mem_init/uninit functions originally took void arguments.
+ *     However, these are sensible places to create/destroy the mmap cookie
+ *     extent map, and so they now take a pointer to the "drm device".
+ */
+void	drm_mem_init(struct drm_device *);
+void	drm_mem_uninit(struct drm_device *);
 void	*drm_alloc(size_t size, int area);
 void	*drm_calloc(size_t nmemb, size_t size, int area);
 void	*drm_realloc(void *oldpt, size_t oldsize, size_t size,
@@ -1154,9 +1184,12 @@
 {
 	drm_local_map_t *map;
 
+	/* NOTE: this code must be remain in harmony with related code
+	 *  in drm_mmap(), drm_addmap_ioctl(), and/or drm_rmmap().
+	 */ 
 	DRM_SPINLOCK_ASSERT(&dev->dev_lock);
 	TAILQ_FOREACH(map, &dev->maplist, link) {
-		if (map->offset == offset)
+		if (map->cookie == offset)
 			return map;
 	}
 	return NULL;
Index: dev/drm/drm_auth.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_auth.c,v
retrieving revision 1.6
diff -u -b -r1.6 drm_auth.c
--- dev/drm/drm_auth.c	29 Jun 2008 12:49:08 -0000	1.6
+++ dev/drm/drm_auth.c	10 Aug 2008 00:57:11 -0000
@@ -79,7 +79,6 @@
 	entry->priv  = priv;
 	entry->next  = NULL;
 
-	DRM_LOCK();
 	if (dev->magiclist[hash].tail) {
 		dev->magiclist[hash].tail->next = entry;
 		dev->magiclist[hash].tail	= entry;
@@ -87,7 +86,6 @@
 		dev->magiclist[hash].head	= entry;
 		dev->magiclist[hash].tail	= entry;
 	}
-	DRM_UNLOCK();
 
 	return 0;
 }
Index: dev/drm/drm_bufs.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_bufs.c,v
retrieving revision 1.10
diff -u -b -r1.10 drm_bufs.c
--- dev/drm/drm_bufs.c	29 Jun 2008 12:49:08 -0000	1.10
+++ dev/drm/drm_bufs.c	10 Aug 2008 00:57:11 -0000
@@ -139,8 +139,10 @@
 	 * initialization necessary.
 	 */
 	map = malloc(sizeof(*map), M_DRM, M_ZERO | M_NOWAIT);
-	if ( !map )
+	if ( !map ) {
+		DRM_LOCK();
 		return DRM_ERR(ENOMEM);
+	}
 
 	map->offset = offset;
 	map->size = size;
@@ -148,6 +150,20 @@
 	map->flags = flags;
 	map->cnt = NULL;	/* cnt, mapsize added for NetBSD port */
 	map->mapsize = 0;
+	map->cookie = 0;
+
+	/* XXX We're not managing any actual address space here; we simply
+	 *     need to assign unique and sane cookies as to not offend
+	 *     the device pager.
+	 */
+	map->cookie = vmem_alloc(dev->vmem, map->size, 
+		VM_INSTANTFIT | VM_NOSLEEP);
+	if (map->cookie == 0) {
+		DRM_DEBUG("vmem_alloc() failed\n");
+		free(map, M_DRM);
+		DRM_LOCK();
+		return DRM_ERR(ENOMEM);
+	}
 
 	switch ( map->type ) {
 	case _DRM_REGISTERS:
@@ -162,20 +178,22 @@
 #endif
 		break;
 	case _DRM_SHM:
-		map->handle = malloc(map->size, M_DRM, M_NOWAIT);
+		map->mem = drm_dmamem_pgalloc(dev, btop(map->size));
 		DRM_DEBUG( "%lu %d %p\n",
 			   map->size, drm_order(map->size), map->handle );
-		if ( !map->handle ) {
+		if ( map->mem == NULL ) {
 			free(map, M_DRM);
+			DRM_LOCK();
 			return DRM_ERR(ENOMEM);
 		}
-		map->offset = (unsigned long)map->handle;
+		map->handle = map->mem->dd_kva;
+		map->offset = (unsigned long)map->mem->dd_kva;
 		if ( map->flags & _DRM_CONTAINS_LOCK ) {
 			/* Prevent a 2nd X Server from creating a 2nd lock */
 			DRM_LOCK();
 			if (dev->lock.hw_lock != NULL) {
 				DRM_UNLOCK();
-				free(map->handle, M_DRM);
+				drm_dmamem_free(map->mem);
 				free(map, M_DRM);
 				return DRM_ERR(EBUSY);
 			}
@@ -197,15 +215,18 @@
 		}
 		if (!valid) {
 			free(map, M_DRM);
+			DRM_LOCK();
 			return DRM_ERR(EACCES);
 		}*/
 		break;
 	case _DRM_SCATTER_GATHER:
 		if (!dev->sg) {
 			free(map, M_DRM);
+			DRM_LOCK();
 			return DRM_ERR(EINVAL);
 		}
 		map->offset = map->offset + dev->sg->handle;
+		map->mem = dev->sg->mem;
 		break;
 	case _DRM_CONSISTENT:
 		/* Unfortunately, we don't get any alignment specification from
@@ -220,14 +241,17 @@
 		map->dmah = drm_pci_alloc(dev, map->size, align, 0xfffffffful);
 		if (map->dmah == NULL) {
 			free(map, M_DRM);
+			DRM_LOCK();
 			return DRM_ERR(ENOMEM);
 		}
 		map->handle = map->dmah->vaddr;
 		map->offset = map->dmah->busaddr;
+		map->mem = map->dmah->mem;
 		break;
 	default:
 		DRM_ERROR("Bad map type %d\n", map->type);
 		free(map, M_DRM);
+		DRM_LOCK();
 		return DRM_ERR(EINVAL);
 	}
 
@@ -274,11 +298,8 @@
 	request.mtrr   = map->mtrr;
 	request.handle = map->handle;
 
-	if (request.type != _DRM_SHM) {
-		request.handle = (void *)request.offset;
-	} else {
-		request.handle = (void *)DRM_NETBSD_ADDR2HANDLE((uintptr_t)map->handle);
-	}
+	request.handle = (void *)map->cookie;
+
 	DRM_COPY_TO_USER_IOCTL((drm_map_t *)data, request, sizeof(drm_map_t));
 
 	return 0;
@@ -304,7 +325,7 @@
 #endif
 		break;
 	case _DRM_SHM:
-		free(map->handle, M_DRM);
+		drm_dmamem_free(map->mem);
 		break;
 	case _DRM_AGP:
 	case _DRM_SCATTER_GATHER:
@@ -314,6 +335,9 @@
 		break;
 	}
 
+	if (map->cookie != 0)
+		vmem_free(dev->vmem, map->cookie, map->size);
+
 	TAILQ_REMOVE(&dev->maplist, map, link);
 	free(map, M_DRM);
 }
@@ -771,7 +795,6 @@
 {
 	int order, ret;
 
-	DRM_SPINLOCK(&dev->dma_lock);
 
 	if (request->count < 0 || request->count > 4096)
 		return DRM_ERR(EINVAL);
@@ -780,6 +803,8 @@
 	if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
 		return DRM_ERR(EINVAL);
 
+	DRM_SPINLOCK(&dev->dma_lock);
+
 	/* No more allocations after first buffer-using ioctl. */
 	if (dev->buf_use != 0) {
 		DRM_SPINUNLOCK(&dev->dma_lock);
@@ -802,7 +827,6 @@
 {
 	int order, ret;
 
-	DRM_SPINLOCK(&dev->dma_lock);
 
 	if (!DRM_SUSER(DRM_CURPROC))
 		return DRM_ERR(EACCES);
@@ -814,6 +838,8 @@
 	if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
 		return DRM_ERR(EINVAL);
 
+	DRM_SPINLOCK(&dev->dma_lock);
+
 	/* No more allocations after first buffer-using ioctl. */
 	if (dev->buf_use != 0) {
 		DRM_SPINUNLOCK(&dev->dma_lock);
@@ -836,7 +862,6 @@
 {
 	int order, ret;
 
-	DRM_SPINLOCK(&dev->dma_lock);
 
 	if (!DRM_SUSER(DRM_CURPROC))
 		return DRM_ERR(EACCES);
@@ -848,6 +873,8 @@
 	if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
 		return DRM_ERR(EINVAL);
 
+	DRM_SPINLOCK(&dev->dma_lock);
+
 	/* No more allocations after first buffer-using ioctl. */
 	if (dev->buf_use != 0) {
 		DRM_SPINUNLOCK(&dev->dma_lock);
@@ -1024,7 +1051,7 @@
 	struct vmspace *vms;
 	struct vnode *vn;
 	voff_t foff;
-	vsize_t size, rsize;
+	vsize_t size;
 	vaddr_t vaddr;
 
 	drm_buf_map_t request;
@@ -1047,25 +1074,25 @@
 	if ((dev->driver.use_agp && (dma->flags & _DRM_DMA_USE_AGP)) ||
 	    (dev->driver.use_sg && (dma->flags & _DRM_DMA_USE_SG))) {
 		drm_local_map_t *map = dev->agp_buffer_map;
+		u_long token = dev->agp_buffer_token;
 
 		if (map == NULL) {
 			retcode = EINVAL;
 			goto done;
 		}
+		/* XXX using cookie, not actual offset here */
 		size = round_page(map->size);
-		foff = map->offset;
+		foff = token ? token : map->cookie;
 	} else {
 		size = round_page(dma->byte_count),
 		foff = 0;
 	}
 
-	vaddr = p->l_proc->p_emul->e_vm_default_addr(p->l_proc,
-	    (vaddr_t)vms->vm_daddr, size);
-	rsize = round_page(size);
-	DRM_DEBUG("mmap %lx/%ld\n", vaddr, rsize);
-	retcode = uvm_mmap(&vms->vm_map, &vaddr, rsize,
-	    UVM_PROT_READ | UVM_PROT_WRITE, UVM_PROT_ALL, MAP_SHARED,
-	    &vn->v_uobj, foff, p->l_proc->p_rlimit[RLIMIT_MEMLOCK].rlim_cur);
+	vaddr = VM_DEFAULT_ADDRESS(p->l_proc->p_vmspace->vm_daddr, size);
+	DRM_DEBUG("mmap %lx/%ld\n", vaddr, size);
+	retcode = uvm_mmap(&vms->vm_map, &vaddr, size, UVM_PROT_RW, 
+	UVM_PROT_ALL, MAP_SHARED, (void *)vn, foff, 
+	p->l_proc->p_rlimit[RLIMIT_MEMLOCK].rlim_cur);
 
 	if (retcode)
 		goto done;
Index: dev/drm/drm_dma.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_dma.c,v
retrieving revision 1.7
diff -u -b -r1.7 drm_dma.c
--- dev/drm/drm_dma.c	19 May 2008 00:17:39 -0000	1.7
+++ dev/drm/drm_dma.c	10 Aug 2008 00:57:11 -0000
@@ -48,7 +48,7 @@
 	if (dev->dma == NULL)
 		return DRM_ERR(ENOMEM);
 
-	DRM_SPININIT(&dev->dma_lock, "drmdma");
+	mutex_init(&dev->dma_lock, MUTEX_DEFAULT, IPL_NONE);
 
 	return 0;
 }
@@ -93,7 +93,7 @@
 	if (dev->dma)
 		free(dev->dma, M_DRM);
 	dev->dma = NULL;
-	DRM_SPINUNINIT(&dev->dma_lock);
+	mutex_destroy(&dev->dma_lock);
 }
 
 
Index: dev/drm/drm_drv.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_drv.c,v
retrieving revision 1.19
diff -u -b -r1.19 drm_drv.c
--- dev/drm/drm_drv.c	3 Jul 2008 17:36:44 -0000	1.19
+++ dev/drm/drm_drv.c	10 Aug 2008 00:57:11 -0000
@@ -204,12 +204,12 @@
         /* dev->maplist : drm_load */
         dev->context_sareas = NULL;
         dev->max_context = 0;
-	mutex_init(&dev->dev_lock, MUTEX_DEFAULT, IPL_NONE);
         dev->dma = NULL;
 	/* dev->irq : drm_load */
 	dev->irq_enabled = 0;
 	dev->pa = *pa;
 	dev->irqh = NULL;
+
 	for(unit=0; unit<DRM_MAX_PCI_RESOURCE; unit++)
 	{
 		dev->pci_map_data[unit].mapped = 0;
@@ -238,7 +238,6 @@
 	}
 	dev->context_flag = 0;
 	dev->last_context = 0;
-	dev->vbl_queue = 0;
 	dev->vbl_received = 0;
 	dev->buf_pgid = 0;
 	dev->sysctl = NULL;
@@ -332,7 +331,6 @@
 		dev->magiclist[i].tail = NULL;
 	}
 
-	dev->lock.lock_queue = 0;
 	dev->irq_enabled = 0;
 	dev->context_flag = 0;
 	dev->last_context = 0;
@@ -422,7 +420,9 @@
 	if ( dev->lock.hw_lock ) {
 		dev->lock.hw_lock = NULL; /* SHM removed */
 		dev->lock.filp = NULL;
-		DRM_WAKEUP_INT((void *)&dev->lock.lock_queue);
+                mutex_enter(&(dev->lock.lock_mutex)); 
+		cv_broadcast(&(dev->lock.lock_cv));
+		mutex_exit(&(dev->lock.lock_mutex));
 	}
 
 	while ((filep = TAILQ_FIRST(&dev->files)) != NULL) {
@@ -438,6 +438,13 @@
 static int drm_load(drm_device_t *dev)
 {
 	int retcode;
+	pcireg_t reg;
+
+       cv_init(&(dev->lock.lock_cv), "drm_cv");
+       mutex_init(&(dev->lock.lock_mutex), MUTEX_DEFAULT, IPL_NONE);
+       mutex_init(&(dev->dev_lock), MUTEX_DEFAULT, IPL_NONE);
+       /*mutex_init(&dev->drw_lock, MUTEX_DEFAULT, IPL_NONE);*/
+
 
 	DRM_DEBUG( "\n" );
 
@@ -450,9 +457,10 @@
 	dev->pci_vendor = PCI_VENDOR(dev->pa.pa_id);
 	dev->pci_device = PCI_PRODUCT(dev->pa.pa_id);
 
+
 	TAILQ_INIT(&dev->maplist);
 
-	drm_mem_init();
+	drm_mem_init(dev);
 	drm_sysctl_init(dev);
 	TAILQ_INIT(&dev->files);
 
@@ -464,6 +472,12 @@
 			goto error;
 	}
 
+	/* enable bus mastering */
+	reg = pci_conf_read(dev->pa.pa_pc, dev->pa.pa_tag, 
+		PCI_COMMAND_STATUS_REG);
+	pci_conf_write(dev->pa.pa_pc, dev->pa.pa_tag, PCI_COMMAND_STATUS_REG,
+	    reg | PCI_COMMAND_MASTER_ENABLE);
+
 	if (dev->driver.use_agp) {
 		if (drm_device_is_agp(dev))
 			dev->agp = drm_agp_init(dev);
@@ -502,7 +516,10 @@
 	DRM_LOCK();
 	drm_lastclose(dev);
 	DRM_UNLOCK();
-	DRM_SPINUNINIT(&dev->dev_lock);
+        cv_destroy(&(dev->lock.lock_cv));
+	mutex_destroy(&(dev->lock.lock_mutex));
+	mutex_destroy(&dev->dev_lock);
+	/*mutex_destroy(&dev->drw_lock);*/
 	return retcode;
 }
 
@@ -553,7 +570,7 @@
 	if (dev->driver.unload != NULL)
 		dev->driver.unload(dev);
 
-	drm_mem_uninit();
+	drm_mem_uninit(dev);
 	DRM_SPINUNINIT(&dev->dev_lock);
 }
 
@@ -657,8 +674,10 @@
 				break;	/* Got lock */
 			}
 				/* Contention */
-			retcode = mtsleep((void *)&dev->lock.lock_queue,
-			    PZERO | PCATCH, "drmlk2", 0, &dev->dev_lock);
+
+
+			DRM_LOCAL_WAIT_ON(retcode, &dev->dev_lock,
+					  &dev->lock.lock_cv); 
 			if (retcode)
 				break;
 		}
Index: dev/drm/drm_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_irq.c,v
retrieving revision 1.16
diff -u -b -r1.16 drm_irq.c
--- dev/drm/drm_irq.c	7 Jul 2008 00:33:23 -0000	1.16
+++ dev/drm/drm_irq.c	10 Aug 2008 00:57:11 -0000
@@ -68,9 +68,9 @@
 	irqreturn_t ret;
 	drm_device_t *dev = (drm_device_t *)arg;
 
-	DRM_SPINLOCK(&dev->irq_lock);
+	mutex_spin_enter(&dev->irq_lock);
 	ret = dev->driver.irq_handler(arg);
-	DRM_SPINUNLOCK(&dev->irq_lock);
+	mutex_spin_exit(&dev->irq_lock);
 	return ret;
 }
 
@@ -94,7 +94,7 @@
 
 	dev->context_flag = 0;
 
-	DRM_SPININIT(&dev->irq_lock, "DRM IRQ lock");
+	mutex_init(&dev->irq_lock, MUTEX_DEFAULT, IPL_VM);
 
 				/* Before installing handler */
 
@@ -107,7 +107,7 @@
 		goto err;
 	}
 	istr = pci_intr_string(dev->pa.pa_pc, ih);
-	dev->irqh = pci_intr_establish(dev->pa.pa_pc, ih, IPL_TTY,
+	dev->irqh = pci_intr_establish(dev->pa.pa_pc, ih, IPL_VM,
 	    drm_irq_handler_wrap, dev);
 	if (!dev->irqh) {
 		retcode = ENOENT;
@@ -124,7 +124,7 @@
 err:
 	DRM_LOCK();
 	dev->irq_enabled = 0;
-	DRM_SPINUNINIT(&dev->irq_lock);
+	mutex_destroy(&dev->irq_lock);
 	DRM_UNLOCK();
 	return retcode;
 }
@@ -141,7 +141,7 @@
 	dev->driver.irq_uninstall(dev);
 
 	pci_intr_disestablish(dev->pa.pa_pc, dev->irqh);
-	DRM_SPINUNINIT(&dev->irq_lock);
+	mutex_destroy(&dev->irq_lock);
 
 	return 0;
 }
@@ -209,9 +209,9 @@
 
 		vblwait.reply.sequence = atomic_read(&dev->vbl_received);
 		
-		DRM_SPINLOCK(&dev->irq_lock);
+		mutex_spin_enter(&dev->irq_lock);
 		TAILQ_INSERT_HEAD(&dev->vbl_sig_list, vbl_sig, link);
-		DRM_SPINUNLOCK(&dev->irq_lock);
+		mutex_spin_exit(&dev->irq_lock);
 		ret = 0;
 #endif
 		ret = EINVAL;
Index: dev/drm/drm_lock.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_lock.c,v
retrieving revision 1.7
diff -u -b -r1.7 drm_lock.c
--- dev/drm/drm_lock.c	19 May 2008 00:17:39 -0000	1.7
+++ dev/drm/drm_lock.c	10 Aug 2008 00:57:11 -0000
@@ -88,6 +88,7 @@
 {
 	unsigned int old, new;
 
+	mutex_enter(&dev->lock.lock_mutex);
 	dev->lock.filp = NULL;
 	do {
 		old  = *lock;
@@ -97,9 +98,11 @@
 	if (_DRM_LOCK_IS_HELD(old) && _DRM_LOCKING_CONTEXT(old) != context) {
 		DRM_ERROR("%d freed heavyweight lock held by %d\n",
 			  context, _DRM_LOCKING_CONTEXT(old));
+		mutex_exit(&dev->lock.lock_mutex);
 		return 1;
 	}
-	DRM_WAKEUP_INT((void *)&dev->lock.lock_queue);
+        cv_broadcast(&(dev->lock.lock_cv));
+	mutex_exit(&(dev->lock.lock_mutex));
 	return 0;
 }
 
@@ -123,7 +126,7 @@
         if (dev->driver.use_dma_queue && lock.context < 0)
                 return EINVAL;
 
-	DRM_LOCK();
+	mutex_enter(&(dev->lock.lock_mutex));
 	for (;;) {
 		if (drm_lock_take(&dev->lock.hw_lock->lock, lock.context)) {
 			dev->lock.filp = (void *)(uintptr_t)DRM_CURRENTPID;
@@ -133,12 +136,13 @@
 		}
 
 		/* Contention */
-		ret = mtsleep((void *)&dev->lock.lock_queue, PZERO | PCATCH,
-		    "drmlk2", 0, &dev->dev_lock);
-		if (ret != 0)
+		 ret = cv_wait_sig(&(dev->lock.lock_cv), &(dev->lock.lock_mutex));
+		if (ret != 0) {
+			mutex_exit(&(dev->lock.lock_mutex));
 			break;
 	}
-	DRM_UNLOCK();
+	}
+	mutex_exit(&(dev->lock.lock_mutex));
 	DRM_DEBUG("%d %s\n", lock.context, ret ? "interrupted" : "has lock");
 
 	if (ret != 0)
Index: dev/drm/drm_memory.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_memory.c,v
retrieving revision 1.14
diff -u -b -r1.14 drm_memory.c
--- dev/drm/drm_memory.c	29 Jun 2008 12:49:08 -0000	1.14
+++ dev/drm/drm_memory.c	10 Aug 2008 00:57:11 -0000
@@ -58,15 +58,18 @@
 MALLOC_DEFINE(M_DRM, "drm", "DRM Data Structures");
 #endif
 
-void drm_mem_init(void)
+void drm_mem_init(struct drm_device *dev)
 {
-/*
-	malloc_type_attach(M_DRM);
-*/
+        dev->vmem = vmem_create("drm_vmem", 0x40000000, LONG_MAX, PAGE_SIZE,
+		NULL, NULL, NULL, PAGE_SIZE, VM_NOSLEEP, IPL_VM);
+
+	if (dev->vmem == NULL)
+		DRM_DEBUG("could not create vmem arena\n");
 }
 
-void drm_mem_uninit(void)
+void drm_mem_uninit(struct drm_device *dev)
 {
+	vmem_destroy(dev->vmem);
 }
 
 void *drm_alloc(size_t size, int area)
@@ -95,7 +98,10 @@
 
 void drm_free(void *pt, size_t size, int area)
 {
+	if (pt != NULL) {
 	free(pt, M_DRM);
+		pt = NULL;
+	}
 }
 
 void *drm_ioremap(drm_device_t *dev, drm_local_map_t *map)
Index: dev/drm/drm_netbsd.c
===================================================================
RCS file: dev/drm/drm_netbsd.c
diff -N dev/drm/drm_netbsd.c
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ dev/drm/drm_netbsd.c	10 Aug 2008 00:57:11 -0000
@@ -0,0 +1,142 @@
+/* $NetBSD: drm_netbsd.c,v 1.1 2008/05/28 04:52:48 bjs Exp $ */
+
+/*-
+ * Copyright (c) 2008 The NetBSD Foundation, Inc.
+ * All rights reserved.
+ *
+ * This code is derived from software contributed to The NetBSD Foundation
+ * by Blair Sadewitz.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+
+#include <dev/drm/drmP.h>
+#include <sys/hash.h>
+
+/* XXX Most everything the DRM wants is expressed in pages.  There are possible 
+   scenarios where e.g. the page size does not equal the page size of the GART,
+   but our DRM does not work on those platforms yet. */
+
+struct drm_dmamem *
+drm_dmamem_pgalloc(drm_device_t *dev, size_t pages)
+{
+	struct drm_dmamem	*mem = NULL;
+	size_t	  	 	size = pages << PAGE_SHIFT;
+	int			 ret = 0;
+
+	mem = malloc(sizeof(*mem), M_DRM, M_NOWAIT | M_ZERO);
+	if (mem == NULL)
+		return NULL;
+
+	mem->phase = DRM_DMAMEM_INIT;
+
+	mem->dd_segs = malloc(sizeof(*mem->dd_segs) * pages, M_DRM,
+	    M_NOWAIT | M_ZERO);
+	if (mem->dd_segs == NULL)
+		goto error;
+
+	mem->dd_dmat = dev->pa.pa_dmat;
+	mem->dd_size = size;
+
+	if (bus_dmamap_create(dev->pa.pa_dmat, size, pages, PAGE_SIZE, 0,
+	    BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &mem->dd_dmam) != 0)
+		goto error;
+	mem->phase = DRM_DMAMAP_CREATE;
+
+	if ((ret = bus_dmamem_alloc(dev->pa.pa_dmat, size, PAGE_SIZE, 0,
+	    mem->dd_segs, pages, &mem->dd_nsegs, BUS_DMA_NOWAIT)) != 0) {
+		goto error;
+	}
+	mem->phase = DRM_DMAMEM_ALLOC;
+
+	if (bus_dmamem_map(dev->pa.pa_dmat, mem->dd_segs, mem->dd_nsegs, size, 
+	    &mem->dd_kva, BUS_DMA_COHERENT|BUS_DMA_NOWAIT) != 0)
+		goto error;
+	mem->phase = DRM_DMAMEM_MAP;
+
+	if (bus_dmamap_load(dev->pa.pa_dmat, mem->dd_dmam, mem->dd_kva, size,
+	    NULL, BUS_DMA_NOWAIT) != 0)
+		goto error;
+	mem->phase = DRM_DMAMAP_LOAD;
+
+	memset(mem->dd_kva, 0, size);
+
+	return mem;
+error:
+	mem->phase &= DRM_DMAMEM_FAIL;
+	drm_dmamem_free(mem);
+	return NULL;
+}
+
+void
+drm_dmamem_free(struct drm_dmamem *mem)
+{
+	if (mem == NULL)
+		return;
+
+	if (mem->phase & DRM_DMAMEM_FAIL) {
+		DRM_DEBUG("attempted allocation failed; teardown sequence follows:\n");
+		mem->phase &= ~DRM_DMAMEM_FAIL;
+	} else if (mem->phase & ~DRM_DMAMAP_LOAD) {
+		DRM_DEBUG("invoked by another function on unloaded map; teardown sequence follows:\n");
+	} else {
+		DRM_DEBUG("freeing DMA memory; teardown sequence follows:\n");
+	}
+
+
+	switch (mem->phase) {
+	case DRM_DMAMAP_LOAD: 
+		DRM_DEBUG("bus_dmamap_unload: tag (%p), map (%p)\n",
+			(void *)mem->dd_dmat, (void *)mem->dd_dmam);
+		bus_dmamap_unload(mem->dd_dmat, mem->dd_dmam);
+		/* FALLTHRU */
+	case DRM_DMAMEM_MAP: 
+		DRM_DEBUG("bus_dmamem_unmap: tag (%p), kva (%p), size (%zd)\n",
+			mem->dd_dmat, mem->dd_kva, mem->dd_size);
+		bus_dmamem_unmap(mem->dd_dmat, mem->dd_kva, mem->dd_size); 
+		/* FALLTHRU */
+	case DRM_DMAMEM_ALLOC: 
+		DRM_DEBUG("bus_dmamem_free: tag (%p), segs (%p), nsegs (%i)\n",
+			mem->dd_dmat, mem->dd_segs, mem->dd_nsegs);
+		bus_dmamem_free(mem->dd_dmat, mem->dd_segs, 
+			mem->dd_nsegs);
+		/* FALLTHRU */
+	case DRM_DMAMAP_CREATE: 
+		DRM_DEBUG("bus_dmamap_destroy: tag (%p), map (%p)\n",
+			(void *)mem->dd_dmat, (void *)mem->dd_dmam);
+		bus_dmamap_destroy(mem->dd_dmat, mem->dd_dmam);
+		/* FALLTHRU */
+	case DRM_DMAMEM_INIT:
+		if (mem->dd_segs != NULL) {
+			free(mem->dd_segs, M_DRM);
+			mem->dd_segs = NULL;
+		}
+	break;
+	}
+
+	free(mem, M_DRM);
+	mem = NULL;
+
+	return;
+}
Index: dev/drm/drm_netbsd.h
===================================================================
RCS file: dev/drm/drm_netbsd.h
diff -N dev/drm/drm_netbsd.h
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ dev/drm/drm_netbsd.h	10 Aug 2008 00:57:11 -0000
@@ -0,0 +1,57 @@
+/* $NetBSD: drm_netbsd.h,v 1.1 2008/05/28 04:52:48 bjs Exp $ */
+
+/*-
+ * Copyright (c) 2008 The NetBSD Foundation, Inc.
+ * All rights reserved.
+ *
+ * This code is derived from software contributed to The NetBSD Foundation
+ * by Blair Sadewitz.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "drmP.h"
+
+#define	DRM_DMAMEM_INIT		0x000
+#define DRM_DMAMAP_CREATE	0x001
+#define DRM_DMAMEM_ALLOC	0x002
+#define DRM_DMAMEM_MAP		0x004
+#define DRM_DMAMAP_LOAD		0x008
+#define	DRM_DMAMEM_FAIL		0x800
+
+#define DRM_DMA_BUSADDR(__m)		((__m)->dd_dmam->dm_segs[0].ds_addr)
+#define DRM_DMA_SEGADDR(__m, __s)	((__m)->dd_dmam->dm_segs[__s].ds_addr)
+#define DRM_DMA_SEGSIZE(__m, __s)	((__m)->dd_dmam->dm_segs[__s].ds_len)
+#define DRM_DMA_KERNADDR(__m)		((__m)->dd_kva)
+
+struct drm_dmamem {
+	bus_dma_tag_t 		dd_dmat;
+	bus_dmamap_t 		dd_dmam;
+	bus_dma_segment_t 	*dd_segs;
+	int 			dd_nsegs;
+	size_t 			dd_size;
+	void 			*dd_kva;
+	u_int			phase;
+};
+
+struct	drm_dmamem *drm_dmamem_pgalloc(struct drm_device *, size_t);
+void	drm_dmamem_free(struct drm_dmamem *);
Index: dev/drm/drm_pci.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_pci.c,v
retrieving revision 1.13
diff -u -b -r1.13 drm_pci.c
--- dev/drm/drm_pci.c	29 Jun 2008 12:49:08 -0000	1.13
+++ dev/drm/drm_pci.c	10 Aug 2008 00:57:11 -0000
@@ -35,55 +35,22 @@
 drm_pci_alloc(drm_device_t *dev, size_t size, size_t align, dma_addr_t maxaddr)
 {
 	drm_dma_handle_t *h;
-	int error, nsegs;
-
-
-	/* Need power-of-two alignment, so fail the allocation if it isn't. */
-	if ((align & (align - 1)) != 0) {
-		DRM_ERROR("drm_pci_alloc with non-power-of-two alignment %d\n",
-		    (int)align);
-		return NULL;
-	}
 
 	h = malloc(sizeof(drm_dma_handle_t), M_DRM, M_ZERO | M_NOWAIT);
 
 	if (h == NULL)
 		return NULL;
-	if ((error = bus_dmamem_alloc(dev->pa.pa_dmat, size, align, 0,
-	    h->segs, 1, &nsegs, BUS_DMA_NOWAIT)) != 0) {
-		printf("drm: Unable to allocate DMA, error %d\n", error);
-		goto fail;
-	}
-	if ((error = bus_dmamem_map(dev->pa.pa_dmat, h->segs, nsegs, size, 
-	     &h->addr, BUS_DMA_NOWAIT | BUS_DMA_COHERENT)) != 0) {
-		printf("drm: Unable to map DMA, error %d\n", error);
-	     	goto free;
-	}
-	if ((error = bus_dmamap_create(dev->pa.pa_dmat, size, 1, size, 0,
-	     BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &h->map)) != 0) {
-		printf("drm: Unable to create DMA map, error %d\n", error);
-		goto unmap;
-	}
-	if ((error = bus_dmamap_load(dev->pa.pa_dmat, h->map, h->addr, size,
-	     NULL, BUS_DMA_NOWAIT)) != 0) {
-		printf("drm: Unable to load DMA map, error %d\n", error);
-		goto destroy;
-	}
-	h->busaddr = DRM_PCI_DMAADDR(h);
-	h->vaddr = h->addr;
-	h->size = size;
-
-	return h;
 
-destroy:
-	bus_dmamap_destroy(dev->pa.pa_dmat, h->map);
-unmap:
-	bus_dmamem_unmap(dev->pa.pa_dmat, h->addr, size);
-free:
-	bus_dmamem_free(dev->pa.pa_dmat, h->segs, 1);
-fail:
+	h->mem = drm_dmamem_pgalloc(dev, round_page(btop(size)));
+	if (h->mem == NULL) {
 	free(h, M_DRM);
 	return NULL;
+	}
+
+	h->busaddr = DRM_DMA_BUSADDR(h->mem);
+	h->vaddr = DRM_DMA_KERNADDR(h->mem);
+
+	return h;
 	
 }
 
@@ -96,10 +63,7 @@
 {
 	if (h == NULL)
 		return;
-	bus_dmamap_unload(dev->pa.pa_dmat, h->map);
-	bus_dmamap_destroy(dev->pa.pa_dmat, h->map);
-	bus_dmamem_unmap(dev->pa.pa_dmat, h->addr, h->size);
-	bus_dmamem_free(dev->pa.pa_dmat, h->segs, 1);
 
+	drm_dmamem_free(h->mem);
 	free(h, M_DRM);
 }
Index: dev/drm/drm_scatter.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_scatter.c,v
retrieving revision 1.7
diff -u -b -r1.7 drm_scatter.c
--- dev/drm/drm_scatter.c	7 Jul 2008 00:33:23 -0000	1.7
+++ dev/drm/drm_scatter.c	10 Aug 2008 00:57:11 -0000
@@ -43,7 +43,11 @@
 
 void drm_sg_cleanup(drm_sg_mem_t *entry)
 {
-	free((void *)entry->handle, M_DRM);
+	if (entry == NULL)
+		return;
+	if (entry->mem != NULL)
+		drm_dmamem_free(entry->mem);
+	if (entry->busaddr != NULL)
 	free(entry->busaddr, M_DRM);
 	free(entry, M_DRM);
 }
@@ -80,17 +84,23 @@
 		return ENOMEM;
 	}
 
-	entry->handle = (long)malloc(pages << PAGE_SHIFT, M_DRM,
-	    M_WAITOK | M_ZERO);
-	if (entry->handle == 0) {
+	if ((entry->mem = drm_dmamem_pgalloc(dev, pages)) == NULL) {
 		drm_sg_cleanup(entry);
 		return ENOMEM;
 	}
 
-	for (i = 0; i < pages; i++) {
-		entry->busaddr[i] = vtophys(entry->handle + i * PAGE_SIZE);
+	entry->handle = (unsigned long)entry->mem->dd_kva;
+
+	if (pages != entry->mem->dd_dmam->dm_nsegs) {
+		DRM_DEBUG("pages (%ld) != nsegs (%i)\n", pages,
+			entry->mem->dd_dmam->dm_nsegs);
+		drm_sg_cleanup(entry);
+		return ENOMEM;
 	}
 
+	for (i = 0; i < pages; i++) 
+		entry->busaddr[i] = entry->mem->dd_dmam->dm_segs[i].ds_addr;
+
 	DRM_DEBUG( "sg alloc handle  = %08lx\n", entry->handle );
 
 	entry->virtual = (void *)entry->handle;
@@ -112,20 +122,21 @@
 	return 0;
 }
 
-int drm_sg_free(DRM_IOCTL_ARGS)
+int
+drm_sg_free(DRM_IOCTL_ARGS)
 {
 	DRM_DEVICE;
 	drm_scatter_gather_t request;
 	drm_sg_mem_t *entry;
 
-	DRM_COPY_FROM_USER_IOCTL( request, (drm_scatter_gather_t *)data,
-			     sizeof(request) );
-
 	DRM_LOCK();
 	entry = dev->sg;
 	dev->sg = NULL;
 	DRM_UNLOCK();
 
+	DRM_COPY_FROM_USER_IOCTL( request, (drm_scatter_gather_t *)data,
+			     sizeof(request) );
+
 	if ( !entry || entry->handle != request.handle )
 		return EINVAL;
 
Index: dev/drm/drm_vm.c
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/drm_vm.c,v
retrieving revision 1.15
diff -u -b -r1.15 drm_vm.c
--- dev/drm/drm_vm.c	29 Jun 2008 12:49:08 -0000	1.15
+++ dev/drm/drm_vm.c	10 Aug 2008 00:57:11 -0000
@@ -41,7 +41,6 @@
 	drm_file_t *priv;
 	drm_map_type_t type;
 	paddr_t phys;
-	uintptr_t roffset;
 
 	DRM_LOCK();
 	priv = drm_find_file_by_proc(dev, DRM_CURPROC);
@@ -83,13 +82,10 @@
 				   for performance, even if the list was a
 				   bit longer. */
 	DRM_LOCK();
-	roffset = DRM_NETBSD_HANDLE2ADDR(offset);
 	TAILQ_FOREACH(map, &dev->maplist, link) {
-		if (map->type == _DRM_SHM) {
-			if (roffset >= (uintptr_t)map->handle && roffset < (uintptr_t)map->handle + map->size)
-				break;
-		} else {
-			if (offset >= map->offset && offset < map->offset + map->size)
+			if ((offset >= map->cookie) && 
+		    	    (offset < map->cookie + map->size)) {
+				offset -= map->cookie;
 				break;
 		}
 	}
@@ -111,16 +107,22 @@
 	case _DRM_FRAME_BUFFER:
 	case _DRM_REGISTERS:
 	case _DRM_AGP:
-		phys = offset;
+		phys = offset + map->offset;
 		break;
+	/* All _DRM_CONSISTENT and _DRM_SHM mappings have a 0 offset */
 	case _DRM_CONSISTENT:
-		phys = vtophys((paddr_t)map->handle + (offset - map->offset));
+		return bus_dmamem_mmap(dev->pa.pa_dmat, map->dmah->mem->dd_segs,
+			map->dmah->mem->dd_nsegs, 0, prot, BUS_DMA_NOWAIT|
+			BUS_DMA_NOCACHE);
+	case _DRM_SHM:
+		return bus_dmamem_mmap(dev->pa.pa_dmat, map->mem->dd_segs,
+			map->mem->dd_nsegs, 0, prot, BUS_DMA_NOWAIT);
 		break;
 	case _DRM_SCATTER_GATHER:
-		phys = vtophys(offset);
-		break;
-	case _DRM_SHM:
-		phys = vtophys(DRM_NETBSD_HANDLE2ADDR(offset));
+		return bus_dmamem_mmap(dev->pa.pa_dmat, 
+			dev->sg->mem->dd_segs, dev->sg->mem->dd_nsegs, 
+			map->offset - dev->sg->handle + offset, prot,
+			BUS_DMA_NOWAIT|BUS_DMA_NOCACHE);
 		break;
 	default:
 		DRM_ERROR("bad map type %d\n", type);
@@ -133,4 +135,3 @@
 	return atop(phys);
 #endif
 }
-
Index: dev/drm/files.drm
===================================================================
RCS file: /cvsroot/src/sys/dev/drm/files.drm,v
retrieving revision 1.6
diff -u -b -r1.6 files.drm
--- dev/drm/files.drm	19 Jul 2008 07:26:54 -0000	1.6
+++ dev/drm/files.drm	10 Aug 2008 00:57:11 -0000
@@ -15,6 +15,7 @@
 file   dev/drm/drm_irq.c           drmbase & !drm_external
 file   dev/drm/drm_lock.c          drmbase & !drm_external
 file   dev/drm/drm_memory.c        drmbase & !drm_external
+file   dev/drm/drm_netbsd.c	   drmbase & !drm_external
 file   dev/drm/drm_pci.c           drmbase & !drm_external
 file   dev/drm/drm_scatter.c       drmbase & !drm_external
 file   dev/drm/drm_sysctl.c        drmbase & !drm_external
@@ -32,6 +33,7 @@
 file   external/bsd/drm/dist/bsd-core/drm_irq.c           drmbase & drm_external
 file   external/bsd/drm/dist/bsd-core/drm_lock.c          drmbase & drm_external
 file   external/bsd/drm/dist/bsd-core/drm_memory.c        drmbase & drm_external
+file   external/bsd/drm/dist/bsd-core/drm_netbsd.c        drmbase & drm_external
 file   external/bsd/drm/dist/bsd-core/drm_pci.c           drmbase & drm_external
 file   external/bsd/drm/dist/bsd-core/drm_scatter.c       drmbase & drm_external
 file   external/bsd/drm/dist/bsd-core/drm_sysctl.c        drmbase & drm_external
Index: dev/pci/drm/i915_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/i915_irq.c,v
retrieving revision 1.7
diff -u -b -r1.7 i915_irq.c
--- dev/pci/drm/i915_irq.c	8 Jul 2008 06:50:22 -0000	1.7
+++ dev/pci/drm/i915_irq.c	10 Aug 2008 00:57:11 -0000
@@ -67,11 +67,11 @@
 	dev_priv->sarea_priv->last_dispatch = READ_BREADCRUMB(dev_priv);
 
 	if (temp & USER_INT_FLAG)
-		DRM_WAKEUP(&dev_priv->irq_queue);
+		DRM_WAKEUP(&(dev_priv->irq_queue));
 
 	if (temp & (VSYNC_PIPEA_FLAG | VSYNC_PIPEB_FLAG)) {
 		atomic_inc(&dev->vbl_received);
-		DRM_WAKEUP(&dev->vbl_queue);
+		DRM_WAKEUP(&(dev->vbl_queue));
 		drm_vbl_send_signals(dev);
 	}
 
@@ -121,7 +121,7 @@
 
 	dev_priv->sarea_priv->perf_boxes |= I915_BOX_WAIT;
 
-	DRM_WAIT_ON(ret, dev_priv->irq_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev_priv->irq_queue), 3 * DRM_HZ,
 		    READ_BREADCRUMB(dev_priv) >= irq_nr);
 
 	if (ret == DRM_ERR(EBUSY)) {
@@ -145,7 +145,7 @@
 		return DRM_ERR(EINVAL);
 	}
 
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received))
 			- *sequence) <= (1<<23)));
 	
@@ -280,7 +280,7 @@
 	drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;
 
 	i915_enable_interrupt(dev);
-	DRM_INIT_WAITQUEUE(&dev_priv->irq_queue);
+	DRM_INIT_WAITQUEUE(&(dev_priv->irq_queue));
 }
 
 void i915_driver_irq_uninstall(drm_device_t * dev)
@@ -296,4 +296,5 @@
 
 	temp = I915_READ16(I915REG_INT_IDENTITY_R);
 	I915_WRITE16(I915REG_INT_IDENTITY_R, temp);
+	DRM_DESTROY_WAITQUEUE(&(dev_priv->irq_queue));
 }
Index: dev/pci/drm/mach64_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/mach64_irq.c,v
retrieving revision 1.6
diff -u -b -r1.6 mach64_irq.c
--- dev/pci/drm/mach64_irq.c	8 Jul 2008 06:50:23 -0000	1.6
+++ dev/pci/drm/mach64_irq.c	10 Aug 2008 00:57:11 -0000
@@ -71,7 +71,7 @@
 			     | MACH64_CRTC_VBLANK_INT);
 
 		atomic_inc(&dev->vbl_received);
-		DRM_WAKEUP(&dev->vbl_queue);
+		DRM_WAKEUP(&(dev->vbl_queue));
 		drm_vbl_send_signals(dev);
 		return IRQ_HANDLED;
 	}
@@ -87,7 +87,7 @@
 	 * by about a day rather than she wants to wait for years
 	 * using vertical blanks...
 	 */
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received))
 		      - *sequence) <= (1 << 23)));
 
Index: dev/pci/drm/mga_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/mga_irq.c,v
retrieving revision 1.6
diff -u -b -r1.6 mga_irq.c
--- dev/pci/drm/mga_irq.c	8 Jul 2008 06:50:23 -0000	1.6
+++ dev/pci/drm/mga_irq.c	10 Aug 2008 00:57:11 -0000
@@ -57,7 +57,7 @@
 	if (status & MGA_VLINEPEN) {
 		MGA_WRITE(MGA_ICLEAR, MGA_VLINEICLR);
 		atomic_inc(&dev->vbl_received);
-		DRM_WAKEUP(&dev->vbl_queue);
+		DRM_WAKEUP(&(dev->vbl_queue));
 		drm_vbl_send_signals(dev);
 		handled = 1;
 	}
@@ -78,7 +78,7 @@
 		}
 
 		atomic_inc(&dev_priv->last_fence_retired);
-		DRM_WAKEUP(&dev_priv->fence_queue);
+		DRM_WAKEUP(&(dev_priv->fence_queue));
 		handled = 1;
 	}
 
@@ -97,7 +97,7 @@
 	 * by about a day rather than she wants to wait for years
 	 * using vertical blanks...
 	 */
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received))
 		      - *sequence) <= (1 << 23)));
 
@@ -116,7 +116,7 @@
 	 * by about a day rather than she wants to wait for years
 	 * using fences.
 	 */
-	DRM_WAIT_ON(ret, dev_priv->fence_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev_priv->fence_queue), 3 * DRM_HZ,
 		    (((cur_fence = atomic_read(&dev_priv->last_fence_retired))
 		      - *sequence) <= (1 << 23)));
 
@@ -139,7 +139,7 @@
 {
 	drm_mga_private_t *dev_priv = (drm_mga_private_t *) dev->dev_private;
 
-	DRM_INIT_WAITQUEUE( &dev_priv->fence_queue );
+	DRM_INIT_WAITQUEUE( &(dev_priv->fence_queue) );
 
 	/* Turn on vertical blank interrupt and soft trap interrupt. */
 	MGA_WRITE(MGA_IEN, MGA_VLINEIEN | MGA_SOFTRAPEN);
@@ -153,6 +153,7 @@
 
 	/* Disable *all* interrupts */
 	MGA_WRITE(MGA_IEN, 0);
+	DRM_DESTROY_WAITQUEUE(&(dev_priv->fence_queue));
 	
 	dev->irq_enabled = 0;
 }
Index: dev/pci/drm/r128_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/r128_irq.c,v
retrieving revision 1.6
diff -u -b -r1.6 r128_irq.c
--- dev/pci/drm/r128_irq.c	8 Jul 2008 06:50:23 -0000	1.6
+++ dev/pci/drm/r128_irq.c	10 Aug 2008 00:57:11 -0000
@@ -72,7 +72,7 @@
 	 * by about a day rather than she wants to wait for years
 	 * using vertical blanks...
 	 */
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received))
 		      - *sequence) <= (1 << 23)));
 
Index: dev/pci/drm/radeon_cp.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/radeon_cp.c,v
retrieving revision 1.10
diff -u -b -r1.10 radeon_cp.c
--- dev/pci/drm/radeon_cp.c	8 Jul 2008 06:50:23 -0000	1.10
+++ dev/pci/drm/radeon_cp.c	10 Aug 2008 00:57:12 -0000
@@ -1944,8 +1944,8 @@
 				msleep(&ret, &dev->dev_lock, PZERO, "rdnrel",
 				       1);
 #else
-				mtsleep(&ret, PZERO, "rdnrel", 1,
-					&dev->dev_lock);
+				ret = cv_timedwait(&(dev->lock.lock_cv), 
+					&(dev->lock.lock_mutex), 1);
 #endif
 #endif
 			}
Index: dev/pci/drm/radeon_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/radeon_irq.c,v
retrieving revision 1.8
diff -u -b -r1.8 radeon_irq.c
--- dev/pci/drm/radeon_irq.c	8 Jul 2008 06:50:23 -0000	1.8
+++ dev/pci/drm/radeon_irq.c	10 Aug 2008 00:57:12 -0000
@@ -87,13 +87,13 @@
 
 	/* SW interrupt */
 	if (stat & RADEON_SW_INT_TEST) {
-		DRM_WAKEUP(&dev_priv->swi_queue);
+		DRM_WAKEUP(&(dev_priv->swi_queue));
 	}
 
 	/* VBLANK interrupt */
 	if (stat & RADEON_CRTC_VBLANK_STAT) {
 		atomic_inc(&dev->vbl_received);
-		DRM_WAKEUP(&dev->vbl_queue);
+		DRM_WAKEUP(&(dev->vbl_queue));
 		drm_vbl_send_signals(dev);
 	}
 
@@ -129,7 +129,7 @@
 
 	dev_priv->stats.boxes |= RADEON_BOX_WAIT_IDLE;
 
-	DRM_WAIT_ON(ret, dev_priv->swi_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev_priv->swi_queue), 3 * DRM_HZ,
 		    RADEON_READ(RADEON_LAST_SWI_REG) >= swi_nr);
 
 	return ret;
@@ -155,7 +155,7 @@
 	 * by about a day rather than she wants to wait for years
 	 * using vertical blanks...
 	 */
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received))
 		      - *sequence) <= (1 << 23)));
 
@@ -233,7 +233,7 @@
 	    (drm_radeon_private_t *) dev->dev_private;
 
 	atomic_set(&dev_priv->swi_emitted, 0);
-	DRM_INIT_WAITQUEUE(&dev_priv->swi_queue);
+	DRM_INIT_WAITQUEUE(&(dev_priv->swi_queue));
 
 	/* Turn on SW and VBL ints */
 	RADEON_WRITE(RADEON_GEN_INT_CNTL,
@@ -249,4 +249,5 @@
 
 	/* Disable *all* interrupts */
 	RADEON_WRITE(RADEON_GEN_INT_CNTL, 0);
+	DRM_DESTROY_WAITQUEUE(&(dev_priv->swi_queue));
 }
Index: dev/pci/drm/via_irq.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/via_irq.c,v
retrieving revision 1.7
diff -u -b -r1.7 via_irq.c
--- dev/pci/drm/via_irq.c	8 Jul 2008 06:50:23 -0000	1.7
+++ dev/pci/drm/via_irq.c	10 Aug 2008 00:57:12 -0000
@@ -142,7 +142,7 @@
 	for (i=0; i<dev_priv->num_irqs; ++i) {
 		if (status & cur_irq->pending_mask) {
 			atomic_inc( &cur_irq->irq_received );
-			DRM_WAKEUP( &cur_irq->irq_queue );
+			DRM_WAKEUP( &(cur_irq->irq_queue) );
 			handled = 1;
 #ifdef VIA_HAVE_DMABLIT
 			if (dev_priv->irq_map[drm_via_irq_dma0_td] == i) {
@@ -196,7 +196,7 @@
 	 * using vertical blanks...
 	 */
 
-	DRM_WAIT_ON(ret, dev->vbl_queue, 3 * DRM_HZ,
+	DRM_WAIT_ON(ret, &(dev->vbl_queue), 3 * DRM_HZ,
 		    (((cur_vblank = atomic_read(&dev->vbl_received)) -
 		      *sequence) <= (1 << 23)));
 	
@@ -240,12 +240,12 @@
 	cur_irq = dev_priv->via_irqs + real_irq;
 
 	if (masks[real_irq][2] && !force_sequence) {
-		DRM_WAIT_ON(ret, cur_irq->irq_queue, 3 * DRM_HZ,
+		DRM_WAIT_ON(ret, &(cur_irq->irq_queue), 3 * DRM_HZ,
 			    ((VIA_READ(masks[irq][2]) & masks[irq][3]) == 
 			     masks[irq][4]));
 		cur_irq_sequence = atomic_read(&cur_irq->irq_received);
 	} else {
-		DRM_WAIT_ON(ret, cur_irq->irq_queue, 3 * DRM_HZ,
+		DRM_WAIT_ON(ret, &(cur_irq->irq_queue), 3 * DRM_HZ,
 			    (((cur_irq_sequence =
 			       atomic_read(&cur_irq->irq_received)) -
 			      *sequence) <= (1 << 23)));		
@@ -288,7 +288,7 @@
 			atomic_set(&cur_irq->irq_received, 0);
 			cur_irq->enable_mask = dev_priv->irq_masks[i][0]; 
 			cur_irq->pending_mask = dev_priv->irq_masks[i][1];
-			DRM_INIT_WAITQUEUE( &cur_irq->irq_queue );
+			DRM_INIT_WAITQUEUE( &(cur_irq->irq_queue) );
 			dev_priv->irq_enable_mask |= cur_irq->enable_mask;
 			dev_priv->irq_pending_mask |= cur_irq->pending_mask;
 			cur_irq++;
@@ -330,7 +330,9 @@
 void via_driver_irq_uninstall(drm_device_t * dev)
 {
 	drm_via_private_t *dev_priv = (drm_via_private_t *) dev->dev_private;
+	drm_via_irq_t *cur_irq;
 	u32 status;
+	int i;
 
 	DRM_DEBUG("driver_irq_uninstall)\n");
 	if (dev_priv) {
@@ -343,6 +345,12 @@
 		status = VIA_READ(VIA_REG_INTERRUPT);
 		VIA_WRITE(VIA_REG_INTERRUPT, status & 
 			  ~(VIA_IRQ_VBLANK_ENABLE | dev_priv->irq_enable_mask));
+		cur_irq = dev_priv->via_irqs;
+ 		for(i = 0; i < dev_priv->num_irqs; ++i) {
+			DRM_DESTROY_WAITQUEUE(&(cur_irq->irq_queue));
+			cur_irq++;
+		}
+
 	}
 }
 
Index: dev/pci/drm/via_video.c
===================================================================
RCS file: /cvsroot/src/sys/dev/pci/drm/via_video.c,v
retrieving revision 1.7
diff -u -b -r1.7 via_video.c
--- dev/pci/drm/via_video.c	8 Jul 2008 06:50:23 -0000	1.7
+++ dev/pci/drm/via_video.c	10 Aug 2008 00:57:12 -0000
@@ -67,6 +67,7 @@
 			}
 			*lock = 0;
 		}
+		DRM_DESTROY_WAITQUEUE(&(dev_priv->decoder_queue[i]));
 	}
 }
 
@@ -91,7 +92,7 @@
 
 	switch (fx.func) {
 	case VIA_FUTEX_WAIT:
-		DRM_WAIT_ON(ret, dev_priv->decoder_queue[fx.lock],
+		DRM_WAIT_ON(ret, &(dev_priv->decoder_queue[fx.lock]),
 			    (fx.ms / 10) * (DRM_HZ / 100), *lock != fx.val);
 		return ret;
 	case VIA_FUTEX_WAKE:
