diff options
Diffstat (limited to 'usr/src/uts/common/io/drm/drm_dma.c')
-rw-r--r-- | usr/src/uts/common/io/drm/drm_dma.c | 166 |
1 files changed, 90 insertions, 76 deletions
diff --git a/usr/src/uts/common/io/drm/drm_dma.c b/usr/src/uts/common/io/drm/drm_dma.c index 589c486..54d7981 100644 --- a/usr/src/uts/common/io/drm/drm_dma.c +++ b/usr/src/uts/common/io/drm/drm_dma.c @@ -1,8 +1,22 @@ /* - * drm_dma.c -- DMA IOCTL and function support -*- linux-c -*- - * Created: Fri Mar 19 14:30:16 1999 by faith@valinux.com + * Copyright (c) 2006, 2012, Oracle and/or its affiliates. All rights reserved. */ + /* + * Copyright (c) 2012 Intel Corporation. All rights reserved. + */ + +/** + * \file drm_dma.c + * DMA IOCTL and function support + * + * \author Rickard E. (Rik) Faith <faith@valinux.com> + * \author Gareth Hughes <gareth@valinux.com> + */ + +/* + * Created: Fri Mar 19 14:30:16 1999 by faith@valinux.com + * * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas. * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California. * All Rights Reserved. @@ -25,109 +39,121 @@ * 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: - * Rickard E. (Rik) Faith <faith@valinux.com> - * Gareth Hughes <gareth@valinux.com> - * */ -/* - * Copyright 2008 Sun Microsystems, Inc. All rights reserved. - * Use is subject to license terms. - */ - -#pragma ident "%Z%%M% %I% %E% SMI" - #include "drmP.h" -int -drm_dma_setup(drm_device_t *dev) +/** + * Initialize the DMA data. + * + * \param dev DRM device. + * \return zero on success or a negative value on failure. + * + * Allocate and initialize a drm_device_dma structure. + */ +int drm_dma_setup(struct drm_device *dev) { int i; - drm_buf_entry_t *pbuf; - dev->dma = drm_calloc(1, sizeof (*dev->dma), DRM_MEM_DMA); - if (dev->dma == NULL) - return (ENOMEM); + dev->dma = kmalloc(sizeof(*dev->dma), GFP_KERNEL); + if (!dev->dma) + return -ENOMEM; + + (void) memset(dev->dma, 0, sizeof(*dev->dma)); + + for (i = 0; i <= DRM_MAX_ORDER; i++) + (void) memset(&dev->dma->bufs[i], 0, sizeof(dev->dma->bufs[0])); mutex_init(&dev->dma_lock, NULL, MUTEX_DRIVER, NULL); - pbuf = &(dev->dma->bufs[0]); - for (i = 0; i <= DRM_MAX_ORDER; i++, pbuf++) - bzero(pbuf, sizeof (drm_buf_entry_t)); - return (0); + return 0; } -void -drm_dma_takedown(drm_device_t *dev) +/** + * Cleanup the DMA resources. + * + * \param dev DRM device. + * + * Free all pages associated with DMA buffers, the buffers and pages lists, and + * finally the drm_device::dma structure itself. + */ +void drm_dma_takedown(struct drm_device *dev) { - drm_device_dma_t *dma = dev->dma; + struct drm_device_dma *dma = dev->dma; int i, j; - if (dma == NULL) + if (!dma) return; /* Clear dma buffers */ for (i = 0; i <= DRM_MAX_ORDER; i++) { if (dma->bufs[i].seg_count) { - drm_free(dma->bufs[i].seglist, - dma->bufs[i].seg_count * - sizeof (*dma->bufs[0].seglist), DRM_MEM_SEGS); + DRM_DEBUG("order %d: buf_count = %d," + " seg_count = %d\n", + i, + dma->bufs[i].buf_count, + dma->bufs[i].seg_count); + kfree(dma->bufs[i].seglist, + dma->bufs[i].seg_count * sizeof (*dma->bufs[0].seglist)); } - - for (j = 0; j < dma->bufs[i].buf_count; j++) { - if (dma->bufs[i].buflist[j].dev_private) { - drm_free(dma->bufs[i].buflist[j].dev_private, - dma->bufs[i].buflist[j].dev_priv_size, - DRM_MEM_BUFS); + if (dma->bufs[i].buf_count) { + for (j = 0; j < dma->bufs[i].buf_count; j++) { + if (dma->bufs[i].buflist[j].dev_private) { + kfree(dma->bufs[i].buflist[j].dev_private, + dma->bufs[i].buflist[j].dev_priv_size); + } } + kfree(dma->bufs[i].buflist, + dma->bufs[i].buf_count * sizeof(*dma->bufs[0].buflist)); } - if (dma->bufs[i].buf_count) - drm_free(dma->bufs[i].buflist, - dma->bufs[i].buf_count * - sizeof (*dma->bufs[0].buflist), DRM_MEM_BUFS); - } - if (dma->buflist) { - drm_free(dma->buflist, - dma->buf_count *sizeof (*dma->buflist), - DRM_MEM_BUFS); - } - - if (dma->pagelist) { - drm_free(dma->pagelist, - dma->page_count *sizeof (*dma->pagelist), - DRM_MEM_PAGES); } - drm_free(dev->dma, sizeof (*dev->dma), DRM_MEM_DRIVER); + if (dma->buflist) + kfree(dma->buflist, dma->buf_count * sizeof(*dma->buflist)); + if (dma->pagelist) + kfree(dma->pagelist, dma->page_count * sizeof(*dma->pagelist)); + kfree(dev->dma, sizeof(*dev->dma)); dev->dma = NULL; + mutex_destroy(&dev->dma_lock); } - -/*ARGSUSED*/ -void -drm_free_buffer(drm_device_t *dev, drm_buf_t *buf) +/** + * Free a buffer. + * + * \param dev DRM device. + * \param buf buffer to free. + * + * Resets the fields of \p buf. + */ +/* LINTED */ +void drm_free_buffer(struct drm_device *dev, drm_buf_t *buf) { if (!buf) return; - buf->pending = 0; - buf->filp = NULL; - buf->used = 0; + buf->pending = 0; + buf->file_priv = NULL; + buf->used = 0; } -void -drm_reclaim_buffers(drm_device_t *dev, drm_file_t *fpriv) +/** + * Reclaim the buffers. + * + * \param file_priv DRM file private. + * + * Frees each buffer associated with \p file_priv not already on the hardware. + */ +void drm_core_reclaim_buffers(struct drm_device *dev, + struct drm_file *file_priv) { - drm_device_dma_t *dma = dev->dma; + struct drm_device_dma *dma = dev->dma; int i; if (!dma) return; for (i = 0; i < dma->buf_count; i++) { - if (dma->buflist[i]->filp == fpriv) { + if (dma->buflist[i]->file_priv == file_priv) { switch (dma->buflist[i]->list) { case DRM_LIST_NONE: drm_free_buffer(dev, dma->buflist[i]); @@ -143,15 +169,3 @@ drm_reclaim_buffers(drm_device_t *dev, drm_file_t *fpriv) } } -/* Call into the driver-specific DMA handler */ -int -drm_dma(DRM_IOCTL_ARGS) -{ - DRM_DEVICE; - - if (dev->driver->dma_ioctl) { - return (dev->driver->dma_ioctl(dev, data, fpriv, mode)); - } else { - return (EINVAL); - } -} |