From 52f9028c84baea81230dc673b756552e8e90aecd Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Thu, 5 Apr 2007 11:21:06 +1000 Subject: Initial import of modesetting for intel driver in DRM --- shared-core/i915_dma.c | 135 ++++++++++++++++++++++++++++++------------------- 1 file changed, 83 insertions(+), 52 deletions(-) (limited to 'shared-core/i915_dma.c') diff --git a/shared-core/i915_dma.c b/shared-core/i915_dma.c index aed3eea1..a5f1473a 100644 --- a/shared-core/i915_dma.c +++ b/shared-core/i915_dma.c @@ -31,13 +31,6 @@ #include "i915_drm.h" #include "i915_drv.h" -#define IS_I965G(dev) (dev->pci_device == 0x2972 || \ - dev->pci_device == 0x2982 || \ - dev->pci_device == 0x2992 || \ - dev->pci_device == 0x29A2 || \ - dev->pci_device == 0x2A02) - - /* Really want an OS-independent resettable timer. Would like to have * this loop run for (eg) 3 sec, but have the timer reset every time * the head pointer changes, so that EBUSY only happens if the ring @@ -87,6 +80,7 @@ void i915_kernel_lost_context(drm_device_t * dev) static int i915_dma_cleanup(drm_device_t * dev) { + drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; /* Make sure interrupts are disabled here because the uninstall ioctl * may not have been called from userspace and after dev_private * is freed, it's too late. @@ -94,25 +88,16 @@ static int i915_dma_cleanup(drm_device_t * dev) if (dev->irq) drm_irq_uninstall(dev); - if (dev->dev_private) { - drm_i915_private_t *dev_priv = - (drm_i915_private_t *) dev->dev_private; - - if (dev_priv->ring.virtual_start) { - drm_core_ioremapfree(&dev_priv->ring.map, dev); - } - - if (dev_priv->status_page_dmah) { - drm_pci_free(dev, dev_priv->status_page_dmah); - /* Need to rewrite hardware status page */ - I915_WRITE(0x02080, 0x1ffff000); - } - - drm_free(dev->dev_private, sizeof(drm_i915_private_t), - DRM_MEM_DRIVER); - - dev->dev_private = NULL; + if (dev_priv->status_page_dmah) { + drm_pci_free(dev, dev_priv->status_page_dmah); + dev_priv->status_page_dmah = NULL; + dev_priv->hw_status_page = NULL; + dev_priv->dma_status_page = 0; + /* Need to rewrite hardware status page */ + I915_WRITE(0x02080, 0x1ffff000); } + + dev_priv->sarea_priv = NULL; return 0; } @@ -121,8 +106,6 @@ static int i915_initialize(drm_device_t * dev, drm_i915_private_t * dev_priv, drm_i915_init_t * init) { - memset(dev_priv, 0, sizeof(drm_i915_private_t)); - DRM_GETSAREA(); if (!dev_priv->sarea) { DRM_ERROR("can not find sarea!\n"); @@ -131,14 +114,6 @@ static int i915_initialize(drm_device_t * dev, return DRM_ERR(EINVAL); } - dev_priv->mmio_map = drm_core_findmap(dev, init->mmio_offset); - if (!dev_priv->mmio_map) { - dev->dev_private = (void *)dev_priv; - i915_dma_cleanup(dev); - DRM_ERROR("can not find mmio map!\n"); - return DRM_ERR(EINVAL); - } - dev_priv->sarea_priv = (drm_i915_sarea_t *) ((u8 *) dev_priv->sarea->handle + init->sarea_priv_offset); @@ -195,7 +170,11 @@ static int i915_initialize(drm_device_t * dev, I915_WRITE(0x02080, dev_priv->dma_status_page); DRM_DEBUG("Enabled hardware status page\n"); - dev->dev_private = (void *)dev_priv; + + /* this probably doesn't belong here - TODO */ + drm_framebuffer_set_object(dev, dev_priv->sarea_priv->front_handle); + drm_set_desired_modes(dev); + return 0; } @@ -237,7 +216,7 @@ static int i915_dma_resume(drm_device_t * dev) static int i915_dma_init(DRM_IOCTL_ARGS) { DRM_DEVICE; - drm_i915_private_t *dev_priv; + drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; drm_i915_init_t init; int retcode = 0; @@ -246,10 +225,6 @@ static int i915_dma_init(DRM_IOCTL_ARGS) switch (init.func) { case I915_INIT_DMA: - dev_priv = drm_alloc(sizeof(drm_i915_private_t), - DRM_MEM_DRIVER); - if (dev_priv == NULL) - return DRM_ERR(ENOMEM); retcode = i915_initialize(dev, dev_priv, &init); break; case I915_CLEANUP_DMA: @@ -882,6 +857,18 @@ static int i915_mmio(DRM_IOCTL_ARGS) int i915_driver_load(drm_device_t *dev, unsigned long flags) { + drm_i915_private_t *dev_priv; + int ret; + unsigned long mmiobase, mmiolen; + + dev_priv = drm_alloc(sizeof(drm_i915_private_t), DRM_MEM_DRIVER); + if (dev_priv == NULL) + return DRM_ERR(ENOMEM); + + memset(dev_priv, 0, sizeof(drm_i915_private_t)); + dev->dev_private = (void *)dev_priv; +// dev_priv->flags = flags; + /* i915 has 4 more counters */ dev->counters += 4; dev->types[6] = _DRM_STAT_IRQ; @@ -889,25 +876,55 @@ int i915_driver_load(drm_device_t *dev, unsigned long flags) dev->types[8] = _DRM_STAT_SECONDARY; dev->types[9] = _DRM_STAT_DMA; + if (IS_I9XX(dev)) { + dev_priv->mmiobase = drm_get_resource_start(dev, 0); + dev_priv->mmiolen = drm_get_resource_len(dev, 0); + } else if (drm_get_resource_start(dev, 1)) { + dev_priv->mmiobase = drm_get_resource_start(dev, 1); + dev_priv->mmiolen = drm_get_resource_len(dev, 1); + } else { + DRM_ERROR("Unable to find MMIO registers\n"); + return -ENODEV; + } + + ret = drm_addmap(dev, dev_priv->mmiobase, dev_priv->mmiolen, + _DRM_REGISTERS, _DRM_READ_ONLY, &dev_priv->mmio_map); + if (ret != 0) { + DRM_ERROR("Cannot add mapping for MMIO registers\n"); + return ret; + } + + DRM_DEBUG("dev_priv->mmio map is %08X\n", dev_priv->mmio_map); + intel_modeset_init(dev); + return 0; +} + +int i915_driver_unload(drm_device_t *dev) +{ + drm_i915_private_t *dev_priv = dev->dev_private; + + intel_modeset_cleanup(dev); + drm_free(dev_priv, sizeof(*dev_priv), DRM_MEM_DRIVER); + + dev->dev_private = NULL; return 0; } void i915_driver_lastclose(drm_device_t * dev) { - if (dev->dev_private) { - drm_i915_private_t *dev_priv = dev->dev_private; - i915_do_cleanup_pageflip(dev); - i915_mem_takedown(&(dev_priv->agp_heap)); - } + drm_i915_private_t *dev_priv = dev->dev_private; + + i915_mem_takedown(&(dev_priv->agp_heap)); + i915_dma_cleanup(dev); + + dev_priv->mmio_map = NULL; } void i915_driver_preclose(drm_device_t * dev, DRMFILE filp) { - if (dev->dev_private) { - drm_i915_private_t *dev_priv = dev->dev_private; - i915_mem_release(dev, filp, dev_priv->agp_heap); - } + drm_i915_private_t *dev_priv = dev->dev_private; + i915_mem_release(dev, filp, dev_priv->agp_heap); } drm_ioctl_desc_t i915_ioctls[] = { @@ -950,8 +967,22 @@ int i915_driver_device_is_agp(drm_device_t * dev) int i915_driver_firstopen(struct drm_device *dev) { -#ifdef I915_HAVE_BUFFER + drm_i915_private_t *dev_priv = dev->dev_private; + int ret; + DRM_DEBUG("\n"); drm_bo_driver_init(dev); -#endif + + if (!dev_priv->mmio_map) { + ret = drm_addmap(dev, dev_priv->mmiobase, dev_priv->mmiolen, + _DRM_REGISTERS, _DRM_READ_ONLY, &dev_priv->mmio_map); + if (ret != 0) { + DRM_ERROR("Cannot add mapping for MMIO registers\n"); + return ret; + } + } + + DRM_DEBUG("dev_priv->mmio map is %08X\n", dev_priv->mmio_map); + return 0; } + -- cgit v1.2.3