Print this page
NEX-1890 update oce from source provided by Emulex
*** 17,28 ****
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
! /* Copyright © 2003-2011 Emulex. All rights reserved. */
/*
* Source file containing the implementation of Driver buffer management
* and related helper functions
*/
#include <oce_impl.h>
--- 17,32 ----
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
! /*
! * Copyright (c) 2009-2012 Emulex. All rights reserved.
! * Use is subject to license terms.
! */
+
/*
* Source file containing the implementation of Driver buffer management
* and related helper functions
*/
#include <oce_impl.h>
*** 57,130 ****
* flags - DDI_DMA_CONSISTENT/DDI_DMA_STREAMING
*
* return pointer to a oce_dma_buf_t structure handling the map
* NULL => failure
*/
! oce_dma_buf_t *
! oce_alloc_dma_buffer(struct oce_dev *dev,
uint32_t size, ddi_dma_attr_t *dma_attr, uint32_t flags)
{
- oce_dma_buf_t *dbuf;
- ddi_dma_cookie_t cookie;
- uint32_t count;
size_t actual_len;
int ret = 0;
ASSERT(size > 0);
/* if NULL use default */
if (dma_attr == NULL) {
dma_attr = &oce_dma_buf_attr;
}
- dbuf = kmem_zalloc(sizeof (oce_dma_buf_t), KM_NOSLEEP);
- if (dbuf == NULL) {
- return (NULL);
- }
-
/* allocate dma handle */
ret = ddi_dma_alloc_handle(dev->dip, dma_attr,
DDI_DMA_DONTWAIT, NULL, &dbuf->dma_handle);
if (ret != DDI_SUCCESS) {
! oce_log(dev, CE_WARN, MOD_CONFIG, "%s",
"Failed to allocate DMA handle");
goto handle_fail;
}
/* allocate the DMA-able memory */
ret = ddi_dma_mem_alloc(dbuf->dma_handle, size, &oce_dma_buf_accattr,
! flags, DDI_DMA_DONTWAIT, NULL, &dbuf->base,
! &actual_len, &dbuf->acc_handle);
if (ret != DDI_SUCCESS) {
! oce_log(dev, CE_WARN, MOD_CONFIG, "%s",
! "Failed to allocate DMA memory");
goto alloc_fail;
}
/* bind handle */
ret = ddi_dma_addr_bind_handle(dbuf->dma_handle,
(struct as *)0, dbuf->base, actual_len,
! DDI_DMA_RDWR | flags,
! DDI_DMA_DONTWAIT, NULL, &cookie, &count);
if (ret != DDI_DMA_MAPPED) {
! oce_log(dev, CE_WARN, MOD_CONFIG, "%s",
"Failed to bind dma handle");
goto bind_fail;
}
bzero(dbuf->base, actual_len);
! dbuf->addr = cookie.dmac_laddress;
dbuf->size = actual_len;
/* usable length */
dbuf->len = size;
dbuf->num_pages = OCE_NUM_PAGES(size);
! return (dbuf);
bind_fail:
ddi_dma_mem_free(&dbuf->acc_handle);
alloc_fail:
ddi_dma_free_handle(&dbuf->dma_handle);
handle_fail:
! kmem_free(dbuf, sizeof (oce_dma_buf_t));
! return (NULL);
} /* oce_dma_alloc_buffer */
/*
* function to delete a dma buffer
*
--- 61,126 ----
* flags - DDI_DMA_CONSISTENT/DDI_DMA_STREAMING
*
* return pointer to a oce_dma_buf_t structure handling the map
* NULL => failure
*/
! int
! oce_alloc_dma_buffer(struct oce_dev *dev, oce_dma_buf_t *dbuf,
uint32_t size, ddi_dma_attr_t *dma_attr, uint32_t flags)
{
size_t actual_len;
int ret = 0;
ASSERT(size > 0);
/* if NULL use default */
if (dma_attr == NULL) {
dma_attr = &oce_dma_buf_attr;
}
/* allocate dma handle */
ret = ddi_dma_alloc_handle(dev->dip, dma_attr,
DDI_DMA_DONTWAIT, NULL, &dbuf->dma_handle);
if (ret != DDI_SUCCESS) {
! oce_log(dev, CE_NOTE, MOD_CONFIG, "%s",
"Failed to allocate DMA handle");
goto handle_fail;
}
/* allocate the DMA-able memory */
ret = ddi_dma_mem_alloc(dbuf->dma_handle, size, &oce_dma_buf_accattr,
! (flags & DDI_DMA_STREAMING) ?
! DDI_DMA_STREAMING : DDI_DMA_CONSISTENT, DDI_DMA_DONTWAIT, NULL,
! &dbuf->base, &actual_len, &dbuf->acc_handle);
if (ret != DDI_SUCCESS) {
! oce_log(dev, CE_NOTE, MOD_CONFIG,
! "Failed to allocate DMA memory: 0x%x bytes", size);
goto alloc_fail;
}
/* bind handle */
ret = ddi_dma_addr_bind_handle(dbuf->dma_handle,
(struct as *)0, dbuf->base, actual_len,
! flags,
! DDI_DMA_DONTWAIT, NULL, &dbuf->cookie, &dbuf->ncookies);
if (ret != DDI_DMA_MAPPED) {
! oce_log(dev, CE_NOTE, MOD_CONFIG, "%s",
"Failed to bind dma handle");
goto bind_fail;
}
bzero(dbuf->base, actual_len);
! dbuf->addr = dbuf->cookie.dmac_laddress;
dbuf->size = actual_len;
/* usable length */
dbuf->len = size;
dbuf->num_pages = OCE_NUM_PAGES(size);
! return (DDI_SUCCESS);
bind_fail:
ddi_dma_mem_free(&dbuf->acc_handle);
alloc_fail:
ddi_dma_free_handle(&dbuf->dma_handle);
handle_fail:
! return (ret);
} /* oce_dma_alloc_buffer */
/*
* function to delete a dma buffer
*
*** 144,158 ****
if (dbuf->dma_handle != NULL) {
(void) ddi_dma_unbind_handle(dbuf->dma_handle);
}
if (dbuf->acc_handle != NULL) {
ddi_dma_mem_free(&dbuf->acc_handle);
}
if (dbuf->dma_handle != NULL) {
ddi_dma_free_handle(&dbuf->dma_handle);
}
- kmem_free(dbuf, sizeof (oce_dma_buf_t));
} /* oce_free_dma_buffer */
/*
* function to create a ring buffer
*
--- 140,155 ----
if (dbuf->dma_handle != NULL) {
(void) ddi_dma_unbind_handle(dbuf->dma_handle);
}
if (dbuf->acc_handle != NULL) {
ddi_dma_mem_free(&dbuf->acc_handle);
+ dbuf->acc_handle = NULL;
}
if (dbuf->dma_handle != NULL) {
ddi_dma_free_handle(&dbuf->dma_handle);
+ dbuf->dma_handle = NULL;
}
} /* oce_free_dma_buffer */
/*
* function to create a ring buffer
*
*** 162,189 ****
* flags - DDI_DMA_CONSISTENT/DDI_DMA_STREAMING for ring memory
*
* return pointer to a ring_buffer structure, NULL on failure
*/
oce_ring_buffer_t *
! create_ring_buffer(struct oce_dev *dev,
uint32_t num_items, uint32_t item_size, uint32_t flags)
{
oce_ring_buffer_t *ring;
! uint32_t size;
/* allocate the ring buffer */
ring = kmem_zalloc(sizeof (oce_ring_buffer_t), KM_NOSLEEP);
if (ring == NULL) {
return (NULL);
}
/* get the dbuf defining the ring */
! size = num_items * item_size;
! ring->dbuf = oce_alloc_dma_buffer(dev, size, NULL, flags);
! if (ring->dbuf == NULL) {
! oce_log(dev, CE_WARN, MOD_CONFIG, "%s",
! "Ring buffer allocation failed");
goto dbuf_fail;
}
/* fill the rest of the ring */
ring->num_items = num_items;
--- 159,186 ----
* flags - DDI_DMA_CONSISTENT/DDI_DMA_STREAMING for ring memory
*
* return pointer to a ring_buffer structure, NULL on failure
*/
oce_ring_buffer_t *
! oce_create_ring_buffer(struct oce_dev *dev,
uint32_t num_items, uint32_t item_size, uint32_t flags)
{
oce_ring_buffer_t *ring;
! int ret;
/* allocate the ring buffer */
ring = kmem_zalloc(sizeof (oce_ring_buffer_t), KM_NOSLEEP);
if (ring == NULL) {
return (NULL);
}
/* get the dbuf defining the ring */
! ret = oce_alloc_dma_buffer(dev, &ring->dbuf, num_items *item_size,
! NULL, flags);
! if (ret != DDI_SUCCESS) {
! oce_log(dev, CE_WARN, MOD_CONFIG,
! "Ring buffer allocation failed 0x%x", ret);
goto dbuf_fail;
}
/* fill the rest of the ring */
ring->num_items = num_items;
*** 209,220 ****
{
ASSERT(dev != NULL);
ASSERT(ring != NULL);
/* free the dbuf associated with the ring */
! oce_free_dma_buffer(dev, ring->dbuf);
! ring->dbuf = NULL;
/* free the ring itself */
kmem_free(ring, sizeof (oce_ring_buffer_t));
} /* destroy_ring_buffer */
--- 206,216 ----
{
ASSERT(dev != NULL);
ASSERT(ring != NULL);
/* free the dbuf associated with the ring */
! oce_free_dma_buffer(dev, &ring->dbuf);
/* free the ring itself */
kmem_free(ring, sizeof (oce_ring_buffer_t));
} /* destroy_ring_buffer */