return 0;
}
- static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
+
+ #define DRI2_SAREA_BLOCK_TYPE(b) ((b) >> 16)
+ #define DRI2_SAREA_BLOCK_SIZE(b) ((b) & 0xffff)
+ #define DRI2_SAREA_BLOCK_NEXT(p) \
+ ((void *) ((unsigned char *) (p) + \
+ DRI2_SAREA_BLOCK_SIZE(*(unsigned int *) p)))
+
+ #define DRI2_SAREA_BLOCK_END 0x0000
+ #define DRI2_SAREA_BLOCK_LOCK 0x0001
+ #define DRI2_SAREA_BLOCK_EVENT_BUFFER 0x0002
+
+ static int
+ setup_dri2_sarea(struct drm_device * dev,
+ struct drm_file *file_priv,
+ drm_i915_init_t * init)
+ {
+ drm_i915_private_t *dev_priv = dev->dev_private;
+ int ret;
+ unsigned int *p, *end, *next;
+
+ mutex_lock(&dev->struct_mutex);
+ dev_priv->sarea_bo =
+ drm_lookup_buffer_object(file_priv,
+ init->sarea_handle, 1);
+ mutex_unlock(&dev->struct_mutex);
+
+ if (!dev_priv->sarea_bo) {
+ DRM_ERROR("did not find sarea bo\n");
+ return -EINVAL;
+ }
+
+ ret = drm_bo_kmap(dev_priv->sarea_bo, 0,
+ dev_priv->sarea_bo->num_pages,
+ &dev_priv->sarea_kmap);
+ if (ret) {
+ DRM_ERROR("could not map sarea bo\n");
+ return ret;
+ }
+
+ p = dev_priv->sarea_kmap.virtual;
+ end = (void *) p + (dev_priv->sarea_bo->num_pages << PAGE_SHIFT);
+ while (p < end && DRI2_SAREA_BLOCK_TYPE(*p) != DRI2_SAREA_BLOCK_END) {
+ switch (DRI2_SAREA_BLOCK_TYPE(*p)) {
+ case DRI2_SAREA_BLOCK_LOCK:
+ dev->lock.hw_lock = (void *) (p + 1);
+ dev->sigdata.lock = dev->lock.hw_lock;
+ break;
+ }
+ next = DRI2_SAREA_BLOCK_NEXT(p);
+ if (next <= p || end < next) {
+ DRM_ERROR("malformed dri2 sarea: next is %p should be within %p-%p\n",
+ next, p, end);
+ return -EINVAL;
+ }
+ p = next;
+ }
+
+ return 0;
+ }
+
+
+ static int i915_initialize(struct drm_device * dev,
+ struct drm_file *file_priv,
+ drm_i915_init_t * init)
{
- drm_i915_private_t *dev_priv = dev->dev_private;
- int ret;
-
- dev_priv->sarea = drm_getsarea(dev);
- if (!dev_priv->sarea) {
- DRM_ERROR("can not find sarea!\n");
- i915_dma_cleanup(dev);
- return -EINVAL;
- }
-
- if (init->mmio_offset != 0)
- dev_priv->mmio_map = drm_core_findmap(dev, init->mmio_offset);
+ struct drm_i915_private *dev_priv = dev->dev_private;
+ struct drm_i915_master_private *master_priv = dev->primary->master->driver_priv;
+ dev_priv->mmio_map = drm_core_findmap(dev, init->mmio_offset);
if (!dev_priv->mmio_map) {
i915_dma_cleanup(dev);
DRM_ERROR("can not find mmio map!\n");
return 0;
}
-int i915_driver_load(struct drm_device *dev, unsigned long flags)
-{
- struct drm_i915_private *dev_priv = dev->dev_private;
- unsigned long base, size;
- int ret = 0, mmio_bar = IS_I9XX(dev) ? 0 : 1;
-
- /* i915 has 4 more counters */
- dev->counters += 4;
- dev->types[6] = _DRM_STAT_IRQ;
- dev->types[7] = _DRM_STAT_PRIMARY;
- dev->types[8] = _DRM_STAT_SECONDARY;
- dev->types[9] = _DRM_STAT_DMA;
-
- dev_priv = drm_alloc(sizeof(drm_i915_private_t), DRM_MEM_DRIVER);
- if (dev_priv == NULL)
- return -ENOMEM;
-
- memset(dev_priv, 0, sizeof(drm_i915_private_t));
-
- dev->dev_private = (void *)dev_priv;
-
- /* Add register map (needed for suspend/resume) */
- base = drm_get_resource_start(dev, mmio_bar);
- size = drm_get_resource_len(dev, mmio_bar);
-
- ret = drm_addmap(dev, base, size, _DRM_REGISTERS,
- _DRM_KERNEL | _DRM_DRIVER, &dev_priv->mmio_map);
-
-#ifdef __linux__
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,25)
- intel_init_chipset_flush_compat(dev);
-#endif
-#endif
-
- return ret;
-}
-
-int i915_driver_unload(struct drm_device *dev)
-{
- struct drm_i915_private *dev_priv = dev->dev_private;
-
- if (dev_priv->mmio_map)
- drm_rmmap(dev, dev_priv->mmio_map);
-
- drm_free(dev->dev_private, sizeof(drm_i915_private_t),
- DRM_MEM_DRIVER);
-#ifdef __linux__
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,25)
- intel_fini_chipset_flush_compat(dev);
-#endif
-#endif
- return 0;
-}
-
++#if 0 /* FIXME DRI2 */
+ void i915_driver_lastclose(struct drm_device * dev)
+ {
+ drm_i915_private_t *dev_priv = dev->dev_private;
+
+ if (drm_getsarea(dev) && dev_priv->sarea_priv)
+ i915_do_cleanup_pageflip(dev);
+ if (dev_priv->agp_heap)
+ i915_mem_takedown(&(dev_priv->agp_heap));
+
+ if (dev_priv->sarea_kmap.virtual) {
+ drm_bo_kunmap(&dev_priv->sarea_kmap);
+ dev_priv->sarea_kmap.virtual = NULL;
+ dev->lock.hw_lock = NULL;
+ dev->sigdata.lock = NULL;
+ }
+
+ if (dev_priv->sarea_bo) {
+ mutex_lock(&dev->struct_mutex);
+ drm_bo_usage_deref_locked(&dev_priv->sarea_bo);
+ mutex_unlock(&dev->struct_mutex);
+ dev_priv->sarea_bo = NULL;
+ }
+
+ i915_dma_cleanup(dev);
+ }
-
-void i915_driver_preclose(struct drm_device * dev, struct drm_file *file_priv)
-{
- drm_i915_private_t *dev_priv = dev->dev_private;
- i915_mem_release(dev, file_priv, dev_priv->agp_heap);
-}
++#endif
+
struct drm_ioctl_desc i915_ioctls[] = {
DRM_IOCTL_DEF(DRM_I915_INIT, i915_dma_init, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
DRM_IOCTL_DEF(DRM_I915_FLUSH, i915_flush_ioctl, DRM_AUTH),