summaryrefslogtreecommitdiff
path: root/usr/src/uts/sun/io/bpp.c
diff options
context:
space:
mode:
Diffstat (limited to 'usr/src/uts/sun/io/bpp.c')
-rw-r--r--usr/src/uts/sun/io/bpp.c108
1 files changed, 67 insertions, 41 deletions
diff --git a/usr/src/uts/sun/io/bpp.c b/usr/src/uts/sun/io/bpp.c
index 52cdf0fc07..25dc5a4d0f 100644
--- a/usr/src/uts/sun/io/bpp.c
+++ b/usr/src/uts/sun/io/bpp.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -19,6 +18,7 @@
*
* CDDL HEADER END
*/
+
/*
* Copyright 2005 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
@@ -89,16 +89,28 @@ static int sbus_cycle = 0; /* sbus clock prop period in nsec */
static void *bpp_state_head; /* opaque handle top of state structs */
-static ddi_dma_lim_t bpp_limits = {
- 0x00000000, /* lower range limit */
- (ulong_t)0xffffffff, /* upper range limit */
+static ddi_dma_attr_t bpp_dma_attr = {
+ DMA_ATTR_V0, /* version */
+ 0x00000000ull, /* dlim_addr_lo */
+ 0xffffffffull, /* dlim_addr_hi */
((1<<24)-1), /* inclusive upper bound of */
/* bpp dma address counter */
/* lower 24 bits are a counter, */
/* upper 8 bits are registered */
- DEFAULT_BURSTSIZE, /* encoded burstsizes */
- (uint_t)1, /* minimum dma transfer */
- 0 /* dma speed - don't care */
+ 1, /* DMA address alignment */
+ DEFAULT_BURSTSIZE, /* encoded burstsizes */
+ 0x1, /* min effective DMA size */
+ 0x7fffffff, /* max DMA xfer size */
+ 0x00ffffff, /* segment boundary */
+ 1, /* s/g list length */
+ 1, /* granularity of device */
+ 0 /* DMA flags */
+};
+
+static ddi_device_acc_attr_t bpp_acc_attr = {
+ DDI_DEVICE_ATTR_V0,
+ DDI_STRUCTURE_BE_ACC,
+ DDI_STRICTORDER_ACC
};
#define KIOIP KSTAT_INTR_PTR(bpp_p->intrstats)
@@ -367,7 +379,6 @@ bpp_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
bpp_p->sbus_clock_cycle));
-
/*
* Map in any device registers. The zebra parallel section
* has only one register area.
@@ -375,10 +386,12 @@ bpp_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
/*
* Map the structure into kernel virtual space.
*/
- if (ddi_map_regs(dip, 0, (caddr_t *)&(bpp_p->bpp_regs_p),
- 0, sizeof (struct bpp_regs)) != DDI_SUCCESS) {
+ if (ddi_regs_map_setup(dip, 0, (caddr_t *)&(bpp_p->bpp_regs_p),
+ 0, sizeof (struct bpp_regs),
+ &bpp_acc_attr, &bpp_p->bpp_acc_handle) != DDI_SUCCESS) {
cmn_err(CE_NOTE,
- "bpp_attach unit %d: ddi_map_regs failed!", unit_no);
+ "bpp_attach unit %d: regs_map_setup failed!", unit_no);
+ cv_destroy(&bpp_p->wr_cv);
mutex_destroy(&bpp_p->bpp_mutex);
ddi_remove_intr(bpp_p->dip, 0, bpp_p->bpp_block_cookie);
ddi_soft_state_free(bpp_state_head, unit_no);
@@ -389,13 +402,27 @@ bpp_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
if (check_bpp_registers(unit_no)) { /* registers don't seem right */
cmn_err(CE_NOTE,
"bpp_attach unit %d: register check failed!", unit_no);
- ddi_unmap_regs(dip, 0, (caddr_t *)&bpp_p->bpp_regs_p,
- 0, sizeof (struct bpp_regs));
+ ddi_regs_map_free(&bpp_p->bpp_acc_handle);
+ cv_destroy(&bpp_p->wr_cv);
mutex_destroy(&bpp_p->bpp_mutex);
ddi_remove_intr(bpp_p->dip, 0, bpp_p->bpp_block_cookie);
ddi_soft_state_free(bpp_state_head, unit_no);
return (DDI_FAILURE);
}
+
+ if (ddi_dma_alloc_handle(dip, &bpp_dma_attr, DDI_DMA_DONTWAIT, NULL,
+ &bpp_p->bpp_dma_handle) != DDI_SUCCESS) {
+ cmn_err(CE_NOTE,
+ "bpp_attach unit %d: dma_alloc_handle failed!",
+ unit_no);
+ ddi_regs_map_free(&bpp_p->bpp_acc_handle);
+ cv_destroy(&bpp_p->wr_cv);
+ mutex_destroy(&bpp_p->bpp_mutex);
+ ddi_remove_intr(bpp_p->dip, 0, bpp_p->bpp_block_cookie);
+ ddi_soft_state_free(bpp_state_head, unit_no);
+ return (DDI_FAILURE);
+ }
+
/* The driver is now commited - all sanity checks done */
(void) sprintf(name, "bpp%d", unit_no);
@@ -404,8 +431,9 @@ bpp_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
ddi_remove_minor_node(dip, NULL);
cmn_err(CE_NOTE, "ddi_create_minor_node failed for unit %d",
unit_no);
- ddi_unmap_regs(dip, 0, (caddr_t *)&bpp_p->bpp_regs_p,
- 0, sizeof (struct bpp_regs));
+ ddi_dma_free_handle(&bpp_p->bpp_dma_handle);
+ ddi_regs_map_free(&bpp_p->bpp_acc_handle);
+ cv_destroy(&bpp_p->wr_cv);
mutex_destroy(&bpp_p->bpp_mutex);
ddi_remove_intr(bpp_p->dip, 0, bpp_p->bpp_block_cookie);
ddi_soft_state_free(bpp_state_head, unit_no);
@@ -691,12 +719,14 @@ bpp_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
/* Remove the minor node created in attach */
ddi_remove_minor_node(dip, NULL);
+ /* Free DMA handle */
+ ddi_dma_free_handle(&bpp_p->bpp_dma_handle);
+
/*
* Unmap register area from kernel memory.
*/
dip = bpp_p->dip;
- ddi_unmap_regs(dip, 0, (caddr_t *)&bpp_p->bpp_regs_p,
- 0, sizeof (struct bpp_regs));
+ ddi_regs_map_free(&bpp_p->bpp_acc_handle);
/*
* Remove interrupt registry
@@ -709,7 +739,8 @@ bpp_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
}
bpp_p->intrstats = NULL;
- /* Destroy the per-unit mutex. */
+ /* Destroy the per-unit cv and mutex. */
+ cv_destroy(&bpp_p->wr_cv);
mutex_destroy(&bpp_p->bpp_mutex);
/* Free the memory allocated for this unit's state struct */
@@ -1208,8 +1239,9 @@ bpp_strategy(register struct buf *bp)
size_t size; /* size of DVMA transfer */
register struct bpp_transfer_parms *bpp_transfer_parms_p;
register volatile struct bpp_regs *bpp_regs_p;
- int flags; /* flags to pass to ddi_dma_buf_setup */
+ int flags; /* flags to use for DMA mapping */
ddi_dma_cookie_t dma_cookie;
+ uint_t dma_cookie_cnt;
unit_no = BPP_UNIT(&(bp->b_edev));
@@ -1242,37 +1274,31 @@ bpp_strategy(register struct buf *bp)
flags = DDI_DMA_WRITE;
BPP_PRINT(5, (CE_CONT,
- "Before dma_buf_setup, b_addr = 0x%p, b_bcount = 0x%x\n",
+ "Before dma_buf_bind, b_addr = 0x%p, b_bcount = 0x%x\n",
(void *)bp->b_un.b_addr, bp->b_bcount));
/*
* Get dvma bus resource, sleeping if necessary.
*/
- if ((ddi_dma_buf_setup(bpp_p->dip, bp, flags, DDI_DMA_SLEEP,
- (caddr_t)0, &bpp_limits,
- &bpp_p->bpp_dma_handle)) != 0) {
+ if (ddi_dma_buf_bind_handle(bpp_p->bpp_dma_handle, bp,
+ flags | DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, 0,
+ &dma_cookie, &dma_cookie_cnt) != DDI_DMA_MAPPED) {
cmn_err(CE_NOTE,
- "ERROR: bpp%d: ddi_dma_buf_setup failed mapping",
+ "ERROR: bpp%d: dma_buf_bind failed mapping",
unit_no);
+ bioerror(bp, ENOMEM);
+ bp->b_resid = bp->b_bcount;
+ biodone(bp);
+ return (0);
}
+ ASSERT(dma_cookie_cnt == 1);
BPP_PRINT(5, (CE_CONT,
- "After dma_buf_setup, b_addr = 0x%p, b_bcount = 0x%x\n",
+ "After dma_buf_bind, b_addr = 0x%p, b_bcount = 0x%x\n",
(void *)bp->b_un.b_addr, bp->b_bcount));
-
- /*
- * Convert the dma_handle into an actual virtual
- * DVMA address which can be put into the DMA engine.
- */
- if (ddi_dma_htoc(bpp_p->bpp_dma_handle, (off_t)0,
- &dma_cookie) != 0) {
- cmn_err(CE_NOTE,
- "ERROR: bpp%d: ddi_dma_htoc failed to fill in DMA cookie!",
- unit_no);
- }
start_address = dma_cookie.dmac_address;
BPP_PRINT(5, (CE_CONT,
- "After dma_htoc, start_address = 0x%x\n", start_address));
+ "start_address = 0x%x\n", start_address));
size = bp->b_bcount;
@@ -1734,7 +1760,7 @@ bpp_intr(caddr_t unit_no)
* Release the dvma bus resource.
*/
- (void) ddi_dma_free(bpp_p->bpp_dma_handle);
+ (void) ddi_dma_unbind_handle(bpp_p->bpp_dma_handle);
BPP_PRINT(5, (CE_CONT,
"bpp_intr, unit %d, Calling biodone.\n", unit_no));
@@ -1923,7 +1949,7 @@ bpp_transfer_timeout(void *unit_no_arg)
/*
* Release the dvma bus resource.
*/
- (void) ddi_dma_free(bpp_p->bpp_dma_handle);
+ (void) ddi_dma_unbind_handle(bpp_p->bpp_dma_handle);
BPP_PRINT(5, (CE_CONT,
"bpp_transfer_timeout, unit %d, Calling biodone.\n", unit_no));