dpt_eisa.c revision 117126
159078Smdodd/*- 259078Smdodd * Copyright (c) 1997, 2000 Matthew N. Dodd <winter@jurai.net> 359078Smdodd * All rights reserved. 434480Sjulian * 534480Sjulian * Redistribution and use in source and binary forms, with or without 634480Sjulian * modification, are permitted provided that the following conditions 734480Sjulian * are met: 834480Sjulian * 1. Redistributions of source code must retain the above copyright 959078Smdodd * notice, this list of conditions and the following disclaimer. 1034480Sjulian * 2. Redistributions in binary form must reproduce the above copyright 1134480Sjulian * notice, this list of conditions and the following disclaimer in the 1234480Sjulian * documentation and/or other materials provided with the distribution. 1334480Sjulian * 1434480Sjulian * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 1534480Sjulian * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1634480Sjulian * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1759078Smdodd * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 1859078Smdodd * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 1934480Sjulian * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2034480Sjulian * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2134480Sjulian * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2234480Sjulian * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2334480Sjulian * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2434480Sjulian * SUCH DAMAGE. 2559078Smdodd * 2659078Smdodd * $FreeBSD: head/sys/dev/dpt/dpt_eisa.c 117126 2003-07-01 15:52:06Z scottl $ 2734480Sjulian */ 2834480Sjulian 2934480Sjulian#include <sys/param.h> 3034480Sjulian#include <sys/systm.h> 3134480Sjulian#include <sys/kernel.h> 3245791Speter#include <sys/module.h> 33117126Sscottl#include <sys/lock.h> 34117126Sscottl#include <sys/mutex.h> 3545791Speter#include <sys/bus.h> 3634480Sjulian 3739234Sgibbs#include <machine/bus_pio.h> 3839234Sgibbs#include <machine/bus.h> 3945791Speter#include <machine/resource.h> 4045791Speter#include <sys/rman.h> 4134480Sjulian 4259078Smdodd#include <dev/eisa/eisaconf.h> 4359078Smdodd 4439234Sgibbs#include <cam/scsi/scsi_all.h> 4539234Sgibbs 4639234Sgibbs#include <dev/dpt/dpt.h> 4739234Sgibbs 48112780Smdodd#define DPT_EISA_IOSIZE 0x9 4952042Smdodd#define DPT_EISA_SLOT_OFFSET 0x0c00 5052042Smdodd#define DPT_EISA_EATA_REG_OFFSET 0x0088 5152042Smdodd 5259078Smdodd#define DPT_EISA_DPT2402 0x12142402 /* DPT PM2012A/9X */ 5359078Smdodd#define DPT_EISA_DPTA401 0x1214A401 /* DPT PM2012B/9X */ 5459078Smdodd#define DPT_EISA_DPTA402 0x1214A402 /* DPT PM2012B2/9X */ 5559078Smdodd#define DPT_EISA_DPTA410 0x1214A410 /* DPT PM2x22A/9X */ 5659078Smdodd#define DPT_EISA_DPTA411 0x1214A411 /* DPT Spectre */ 5759078Smdodd#define DPT_EISA_DPTA412 0x1214A412 /* DPT PM2021A/9X */ 5859078Smdodd#define DPT_EISA_DPTA420 0x1214A420 /* DPT Smart Cache IV (PM2042) */ 5959078Smdodd#define DPT_EISA_DPTA501 0x1214A501 /* DPT PM2012B1/9X" */ 6059078Smdodd#define DPT_EISA_DPTA502 0x1214A502 /* DPT PM2012Bx/9X */ 6159078Smdodd#define DPT_EISA_DPTA701 0x1214A701 /* DPT PM2011B1/9X */ 6259078Smdodd#define DPT_EISA_DPTBC01 0x1214BC01 /* DPT PM3011/7X ESDI */ 6359078Smdodd#define DPT_EISA_DPT8200 0x12148200 /* NEC EATA SCSI */ 6459078Smdodd#define DPT_EISA_DPT2408 0x12142408 /* ATT EATA SCSI */ 6552042Smdodd 6634480Sjulian/* Function Prototypes */ 6734480Sjulian 6859078Smdoddstatic const char * dpt_eisa_match (eisa_id_t); 6959078Smdoddstatic int dpt_eisa_probe (device_t); 7059078Smdoddstatic int dpt_eisa_attach (device_t); 7134480Sjulian 7239234Sgibbsstatic int 7359078Smdodddpt_eisa_probe (device_t dev) 7434480Sjulian{ 7552042Smdodd const char * desc; 7652042Smdodd u_int32_t io_base; 7752042Smdodd dpt_conf_t * conf; 7834480Sjulian 7945791Speter desc = dpt_eisa_match(eisa_get_id(dev)); 8045791Speter if (!desc) 8145791Speter return (ENXIO); 8245791Speter device_set_desc(dev, desc); 8334480Sjulian 84112780Smdodd io_base = (eisa_get_slot(dev) * EISA_SLOT_SIZE) + 85112780Smdodd DPT_EISA_SLOT_OFFSET + 86112780Smdodd DPT_EISA_EATA_REG_OFFSET; 8745791Speter 88112780Smdodd conf = dpt_pio_get_conf(io_base); 8952042Smdodd if (!conf) { 9052042Smdodd printf("dpt: dpt_pio_get_conf() failed.\n"); 9152042Smdodd return (ENXIO); 9245791Speter } 9334480Sjulian 9452042Smdodd eisa_add_iospace(dev, io_base, DPT_EISA_IOSIZE, RESVADDR_NONE); 9552042Smdodd eisa_add_intr(dev, conf->IRQ, 9652042Smdodd (conf->IRQ_TR ? EISA_TRIGGER_LEVEL : EISA_TRIGGER_EDGE)); 9745791Speter 9845791Speter return 0; 9934480Sjulian} 10034480Sjulian 10145791Speterstatic int 10259078Smdodddpt_eisa_attach (device_t dev) 10334480Sjulian{ 104112780Smdodd dpt_softc_t * dpt; 10539234Sgibbs int s; 10659078Smdodd int error = 0; 10734480Sjulian 108112780Smdodd dpt = device_get_softc(dev); 10934480Sjulian 110112780Smdodd dpt->io_rid = 0; 111112780Smdodd dpt->io_type = SYS_RES_IOPORT; 112112780Smdodd dpt->irq_rid = 0; 11359078Smdodd 114112780Smdodd error = dpt_alloc_resources(dev); 115112780Smdodd if (error) { 11645791Speter goto bad; 11759078Smdodd } 11834480Sjulian 119112780Smdodd dpt_alloc(dev); 120112780Smdodd 12139234Sgibbs /* Allocate a dmatag representing the capabilities of this attachment */ 12239234Sgibbs /* XXX Should be a child of the EISA bus dma tag */ 12359078Smdodd if (bus_dma_tag_create( /* parent */ NULL, 12459078Smdodd /* alignemnt */ 1, 12559078Smdodd /* boundary */ 0, 12659078Smdodd /* lowaddr */ BUS_SPACE_MAXADDR_32BIT, 12759078Smdodd /* highaddr */ BUS_SPACE_MAXADDR, 12859078Smdodd /* filter */ NULL, 12959078Smdodd /* filterarg */ NULL, 13059078Smdodd /* maxsize */ BUS_SPACE_MAXSIZE_32BIT, 131104710Speter /* nsegments */ ~0, 13259078Smdodd /* maxsegsz */ BUS_SPACE_MAXSIZE_32BIT, 133117126Sscottl /* flags */ 0, 134117126Sscottl /* lockfunc */ busdma_lock_mutex, 135117126Sscottl /* lockarg */ &Giant, 13659078Smdodd &dpt->parent_dmat) != 0) { 13759078Smdodd error = ENXIO; 13845791Speter goto bad; 13934480Sjulian } 14034480Sjulian 14159078Smdodd s = splcam(); 14234480Sjulian 14339234Sgibbs if (dpt_init(dpt) != 0) { 144112780Smdodd splx(s); 14559078Smdodd error = ENXIO; 14645791Speter goto bad; 14734480Sjulian } 14834480Sjulian 14939234Sgibbs /* Register with the XPT */ 15039234Sgibbs dpt_attach(dpt); 15145791Speter 15239234Sgibbs splx(s); 15334480Sjulian 154112780Smdodd if (bus_setup_intr(dev, dpt->irq_res, INTR_TYPE_CAM | INTR_ENTROPY, 155112780Smdodd dpt_intr, dpt, &dpt->ih)) { 15659078Smdodd device_printf(dev, "Unable to register interrupt handler\n"); 15759078Smdodd error = ENXIO; 15859078Smdodd goto bad; 15959078Smdodd } 16045791Speter 16159078Smdodd return (error); 16259078Smdodd 16345791Speter bad: 164112780Smdodd dpt_release_resources(dev); 16559078Smdodd 166112780Smdodd if (dpt) 167112780Smdodd dpt_free(dpt); 168112780Smdodd 16959078Smdodd return (error); 17034480Sjulian} 17134480Sjulian 17234480Sjulianstatic const char * 17334480Sjuliandpt_eisa_match(type) 17434480Sjulian eisa_id_t type; 17534480Sjulian{ 17634480Sjulian switch (type) { 17759078Smdodd case DPT_EISA_DPT2402: 17859078Smdodd case DPT_EISA_DPTA401: 17959078Smdodd case DPT_EISA_DPTA402: 18059078Smdodd case DPT_EISA_DPTA410: 18159078Smdodd case DPT_EISA_DPTA411: 18259078Smdodd case DPT_EISA_DPTA412: 18359078Smdodd case DPT_EISA_DPTA420: 18459078Smdodd case DPT_EISA_DPTA501: 18559078Smdodd case DPT_EISA_DPTA502: 18659078Smdodd case DPT_EISA_DPTA701: 18759078Smdodd case DPT_EISA_DPTBC01: 18859078Smdodd case DPT_EISA_DPT8200: 18959078Smdodd case DPT_EISA_DPT2408: 19059078Smdodd return ("DPT SCSI Host Bus Adapter"); 19134480Sjulian break; 19234480Sjulian default: 19334480Sjulian break; 19434480Sjulian } 19534480Sjulian 19634480Sjulian return (NULL); 19734480Sjulian} 19834480Sjulian 19945791Speterstatic device_method_t dpt_eisa_methods[] = { 20045791Speter /* Device interface */ 20145791Speter DEVMETHOD(device_probe, dpt_eisa_probe), 20245791Speter DEVMETHOD(device_attach, dpt_eisa_attach), 203112780Smdodd DEVMETHOD(device_detach, dpt_detach), 20445791Speter 20545791Speter { 0, 0 } 20645791Speter}; 20745791Speter 20845791Speterstatic driver_t dpt_eisa_driver = { 20945791Speter "dpt", 21045791Speter dpt_eisa_methods, 21159078Smdodd sizeof(dpt_softc_t), 21245791Speter}; 21345791Speter 21445791SpeterDRIVER_MODULE(dpt, eisa, dpt_eisa_driver, dpt_devclass, 0, 0); 215