From 270cffbe43955033a54dd54695ca1108194e087e Mon Sep 17 00:00:00 2001
From: Alan Hourihane <alanh@fairlite.demon.co.uk>
Date: Mon, 23 Jan 2006 10:05:22 +0000
Subject: Fix CMDBUFFER path, add heap destroy and flesh out sarea for rotation
     (Tungsten Graphics)

---
 shared-core/i915_dma.c | 47 ++++++++++++++++++++++++++++++-----------------
 shared-core/i915_drm.h | 35 ++++++++++++++++++++++++++++++++++-
 shared-core/i915_drv.h |  6 ++++--
 shared-core/i915_mem.c | 30 ++++++++++++++++++++++++++++++
 4 files changed, 98 insertions(+), 20 deletions(-)

(limited to 'shared-core')

diff --git a/shared-core/i915_dma.c b/shared-core/i915_dma.c
index 3d2eae2b..5418819a 100644
--- a/shared-core/i915_dma.c
+++ b/shared-core/i915_dma.c
@@ -344,18 +344,20 @@ static int i915_emit_cmds(drm_device_t * dev, int __user * buffer, int dwords)
 	int i;
 	RING_LOCALS;
 
+	if ((dwords+1) * sizeof(int) >= dev_priv->ring.Size - 8)
+		return DRM_ERR(EINVAL);
+
+	BEGIN_LP_RING(((dwords+1)&~1));
+
 	for (i = 0; i < dwords;) {
 		int cmd, sz;
 
 		if (DRM_COPY_FROM_USER_UNCHECKED(&cmd, &buffer[i], sizeof(cmd)))
 			return DRM_ERR(EINVAL);
 
-/* 		printk("%d/%d ", i, dwords); */
-
 		if ((sz = validate_cmd(cmd)) == 0 || i + sz > dwords)
 			return DRM_ERR(EINVAL);
 
-		BEGIN_LP_RING(sz);
 		OUT_RING(cmd);
 
 		while (++i, --sz) {
@@ -365,9 +367,13 @@ static int i915_emit_cmds(drm_device_t * dev, int __user * buffer, int dwords)
 			}
 			OUT_RING(cmd);
 		}
-		ADVANCE_LP_RING();
 	}
+		
+	if (dwords & 1)
+		OUT_RING(0);
 
+	ADVANCE_LP_RING();
+		
 	return 0;
 }
 
@@ -401,6 +407,22 @@ static int i915_emit_box(drm_device_t * dev,
 	return 0;
 }
 
+
+static void i915_emit_breadcrumb(drm_device_t *dev)
+{
+	drm_i915_private_t *dev_priv = dev->dev_private;
+	RING_LOCALS;
+
+	dev_priv->sarea_priv->last_enqueue = dev_priv->counter++;
+
+	BEGIN_LP_RING(4);
+	OUT_RING(CMD_STORE_DWORD_IDX);
+	OUT_RING(20);
+	OUT_RING(dev_priv->counter);
+	OUT_RING(0);
+	ADVANCE_LP_RING();
+}
+
 static int i915_dispatch_cmdbuffer(drm_device_t * dev,
 				   drm_i915_cmdbuffer_t * cmd)
 {
@@ -429,6 +451,7 @@ static int i915_dispatch_cmdbuffer(drm_device_t * dev,
 			return ret;
 	}
 
+	i915_emit_breadcrumb( dev );
 	return 0;
 }
 
@@ -473,15 +496,7 @@ static int i915_dispatch_batchbuffer(drm_device_t * dev,
 		}
 	}
 
-	dev_priv->sarea_priv->last_enqueue = dev_priv->counter++;
-
-	BEGIN_LP_RING(4);
-	OUT_RING(CMD_STORE_DWORD_IDX);
-	OUT_RING(20);
-	OUT_RING(dev_priv->counter);
-	OUT_RING(0);
-	ADVANCE_LP_RING();
-
+	i915_emit_breadcrumb( dev );
 	return 0;
 }
 
@@ -664,9 +679,6 @@ static int i915_getparam(DRM_IOCTL_ARGS)
 	case I915_PARAM_ALLOW_BATCHBUFFER:
 		value = dev_priv->allow_batchbuffer ? 1 : 0;
 		break;
-	case I915_PARAM_LAST_DISPATCH:
-		value = READ_BREADCRUMB(dev_priv);
-		break;
 	default:
 		DRM_ERROR("Unkown parameter %d\n", param.param);
 		return DRM_ERR(EINVAL);
@@ -756,7 +768,8 @@ drm_ioctl_desc_t i915_ioctls[] = {
 	[DRM_IOCTL_NR(DRM_I915_ALLOC)] = {i915_mem_alloc, DRM_AUTH},
 	[DRM_IOCTL_NR(DRM_I915_FREE)] = {i915_mem_free, DRM_AUTH},
 	[DRM_IOCTL_NR(DRM_I915_INIT_HEAP)] = {i915_mem_init_heap, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
-	[DRM_IOCTL_NR(DRM_I915_CMDBUFFER)] = {i915_cmdbuffer, DRM_AUTH}
+	[DRM_IOCTL_NR(DRM_I915_CMDBUFFER)] = {i915_cmdbuffer, DRM_AUTH},
+	[DRM_IOCTL_NR(DRM_I915_DESTROY_HEAP)] = { i915_mem_destroy_heap, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY }
 };
 
 int i915_max_ioctl = DRM_ARRAY_SIZE(i915_ioctls);
diff --git a/shared-core/i915_drm.h b/shared-core/i915_drm.h
index 0e718aec..c70d1c45 100644
--- a/shared-core/i915_drm.h
+++ b/shared-core/i915_drm.h
@@ -74,6 +74,30 @@ typedef struct _drm_i915_sarea {
 	int pf_active;
 	int pf_current_page;	/* which buffer is being displayed? */
 	int perf_boxes;		/* performance boxes to be displayed */
+	int width, height;      /* screen size in pixels */
+
+	drm_handle_t front_handle;
+	int front_offset;
+	int front_size;
+
+	drm_handle_t back_handle;
+	int back_offset;
+	int back_size;
+
+	drm_handle_t depth_handle;
+	int depth_offset;
+	int depth_size;
+
+	drm_handle_t tex_handle;
+	int tex_offset;
+	int tex_size;
+	int log_tex_granularity;
+	int pitch;
+	int rotation;           /* 0, 90, 180 or 270 */
+	int rotated_offset;
+	int rotated_size;
+	int rotated_pitch;
+        int virtualX, virtualY;
 } drm_i915_sarea_t;
 
 /* Flags for perf_boxes
@@ -99,6 +123,7 @@ typedef struct _drm_i915_sarea {
 #define DRM_I915_FREE		0x09
 #define DRM_I915_INIT_HEAP	0x0a
 #define DRM_I915_CMDBUFFER	0x0b
+#define DRM_I915_DESTROY_HEAP	0x0c
 
 #define DRM_IOCTL_I915_INIT		DRM_IOW( DRM_COMMAND_BASE + DRM_I915_INIT, drm_i915_init_t)
 #define DRM_IOCTL_I915_FLUSH		DRM_IO ( DRM_COMMAND_BASE + DRM_I915_FLUSH)
@@ -112,6 +137,8 @@ typedef struct _drm_i915_sarea {
 #define DRM_IOCTL_I915_FREE             DRM_IOW( DRM_COMMAND_BASE + DRM_I915_FREE, drm_i915_mem_free_t)
 #define DRM_IOCTL_I915_INIT_HEAP        DRM_IOW( DRM_COMMAND_BASE + DRM_I915_INIT_HEAP, drm_i915_mem_init_heap_t)
 #define DRM_IOCTL_I915_CMDBUFFER	DRM_IOW( DRM_COMMAND_BASE + DRM_I915_CMDBUFFER, drm_i915_cmdbuffer_t)
+#define DRM_IOCTL_I915_DESTROY_HEAP	DRM_IOW( DRM_COMMAND_BASE + DRM_I915_DESTROY_HEAP, drm_i915_mem_destroy_heap_t)
+
 
 /* Allow drivers to submit batchbuffers directly to hardware, relying
  * on the security mechanisms provided by hardware.
@@ -151,7 +178,6 @@ typedef struct drm_i915_irq_wait {
  */
 #define I915_PARAM_IRQ_ACTIVE            1
 #define I915_PARAM_ALLOW_BATCHBUFFER     2
-#define I915_PARAM_LAST_DISPATCH         3
 
 typedef struct drm_i915_getparam {
 	int param;
@@ -191,4 +217,11 @@ typedef struct drm_i915_mem_init_heap {
 	int start;
 } drm_i915_mem_init_heap_t;
 
+/* Allow memory manager to be torn down and re-initialized (eg on
+ * rotate):
+ */
+typedef struct drm_i915_mem_destroy_heap {
+	        int region;
+} drm_i915_mem_destroy_heap_t;
+
 #endif				/* _I915_DRM_H_ */
diff --git a/shared-core/i915_drv.h b/shared-core/i915_drv.h
index e5bda46d..cb86932a 100644
--- a/shared-core/i915_drv.h
+++ b/shared-core/i915_drv.h
@@ -37,16 +37,17 @@
 
 #define DRIVER_NAME		"i915"
 #define DRIVER_DESC		"Intel Graphics"
-#define DRIVER_DATE		"20051209"
+#define DRIVER_DATE		"20060119"
 
 /* Interface history:
  *
  * 1.1: Original.
  * 1.2: Add Power Management
  * 1.3: Add vblank support
+ * 1.4: Fix cmdbuffer path, add heap destroy
  */
 #define DRIVER_MAJOR		1
-#define DRIVER_MINOR		3
+#define DRIVER_MINOR		4
 #define DRIVER_PATCHLEVEL	0
 
 typedef struct _drm_i915_ring_buffer {
@@ -123,6 +124,7 @@ extern void i915_driver_irq_uninstall(drm_device_t * dev);
 extern int i915_mem_alloc(DRM_IOCTL_ARGS);
 extern int i915_mem_free(DRM_IOCTL_ARGS);
 extern int i915_mem_init_heap(DRM_IOCTL_ARGS);
+extern int i915_mem_destroy_heap(DRM_IOCTL_ARGS);
 extern void i915_mem_takedown(struct mem_block **heap);
 extern void i915_mem_release(drm_device_t * dev,
 			     DRMFILE filp, struct mem_block *heap);
diff --git a/shared-core/i915_mem.c b/shared-core/i915_mem.c
index ba87ff17..13f19f3a 100644
--- a/shared-core/i915_mem.c
+++ b/shared-core/i915_mem.c
@@ -365,3 +365,33 @@ int i915_mem_init_heap(DRM_IOCTL_ARGS)
 
 	return init_heap(heap, initheap.start, initheap.size);
 }
+
+int i915_mem_destroy_heap( DRM_IOCTL_ARGS )
+{
+	DRM_DEVICE;
+	drm_i915_private_t *dev_priv = dev->dev_private;
+	drm_i915_mem_destroy_heap_t destroyheap;
+	struct mem_block **heap;
+
+	if ( !dev_priv ) {
+		DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ );
+		return DRM_ERR(EINVAL);
+	}
+
+	DRM_COPY_FROM_USER_IOCTL( destroyheap, (drm_i915_mem_destroy_heap_t *)data,
+				  sizeof(destroyheap) );
+
+	heap = get_heap( dev_priv, destroyheap.region );
+	if (!heap) {
+		DRM_ERROR("get_heap failed");
+		return DRM_ERR(EFAULT);
+	}
+	
+	if (!*heap) {
+		DRM_ERROR("heap not initialized?");
+		return DRM_ERR(EFAULT);
+	}
+
+	i915_mem_takedown( heap );
+	return 0;
+}
-- 
cgit v1.2.3