diff options
Diffstat (limited to 'sys/dev/isa')
-rw-r--r-- | sys/dev/isa/files.isa | 15 | ||||
-rw-r--r-- | sys/dev/isa/files.isapnp | 9 | ||||
-rw-r--r-- | sys/dev/isa/seagate.c | 1374 | ||||
-rw-r--r-- | sys/dev/isa/wss.c | 466 | ||||
-rw-r--r-- | sys/dev/isa/wss_isa.c | 365 | ||||
-rw-r--r-- | sys/dev/isa/wss_isapnp.c | 120 | ||||
-rw-r--r-- | sys/dev/isa/wssreg.h | 62 | ||||
-rw-r--r-- | sys/dev/isa/wssvar.h | 83 | ||||
-rw-r--r-- | sys/dev/isa/ym.c | 869 | ||||
-rw-r--r-- | sys/dev/isa/ym_isapnp.c | 123 | ||||
-rw-r--r-- | sys/dev/isa/ymvar.h | 101 |
11 files changed, 2 insertions, 3585 deletions
diff --git a/sys/dev/isa/files.isa b/sys/dev/isa/files.isa index 863d11c2afd..f3c51352c56 100644 --- a/sys/dev/isa/files.isa +++ b/sys/dev/isa/files.isa @@ -1,4 +1,4 @@ -# $OpenBSD: files.isa,v 1.119 2015/09/30 12:15:12 jung Exp $ +# $OpenBSD: files.isa,v 1.120 2016/08/31 12:46:45 tedu Exp $ # $NetBSD: files.isa,v 1.21 1996/05/16 03:45:55 mycroft Exp $ # # Config file and device description for machine-independent ISA code. @@ -109,11 +109,6 @@ device aha: scsi, isa_dma attach aha at isa with aha_isa file dev/isa/aha.c aha needs-flag -# Seagate ST0[12] ICs -device sea: scsi -attach sea at isa -file dev/isa/seagate.c sea - # UltraStor UHA-[13]4f boards # device declaration in sys/conf/files attach uha at isa with uha_isa: isa_dma @@ -248,14 +243,6 @@ file dev/isa/ad1848.c ad1848 define ics2101 file dev/isa/ics2101.c ics2101 - -# Microsoft Windows Sound System -device wss: audio, isa_dma, ad1848 -file dev/isa/wss.c wss - -attach wss at isa with wss_isa -file dev/isa/wss_isa.c wss & (wss_isa | wss_isapnp) - # ESS Technology ES1887/ES888/ES1888 device ess {} : audio, isa_dma, midibus file dev/isa/ess.c ess diff --git a/sys/dev/isa/files.isapnp b/sys/dev/isa/files.isapnp index 76f1f6c77b5..bf252de8646 100644 --- a/sys/dev/isa/files.isapnp +++ b/sys/dev/isa/files.isapnp @@ -1,4 +1,4 @@ -# $OpenBSD: files.isapnp,v 1.33 2015/05/11 06:46:21 ratchov Exp $ +# $OpenBSD: files.isapnp,v 1.34 2016/08/31 12:46:45 tedu Exp $ # $NetBSD: files.isapnp,v 1.7 1997/10/16 17:16:36 matt Exp $ # # Config file and device description for machine-independent ISAPnP code. @@ -34,8 +34,6 @@ file dev/isa/aic_isapnp.c aic_isapnp attach sb at isapnp with sb_isapnp file dev/isa/sb_isapnp.c sb_isapnp -attach wss at isapnp with wss_isapnp -file dev/isa/wss_isapnp.c wss_isapnp attach ess at isapnp with ess_isapnp file dev/isa/ess_isapnp.c ess_isapnp attach gus at isapnp with gus_isapnp @@ -63,8 +61,3 @@ attach we at isapnp with we_isapnp attach rt at isapnp with rt_isapnp file dev/isa/rt_isapnp.c rt_isapnp -# Yamaha OPL3-SA3 -device ym: audio, isa_dma, ad1848, midibus -attach ym at isapnp with ym_isapnp -file dev/isa/ym.c ym_isapnp -file dev/isa/ym_isapnp.c ym_isapnp diff --git a/sys/dev/isa/seagate.c b/sys/dev/isa/seagate.c deleted file mode 100644 index d79e071d235..00000000000 --- a/sys/dev/isa/seagate.c +++ /dev/null @@ -1,1374 +0,0 @@ -/* $OpenBSD: seagate.c,v 1.38 2014/09/14 14:17:25 jsg Exp $ */ - -/* - * ST01/02, Future Domain TMC-885, TMC-950 SCSI driver - * - * Copyright 1994, Charles Hannum (mycroft@ai.mit.edu) - * Copyright 1994, Kent Palmkvist (kentp@isy.liu.se) - * Copyright 1994, Robert Knier (rknier@qgraph.com) - * Copyright 1992, 1994 Drew Eckhardt (drew@colorado.edu) - * Copyright 1994, Julian Elischer (julian@tfs.com) - * - * Others that has contributed by example code is - * Glen Overby (overby@cray.com) - * Tatu Yllnen - * Brian E Litzinger - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE DEVELOPERS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -/* - * kentp 940307 alpha version based on newscsi-03 version of Julians SCSI-code - * kentp 940314 Added possibility to not use messages - * rknier 940331 Added fast transfer code - * rknier 940407 Added assembler coded data transfers - */ - -/* - * What should really be done: - * - * Add missing tests for timeouts - * Restructure interrupt enable/disable code (runs to long with int disabled) - * Find bug? giving problem with tape status - * Add code to handle Future Domain 840, 841, 880 and 881 - * adjust timeouts (startup is very slow) - * add code to use tagged commands in SCSI2 - * Add code to handle slow devices better (sleep if device not disconnecting) - * Fix unnecessary interrupts - */ - -/* - * Note to users trying to share a disk between DOS and unix: - * The ST01/02 is a translating host-adapter. It is not giving DOS - * the same number of heads/tracks/sectors as specified by the disk. - * It is therefore important to look at what numbers DOS thinks the - * disk has. Use these to disklabel your disk in an appropriate manner - */ - -#include <sys/types.h> -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/kernel.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/device.h> -#include <sys/buf.h> -#include <sys/queue.h> -#include <sys/malloc.h> - -#include <machine/intr.h> -#include <machine/pio.h> - -#include <scsi/scsi_all.h> -#include <scsi/scsi_message.h> -#include <scsi/scsiconf.h> - -#include <dev/isa/isareg.h> -#include <dev/isa/isavar.h> -#include <i386/isa/isa_machdep.h> /* XXX USES ISA HOLE DIRECTLY */ - -#define SEA_SCB_MAX 32 /* allow maximally 8 scsi control blocks */ -#define SCB_TABLE_SIZE 8 /* start with 8 scb entries in table */ -#define BLOCK_SIZE 512 /* size of READ/WRITE areas on SCSI card */ - -/* - * defining SEA_BLINDTRANSFER will make DATA IN and DATA OUT to be done with - * blind transfers, i.e. no check is done for scsi phase changes. This will - * result in data loss if the scsi device does not send its data using - * BLOCK_SIZE bytes at a time. - * If SEA_BLINDTRANSFER defined and SEA_ASSEMBLER also defined will result in - * the use of blind transfers coded in assembler. SEA_ASSEMBLER is no good - * without SEA_BLINDTRANSFER defined. - */ -#define SEA_BLINDTRANSFER /* do blind transfers */ -#define SEA_ASSEMBLER /* Use assembly code for fast transfers */ - -/* - * defining SEA_NOMSGS causes messages not to be used (thereby disabling - * disconnects) - */ -#undef SEA_NOMSGS - -/* - * defining SEA_NODATAOUT makes dataout phase being aborted - */ -#undef SEA_NODATAOUT - -/* Debugging definitions. Should not be used unless you want a lot of - printouts even under normal conditions */ - -#undef SEA_DEBUGQUEUE /* Display info about queue-lengths */ - -/******************************* board definitions **************************/ -/* - * CONTROL defines - */ -#define CMD_RST 0x01 /* scsi reset */ -#define CMD_SEL 0x02 /* scsi select */ -#define CMD_BSY 0x04 /* scsi busy */ -#define CMD_ATTN 0x08 /* scsi attention */ -#define CMD_START_ARB 0x10 /* start arbitration bit */ -#define CMD_EN_PARITY 0x20 /* enable scsi parity generation */ -#define CMD_INTR 0x40 /* enable scsi interrupts */ -#define CMD_DRVR_ENABLE 0x80 /* scsi enable */ - -/* - * STATUS - */ -#define STAT_BSY 0x01 /* scsi busy */ -#define STAT_MSG 0x02 /* scsi msg */ -#define STAT_IO 0x04 /* scsi I/O */ -#define STAT_CD 0x08 /* scsi C/D */ -#define STAT_REQ 0x10 /* scsi req */ -#define STAT_SEL 0x20 /* scsi select */ -#define STAT_PARITY 0x40 /* parity error bit */ -#define STAT_ARB_CMPL 0x80 /* arbitration complete bit */ - -/* - * REQUESTS - */ -#define PH_DATAOUT (0) -#define PH_DATAIN (STAT_IO) -#define PH_CMD (STAT_CD) -#define PH_STAT (STAT_CD | STAT_IO) -#define PH_MSGOUT (STAT_MSG | STAT_CD) -#define PH_MSGIN (STAT_MSG | STAT_CD | STAT_IO) - -#define PH_MASK (STAT_MSG | STAT_CD | STAT_IO) - -#define PH_INVALID 0xff - -#define SEA_RAMOFFSET 0x00001800 - -#define BASE_CMD (CMD_INTR | CMD_EN_PARITY) - -#define SEAGATE 1 /* Seagate ST0[12] */ -#define FDOMAIN 2 /* Future Domain TMC-{885,950} */ -#define FDOMAIN840 3 /* Future Domain TMC-{84[01],88[01]} */ - -/******************************************************************************/ - -/* scsi control block used to keep info about a scsi command */ -struct sea_scb { - u_char *data; /* position in data buffer so far */ - int datalen; /* bytes remaining to transfer */ - TAILQ_ENTRY(sea_scb) chain; - struct scsi_xfer *xs; /* the scsi_xfer for this cmd */ - int flags; /* status of the instruction */ -#define SCB_FREE 0 -#define SCB_ACTIVE 1 -#define SCB_ABORTED 2 -#define SCB_TIMEOUT 4 -#define SCB_ERROR 8 -}; - -/* - * data structure describing current status of the scsi bus. One for each - * controller card. - */ -struct sea_softc { - struct device sc_dev; - struct isadev sc_id; - void *sc_ih; - - int type; /* board type */ - caddr_t maddr; /* Base address for card */ - caddr_t maddr_cr_sr; /* Address of control and status reg */ - caddr_t maddr_dr; /* Address of data register */ - - struct scsi_link sc_link; /* prototype for subdevs */ - TAILQ_HEAD(, sea_scb) free_list, ready_list, nexus_list; - struct sea_scb *nexus; /* currently connected command */ - int numscbs; /* number of scsi control blocks */ - struct sea_scb scb[SCB_TABLE_SIZE]; - - struct mutex sc_scb_mtx; - struct scsi_iopool sc_iopool; - - int our_id; /* our scsi id */ - u_char our_id_mask; - volatile u_char busy[8]; /* index=target, bit=lun, Keep track of - busy luns at device target */ -}; - -/* flag showing if main routine is running. */ -static volatile int main_running = 0; - -#define STATUS (*(volatile u_char *)sea->maddr_cr_sr) -#define CONTROL STATUS -#define DATA (*(volatile u_char *)sea->maddr_dr) - -/* - * These are "special" values for the tag parameter passed to sea_select - * Not implemented right now. - */ -#define TAG_NEXT -1 /* Use next free tag */ -#define TAG_NONE -2 /* - * Establish I_T_L nexus instead of I_T_L_Q - * even on SCSI-II devices. - */ - -typedef struct { - char *signature; - int offset, length; - int type; -} BiosSignature; - -/* - * Signatures for automatic recognition of board type - */ -static const BiosSignature signatures[] = { -{"ST01 v1.7 (C) Copyright 1987 Seagate", 15, 37, SEAGATE}, -{"SCSI BIOS 2.00 (C) Copyright 1987 Seagate", 15, 40, SEAGATE}, - -/* - * The following two lines are NOT mistakes. One detects ROM revision - * 3.0.0, the other 3.2. Since seagate has only one type of SCSI adapter, - * and this is not going to change, the "SEAGATE" and "SCSI" together - * are probably "good enough" - */ -{"SEAGATE SCSI BIOS ", 16, 17, SEAGATE}, -{"SEAGATE SCSI BIOS ", 17, 17, SEAGATE}, - -/* - * However, future domain makes several incompatible SCSI boards, so specific - * signatures must be used. - */ -{"FUTURE DOMAIN CORP. (C) 1986-1989 V5.0C2/14/89", 5, 45, FDOMAIN}, -{"FUTURE DOMAIN CORP. (C) 1986-1989 V6.0A7/28/89", 5, 46, FDOMAIN}, -{"FUTURE DOMAIN CORP. (C) 1986-1990 V6.0105/31/90",5, 47, FDOMAIN}, -{"FUTURE DOMAIN CORP. (C) 1986-1990 V6.0209/18/90",5, 47, FDOMAIN}, -{"FUTURE DOMAIN CORP. (C) 1986-1990 V7.009/18/90", 5, 46, FDOMAIN}, -{"FUTURE DOMAIN CORP. (C) 1992 V8.00.004/02/92", 5, 44, FDOMAIN}, -{"FUTURE DOMAIN TMC-950", 5, 21, FDOMAIN}, -}; - -#define nsignatures (sizeof(signatures) / sizeof(signatures[0])) - -#ifdef notdef -static const char *bases[] = { - (char *) 0xc8000, (char *) 0xca000, (char *) 0xcc000, - (char *) 0xce000, (char *) 0xdc000, (char *) 0xde000 -}; - -#define nbases (sizeof(bases) / sizeof(bases[0])) -#endif - -void *sea_scb_alloc(void *); -int seaintr(void *); -void sea_scsi_cmd(struct scsi_xfer *); -int sea_poll(struct sea_softc *, struct scsi_xfer *, int); -int sea_select(struct sea_softc *sea, struct sea_scb *scb); -int sea_transfer_pio(struct sea_softc *sea, u_char *phase, - int *count, u_char **data); -int sea_abort(struct sea_softc *, struct sea_scb *scb); -static void sea_main(void); -static void sea_information_transfer(struct sea_softc *); -void sea_timeout(void *); -void sea_done(struct sea_softc *, struct sea_scb *); -void sea_scb_free(void *, void *); -void sea_init(struct sea_softc *); -void sea_send_scb(struct sea_softc *sea, struct sea_scb *scb); -void sea_reselect(struct sea_softc *sea); - -struct scsi_adapter sea_switch = { - sea_scsi_cmd, - scsi_minphys, /* no special minphys(), since driver uses PIO */ - 0, - 0, -}; - -int seaprobe(struct device *, void *, void *); -void seaattach(struct device *, struct device *, void *); -int seaprint(void *, const char *); - -struct cfattach sea_ca = { - sizeof(struct sea_softc), seaprobe, seaattach -}; - -struct cfdriver sea_cd = { - NULL, "sea", DV_DULL -}; - -#ifdef SEA_DEBUGQUEUE -void -sea_queue_length(struct sea_softc *sea) -{ - struct sea_scb *scb; - int connected, issued, disconnected; - - connected = sea->nexus ? 1 : 0; - issued = 0; - TAILQ_FOREACH(scb, &sea->ready_list, chain) - issued++; - disconnected = 0; - TAILQ_FOREACH(scb, &sea->nexus_list, chain) - disconnected++; - printf("%s: length: %d/%d/%d\n", sea->sc_dev.dv_xname, connected, - issued, disconnected); -} -#endif - -/* - * Check if the device can be found at the port given and if so, detect the - * type the type of board. Set it up ready for further work. Takes the isa_dev - * structure from autoconf as an argument. - * Returns 1 if card recognized, 0 if errors. - */ -int -seaprobe(struct device *parent, void *match, void *aux) -{ - struct sea_softc *sea = match; - struct isa_attach_args *ia = aux; - int i; - - /* - * Could try to find a board by looking through all possible addresses. - * This is not done the right way now, because I have not found a way - * to get a boards virtual memory address given its physical. There is - * a function that returns the physical address for a given virtual - * address, but not the other way around. - */ - - if (ia->ia_maddr == MADDRUNK) { - /* XXX */ - return 0; - } else - sea->maddr = ISA_HOLE_VADDR(ia->ia_maddr); - - /* check board type */ /* No way to define this through config */ - for (i = 0; i < nsignatures; i++) - if (!bcmp(sea->maddr + signatures[i].offset, - signatures[i].signature, signatures[i].length)) { - sea->type = signatures[i].type; - break; - } - - /* Find controller and data memory addresses */ - switch (sea->type) { - case SEAGATE: - case FDOMAIN840: - sea->maddr_cr_sr = - (void *) (((u_char *)sea->maddr) + 0x1a00); - sea->maddr_dr = - (void *) (((u_char *)sea->maddr) + 0x1c00); - break; - case FDOMAIN: - sea->maddr_cr_sr = - (void *) (((u_char *)sea->maddr) + 0x1c00); - sea->maddr_dr = - (void *) (((u_char *)sea->maddr) + 0x1e00); - break; - default: -#if 0 - printf("%s: board type unknown at address %p\n", - sea->sc_dev.dv_xname, sea->maddr); -#endif - return 0; - } - - /* Test controller RAM (works the same way on future domain cards?) */ - *((u_char *)sea->maddr + SEA_RAMOFFSET) = 0xa5; - *((u_char *)sea->maddr + SEA_RAMOFFSET + 1) = 0x5a; - - if ((*((u_char *)sea->maddr + SEA_RAMOFFSET) != 0xa5) || - (*((u_char *)sea->maddr + SEA_RAMOFFSET + 1) != 0x5a)) { - printf("%s: board RAM failure\n", sea->sc_dev.dv_xname); - return 0; - } - - ia->ia_drq = DRQUNK; - ia->ia_msize = 0x2000; - ia->ia_iosize = 0; - return 1; -} - -int -seaprint(void *aux, const char *name) -{ - if (name != NULL) - printf("%s: scsibus ", name); - return UNCONF; -} - -/* - * Attach all sub-devices we can find - */ -void -seaattach(struct device *parent, struct device *self, void *aux) -{ - struct isa_attach_args *ia = aux; - struct sea_softc *sea = (void *)self; - struct scsibus_attach_args saa; - - sea_init(sea); - - /* - * fill in the prototype scsi_link. - */ - sea->sc_link.adapter_softc = sea; - sea->sc_link.adapter_target = sea->our_id; - sea->sc_link.adapter = &sea_switch; - sea->sc_link.openings = 1; - sea->sc_link.pool = &sea->sc_iopool; - - printf("\n"); - - sea->sc_ih = isa_intr_establish(ia->ia_ic, ia->ia_irq, IST_EDGE, - IPL_BIO, seaintr, sea, sea->sc_dev.dv_xname); - - bzero(&saa, sizeof(saa)); - saa.saa_sc_link = &sea->sc_link; - - /* - * ask the adapter what subunits are present - */ - config_found(self, &saa, seaprint); -} - -/* - * Catch an interrupt from the adaptor - */ -int -seaintr(void *arg) -{ - struct sea_softc *sea = arg; - -#ifdef DEBUG /* extra overhead, and only needed for intr debugging */ - if ((STATUS & STAT_PARITY) == 0 && - (STATUS & (STAT_SEL | STAT_IO)) != (STAT_SEL | STAT_IO)) - return 0; -#endif - -loop: - /* dispatch to appropriate routine if found and done=0 */ - /* should check to see that this card really caused the interrupt */ - - if (STATUS & STAT_PARITY) { - /* Parity error interrupt */ - printf("%s: parity error\n", sea->sc_dev.dv_xname); - return 1; - } - - if ((STATUS & (STAT_SEL | STAT_IO)) == (STAT_SEL | STAT_IO)) { - /* Reselect interrupt */ - sea_reselect(sea); - if (!main_running) - sea_main(); - goto loop; - } - - return 1; -} - -/* - * Setup data structures, and reset the board and the SCSI bus. - */ -void -sea_init(struct sea_softc *sea) -{ - int i; - - /* Reset the scsi bus (I don't know if this is needed */ - CONTROL = BASE_CMD | CMD_DRVR_ENABLE | CMD_RST; - delay(25); /* hold reset for at least 25 microseconds */ - CONTROL = BASE_CMD; - delay(10); /* wait a Bus Clear Delay (800 ns + bus free delay (800 ns) */ - - /* Set our id (don't know anything about this) */ - switch (sea->type) { - case SEAGATE: - sea->our_id = 7; - break; - case FDOMAIN: - case FDOMAIN840: - sea->our_id = 6; - break; - } - sea->our_id_mask = 1 << sea->our_id; - - /* init fields used by our routines */ - sea->nexus = 0; - TAILQ_INIT(&sea->ready_list); - TAILQ_INIT(&sea->nexus_list); - TAILQ_INIT(&sea->free_list); - mtx_init(&sea->sc_scb_mtx, IPL_BIO); - scsi_iopool_init(&sea->sc_iopool, sea, sea_scb_alloc, sea_scb_free); - - for (i = 0; i < 8; i++) - sea->busy[i] = 0x00; - - /* link up the free list of scbs */ - sea->numscbs = SCB_TABLE_SIZE; - for (i = 0; i < SCB_TABLE_SIZE; i++) { - TAILQ_INSERT_TAIL(&sea->free_list, &sea->scb[i], chain); - } -} - -/* - * start a scsi operation given the command and the data address. Also needs - * the unit, target and lu. - */ -void -sea_scsi_cmd(struct scsi_xfer *xs) -{ - struct scsi_link *sc_link = xs->sc_link; - struct sea_softc *sea = sc_link->adapter_softc; - struct sea_scb *scb; - int flags; - int s; - - SC_DEBUG(sc_link, SDEV_DB2, ("sea_scsi_cmd\n")); - - flags = xs->flags; - scb = xs->io; - scb->flags = SCB_ACTIVE; - scb->xs = xs; - timeout_set(&scb->xs->stimeout, sea_timeout, scb); - - if (flags & SCSI_RESET) { - /* - * Try to send a reset command to the card. - * XXX Not implemented. - */ - printf("%s: resetting\n", sea->sc_dev.dv_xname); - xs->error = XS_DRIVER_STUFFUP; - scsi_done(xs); - return; - } - - /* - * Put all the arguments for the xfer in the scb - */ - scb->datalen = xs->datalen; - scb->data = xs->data; - -#ifdef SEA_DEBUGQUEUE - sea_queue_length(sea); -#endif - - s = splbio(); - - sea_send_scb(sea, scb); - - /* - * Usually return SUCCESSFULLY QUEUED - */ - if ((flags & SCSI_POLL) == 0) { - timeout_add_msec(&scb->xs->stimeout, xs->timeout); - splx(s); - return; - } - - splx(s); - - /* - * If we can't use interrupts, poll on completion - */ - if (sea_poll(sea, xs, xs->timeout)) { - sea_timeout(scb); - if (sea_poll(sea, xs, 2000)) - sea_timeout(scb); - } -} - -/* - * Get a free scb. - */ -void * -sea_scb_alloc(void *xsea) -{ - struct sea_softc *sea = xsea; - struct sea_scb *scb; - - mtx_enter(&sea->sc_scb_mtx); - scb = TAILQ_FIRST(&sea->free_list); - if (scb) { - TAILQ_REMOVE(&sea->free_list, scb, chain); - } - mtx_leave(&sea->sc_scb_mtx); - - return scb; -} - -/* - * Try to send this command to the board. Because this board does not use any - * mailboxes, this routine simply adds the command to the queue held by the - * sea_softc structure. - * A check is done to see if the command contains a REQUEST_SENSE command, and - * if so the command is put first in the queue, otherwise the command is added - * to the end of the queue. ?? Not correct ?? - */ -void -sea_send_scb(struct sea_softc *sea, struct sea_scb *scb) -{ - - TAILQ_INSERT_TAIL(&sea->ready_list, scb, chain); - /* Try to do some work on the card. */ - if (!main_running) - sea_main(); -} - -/* - * Coroutine that runs as long as more work can be done on the seagate host - * adapter in a system. Both sea_scsi_cmd and sea_intr will try to start it in - * case it is not running. - */ -void -sea_main(void) -{ - struct sea_softc *sea; - struct sea_scb *scb; - int done; - int unit; - int s; - - main_running = 1; - - /* - * This should not be run with interrupts disabled, but use the splx - * code instead. - */ -loop: - done = 1; - for (unit = 0; unit < sea_cd.cd_ndevs; unit++) { - sea = sea_cd.cd_devs[unit]; - if (!sea) - continue; - s = splbio(); - if (!sea->nexus) { - /* - * Search through the ready_list for a command - * destined for a target that's not busy. - */ - TAILQ_FOREACH(scb, &sea->ready_list, chain) { - if (!(sea->busy[scb->xs->sc_link->target] & - (1 << scb->xs->sc_link->lun))) { - TAILQ_REMOVE(&sea->ready_list, scb, - chain); - - /* Re-enable interrupts. */ - splx(s); - - /* - * Attempt to establish an I_T_L nexus. - * On success, sea->nexus is set. - * On failure, we must add the command - * back to the issue queue so we can - * keep trying. - */ - - /* - * REQUEST_SENSE commands are issued - * without tagged queueing, even on - * SCSI-II devices because the - * contingent alligence condition - * exists for the entire unit. - */ - - /* - * First check that if any device has - * tried a reconnect while we have done - * other things with interrupts - * disabled. - */ - - if ((STATUS & (STAT_SEL | STAT_IO)) == - (STAT_SEL | STAT_IO)) { - sea_reselect(sea); - break; - } - if (sea_select(sea, scb)) { - s = splbio(); - TAILQ_INSERT_HEAD(&sea->ready_list, - scb, chain); - splx(s); - } else - break; - } /* if target/lun is not busy */ - } /* for scb */ - if (!sea->nexus) { - /* check for reselection phase */ - if ((STATUS & (STAT_SEL | STAT_IO)) == - (STAT_SEL | STAT_IO)) { - sea_reselect(sea); - } - } - } /* if (!sea->nexus) */ - - splx(s); - if (sea->nexus) { /* we are connected. Do the task */ - sea_information_transfer(sea); - done = 0; - } else - break; - } /* for instance */ - - if (!done) - goto loop; - - main_running = 0; -} - -void -sea_scb_free(void *xsea, void *xscb) -{ - struct sea_softc *sea = xsea; - struct sea_scb *scb = xscb; - - scb->flags = SCB_FREE; - - mtx_enter(&sea->sc_scb_mtx); - TAILQ_INSERT_HEAD(&sea->free_list, scb, chain); - mtx_leave(&sea->sc_scb_mtx); -} - -void -sea_timeout(void *arg) -{ - struct sea_scb *scb = arg; - struct scsi_xfer *xs = scb->xs; - struct scsi_link *sc_link = xs->sc_link; - struct sea_softc *sea = sc_link->adapter_softc; - int s; - - sc_print_addr(sc_link); - printf("timed out"); - - s = splbio(); - - /* - * If it has been through before, then - * a previous abort has failed, don't - * try abort again - */ - if (scb->flags & SCB_ABORTED) { - /* abort timed out */ - printf(" AGAIN\n"); - scb->xs->retries = 0; - scb->flags |= SCB_ABORTED; - sea_done(sea, scb); - } else { - /* abort the operation that has timed out */ - printf("\n"); - scb->flags |= SCB_ABORTED; - sea_abort(sea, scb); - /* 2 secs for the abort */ - if ((xs->flags & SCSI_POLL) == 0) - timeout_add_sec(&scb->xs->stimeout, 2); - } - - splx(s); -} - -void -sea_reselect(struct sea_softc *sea) -{ - u_char target_mask; - int i; - u_char lun, phase; - u_char msg[3]; - int len; - u_char *data; - struct sea_scb *scb; - int abort = 0; - - if (!((target_mask = STATUS) & STAT_SEL)) { - printf("%s: wrong state 0x%x\n", sea->sc_dev.dv_xname, - target_mask); - return; - } - - /* wait for a device to win the reselection phase */ - /* signals this by asserting the I/O signal */ - for (i = 10; i && (STATUS & (STAT_SEL | STAT_IO | STAT_BSY)) != - (STAT_SEL | STAT_IO | 0); i--); - /* !! Check for timeout here */ - /* the data bus contains original initiator id ORed with target id */ - target_mask = DATA; - /* see that we really are the initiator */ - if (!(target_mask & sea->our_id_mask)) { - printf("%s: polled reselection was not for me: 0x%x\n", - sea->sc_dev.dv_xname, target_mask); - return; - } - /* find target who won */ - target_mask &= ~sea->our_id_mask; - /* host responds by asserting the BSY signal */ - CONTROL = BASE_CMD | CMD_DRVR_ENABLE | CMD_BSY; - /* target should respond by deasserting the SEL signal */ - for (i = 50000; i && (STATUS & STAT_SEL); i++); - /* remove the busy status */ - CONTROL = BASE_CMD | CMD_DRVR_ENABLE; - /* we are connected. Now we wait for the MSGIN condition */ - for (i = 50000; i && !(STATUS & STAT_REQ); i--); - /* !! Add timeout check here */ - /* hope we get an IDENTIFY message */ - len = 3; - data = msg; - phase = PH_MSGIN; - sea_transfer_pio(sea, &phase, &len, &data); - - if (MSG_ISIDENTIFY(msg[0])) { - printf("%s: expecting IDENTIFY message, got 0x%x\n", - sea->sc_dev.dv_xname, msg[0]); - abort = 1; - scb = NULL; - } else { - lun = msg[0] & 0x07; - - /* - * Find the command corresponding to the I_T_L or I_T_L_Q nexus - * we just reestablished, and remove it from the disconnected - * queue. - */ - TAILQ_FOREACH(scb, &sea->nexus_list, chain) - if (target_mask == (1 << scb->xs->sc_link->target) && - lun == scb->xs->sc_link->lun) { - TAILQ_REMOVE(&sea->nexus_list, scb, - chain); - break; - } - if (!scb) { - printf("%s: target %02x lun %d not disconnected\n", - sea->sc_dev.dv_xname, target_mask, lun); - /* - * Since we have an established nexus that we can't do - * anything with, we must abort it. - */ - abort = 1; - } - } - - if (abort) { - msg[0] = MSG_ABORT; - len = 1; - data = msg; - phase = PH_MSGOUT; - CONTROL = BASE_CMD | CMD_ATTN; - sea_transfer_pio(sea, &phase, &len, &data); - } else - sea->nexus = scb; - - return; -} - -/* - * Transfer data in given phase using polled I/O. - */ -int -sea_transfer_pio(struct sea_softc *sea, u_char *phase, int *count, u_char **data) -{ - u_char p = *phase, tmp; - int c = *count; - u_char *d = *data; - int timeout; - - do { - /* - * Wait for assertion of REQ, after which the phase bits will - * be valid. - */ - for (timeout = 0; timeout < 50000; timeout++) - if ((tmp = STATUS) & STAT_REQ) - break; - if (!(tmp & STAT_REQ)) { - printf("%s: timeout waiting for STAT_REQ\n", - sea->sc_dev.dv_xname); - break; - } - - /* - * Check for phase mismatch. Reached if the target decides - * that it has finished the transfer. - */ - if (sea->type == FDOMAIN840) - tmp = ((tmp & 0x08) >> 2) | - ((tmp & 0x02) << 2) | - (tmp & 0xf5); - if ((tmp & PH_MASK) != p) - break; - - /* Do actual transfer from SCSI bus to/from memory. */ - if (!(p & STAT_IO)) - DATA = *d; - else - *d = DATA; - ++d; - - /* - * The SCSI standard suggests that in MSGOUT phase, the - * initiator should drop ATN on the last byte of the message - * phase after REQ has been asserted for the handshake but - * before the initiator raises ACK. - * Don't know how to accomplish this on the ST01/02. - */ - -#if 0 - /* - * XXX - * The st01 code doesn't wait for STAT_REQ to be deasserted. - * Is this ok? - */ - for (timeout = 0; timeout < 200000L; timeout++) - if (!(STATUS & STAT_REQ)) - break; - if (STATUS & STAT_REQ) - printf("%s: timeout on wait for !STAT_REQ", - sea->sc_dev.dv_xname); -#endif - } while (--c); - - *count = c; - *data = d; - tmp = STATUS; - if (tmp & STAT_REQ) - *phase = tmp & PH_MASK; - else - *phase = PH_INVALID; - - if (c && (*phase != p)) - return -1; - return 0; -} - -/* - * Establish I_T_L or I_T_L_Q nexus for new or existing command including - * ARBITRATION, SELECTION, and initial message out for IDENTIFY and queue - * messages. Return -1 if selection could not execute for some reason, 0 if - * selection succeded or failed because the target did not respond. - */ -int -sea_select(struct sea_softc *sea, struct sea_scb *scb) -{ - u_char msg[3], phase; - u_char *data; - int len; - int timeout; - - CONTROL = BASE_CMD; - DATA = sea->our_id_mask; - CONTROL = (BASE_CMD & ~CMD_INTR) | CMD_START_ARB; - - /* wait for arbitration to complete */ - for (timeout = 0; timeout < 3000000L; timeout++) - if (STATUS & STAT_ARB_CMPL) - break; - if (!(STATUS & STAT_ARB_CMPL)) { - if (STATUS & STAT_SEL) { - printf("%s: arbitration lost\n", sea->sc_dev.dv_xname); - scb->flags |= SCB_ERROR; - } else { - printf("%s: arbitration timeout\n", - sea->sc_dev.dv_xname); - scb->flags |= SCB_TIMEOUT; - } - CONTROL = BASE_CMD; - return -1; - } - - delay(2); - DATA = (u_char)((1 << scb->xs->sc_link->target) | sea->our_id_mask); - CONTROL = -#ifdef SEA_NOMSGS - (BASE_CMD & ~CMD_INTR) | CMD_DRVR_ENABLE | CMD_SEL; -#else - (BASE_CMD & ~CMD_INTR) | CMD_DRVR_ENABLE | CMD_SEL | CMD_ATTN; -#endif - delay(1); - - /* wait for a bsy from target */ - for (timeout = 0; timeout < 2000000L; timeout++) - if (STATUS & STAT_BSY) - break; - if (!(STATUS & STAT_BSY)) { - /* should return some error to the higher level driver */ - CONTROL = BASE_CMD; - scb->flags |= SCB_TIMEOUT; - return 0; - } - - /* Try to make the target to take a message from us */ -#ifdef SEA_NOMSGS - CONTROL = (BASE_CMD & ~CMD_INTR) | CMD_DRVR_ENABLE; -#else - CONTROL = (BASE_CMD & ~CMD_INTR) | CMD_DRVR_ENABLE | CMD_ATTN; -#endif - delay(1); - - /* should start a msg_out phase */ - for (timeout = 0; timeout < 2000000L; timeout++) - if (STATUS & STAT_REQ) - break; - /* Remove ATN. */ - CONTROL = BASE_CMD | CMD_DRVR_ENABLE; - if (!(STATUS & STAT_REQ)) { - /* - * This should not be taken as an error, but more like an - * unsupported feature! Should set a flag indicating that the - * target don't support messages, and continue without failure. - * (THIS IS NOT AN ERROR!) - */ - } else { - msg[0] = MSG_IDENTIFY(scb->xs->sc_link->lun, 1); - len = 1; - data = msg; - phase = PH_MSGOUT; - /* Should do test on result of sea_transfer_pio(). */ - sea_transfer_pio(sea, &phase, &len, &data); - } - if (!(STATUS & STAT_BSY)) - printf("%s: after successful arbitrate: no STAT_BSY!\n", - sea->sc_dev.dv_xname); - - sea->nexus = scb; - sea->busy[scb->xs->sc_link->target] |= 1 << scb->xs->sc_link->lun; - /* This assignment should depend on possibility to send a message to target. */ - CONTROL = BASE_CMD | CMD_DRVR_ENABLE; - /* XXX Reset pointer in command? */ - return 0; -} - -/* - * Send an abort to the target. Return 1 success, 0 on failure. - */ -int -sea_abort(struct sea_softc *sea, struct sea_scb *scb) -{ - struct sea_scb *tmp; - u_char msg, phase, *msgptr; - int len; - - /* - * If the command hasn't been issued yet, we simply remove it from the - * issue queue - * XXX Could avoid this loop. - */ - TAILQ_FOREACH(tmp, &sea->ready_list, chain) - if (scb == tmp) { - TAILQ_REMOVE(&sea->ready_list, scb, chain); - /* XXX Set some type of error result for operation. */ - return 1; - } - - /* - * If any commands are connected, we're going to fail the abort and let - * the high level SCSI driver retry at a later time or issue a reset. - */ - if (sea->nexus) - return 0; - - /* - * If the command is currently disconnected from the bus, and there are - * no connected commands, we reconnect the I_T_L or I_T_L_Q nexus - * associated with it, go into message out, and send an abort message. - */ - TAILQ_FOREACH(tmp, &sea->nexus_list, chain) - if (scb == tmp) { - if (sea_select(sea, scb)) - return 0; - - msg = MSG_ABORT; - msgptr = &msg; - len = 1; - phase = PH_MSGOUT; - CONTROL = BASE_CMD | CMD_ATTN; - sea_transfer_pio(sea, &phase, &len, &msgptr); - - TAILQ_FOREACH(tmp, &sea->nexus_list, chain) - if (scb == tmp) { - TAILQ_REMOVE(&sea->nexus_list, - scb, chain); - /* XXX Set some type of error result - for the operation. */ - return 1; - } - } - - /* Command not found in any queue; race condition? */ - return 1; -} - -void -sea_done(struct sea_softc *sea, struct sea_scb *scb) -{ - struct scsi_xfer *xs = scb->xs; - - timeout_del(&scb->xs->stimeout); - - xs->resid = scb->datalen; - - /* XXXX need to get status */ - if (scb->flags == SCB_ACTIVE) { - xs->resid = 0; - } else { - if (scb->flags & (SCB_TIMEOUT | SCB_ABORTED)) - xs->error = XS_TIMEOUT; - if (scb->flags & SCB_ERROR) - xs->error = XS_DRIVER_STUFFUP; - } - scsi_done(xs); -} - -/* - * Wait for completion of command in polled mode. - */ -int -sea_poll(struct sea_softc *sea, struct scsi_xfer *xs, int count) -{ - int s; - - while (count) { - /* try to do something */ - s = splbio(); - if (!main_running) - sea_main(); - splx(s); - if (xs->flags & ITSDONE) - return 0; - delay(1000); - count--; - } - return 1; -} - -/* - * Do the transfer. We know we are connected. Update the flags, and call - * sea_done() when task accomplished. Dialog controlled by the target. - */ -void -sea_information_transfer(struct sea_softc *sea) -{ - int timeout; - u_char msgout = MSG_NOOP; - int len; - int s; - u_char *data; - u_char phase, tmp, old_phase = PH_INVALID; - struct sea_scb *scb = sea->nexus; - int loop; - - for (timeout = 0; timeout < 10000000L; timeout++) { - tmp = STATUS; - if (tmp & STAT_PARITY) - printf("%s: parity error detected\n", - sea->sc_dev.dv_xname); - if (!(tmp & STAT_BSY)) { - for (loop = 0; loop < 20; loop++) - if ((tmp = STATUS) & STAT_BSY) - break; - if (!(tmp & STAT_BSY)) { - printf("%s: !STAT_BSY unit in data transfer!\n", - sea->sc_dev.dv_xname); - s = splbio(); - sea->nexus = NULL; - scb->flags = SCB_ERROR; - splx(s); - sea_done(sea, scb); - return; - } - } - - /* we only have a valid SCSI phase when REQ is asserted */ - if (!(tmp & STAT_REQ)) - continue; - - if (sea->type == FDOMAIN840) - tmp = ((tmp & 0x08) >> 2) | - ((tmp & 0x02) << 2) | - (tmp & 0xf5); - phase = tmp & PH_MASK; - if (phase != old_phase) - old_phase = phase; - - switch (phase) { - case PH_DATAOUT: -#ifdef SEA_NODATAOUT - printf("%s: SEA_NODATAOUT set, attempted DATAOUT aborted\n", - sea->sc_dev.dv_xname); - msgout = MSG_ABORT; - CONTROL = BASE_CMD | CMD_ATTN; - break; -#endif - case PH_DATAIN: - if (!scb->data) - printf("no data address!\n"); -#ifdef SEA_BLINDTRANSFER - if (scb->datalen && !(scb->datalen % BLOCK_SIZE)) { - while (scb->datalen) { - for (loop = 0; loop < 50000; loop++) - if ((tmp = STATUS) & STAT_REQ) - break; - if (!(tmp & STAT_REQ)) { - printf("%s: timeout waiting for STAT_REQ\n", - sea->sc_dev.dv_xname); - /* XXX Do something? */ - } - if (sea->type == FDOMAIN840) - tmp = ((tmp & 0x08) >> 2) | - ((tmp & 0x02) << 2) | - (tmp & 0xf5); - if ((tmp & PH_MASK) != phase) - break; - if (!(phase & STAT_IO)) { -#ifdef SEA_ASSEMBLER - int block = BLOCK_SIZE; - void *a = sea->maddr_dr; - asm("shr $2, %%ecx\n\t\ - cld\n\t\ - rep\n\t\ - movsl" : - "=S" (scb->data), - "=c" (block) , - "=D" (a) : - "0" (scb->data), - "2" (a), - "1" (block) ); -#else - int count; - for (count = 0; - count < BLOCK_SIZE; - count++) - DATA = *(scb->data++); -#endif - } else { -#ifdef SEA_ASSEMBLER - int block = BLOCK_SIZE; - void *a = sea->maddr_dr; - asm("shr $2, %%ecx\n\t\ - cld\n\t\ - rep\n\t\ - movsl" : - "=D" (scb->data), "=c" (block) , - "=S" (a) : - "0" (scb->data), - "2" (a) , - "1" (block) ); -#else - int count; - for (count = 0; - count < BLOCK_SIZE; - count++) - *(scb->data++) = DATA; -#endif - } - scb->datalen -= BLOCK_SIZE; - } - } -#endif - if (scb->datalen) - sea_transfer_pio(sea, &phase, &scb->datalen, - &scb->data); - break; - case PH_MSGIN: - /* Multibyte messages should not be present here. */ - len = 1; - data = &tmp; - sea_transfer_pio(sea, &phase, &len, &data); - /* scb->MessageIn = tmp; */ - - switch (tmp) { - case MSG_ABORT: - scb->flags = SCB_ABORTED; - printf("sea: command aborted by target\n"); - CONTROL = BASE_CMD; - sea_done(sea, scb); - return; - case MSG_CMDCOMPLETE: - s = splbio(); - sea->nexus = NULL; - splx(s); - sea->busy[scb->xs->sc_link->target] &= - ~(1 << scb->xs->sc_link->lun); - CONTROL = BASE_CMD; - sea_done(sea, scb); - return; - case MSG_MESSAGE_REJECT: - printf("%s: message_reject received\n", - sea->sc_dev.dv_xname); - break; - case MSG_DISCONNECT: - s = splbio(); - TAILQ_INSERT_TAIL(&sea->nexus_list, - scb, chain); - sea->nexus = NULL; - CONTROL = BASE_CMD; - splx(s); - return; - case MSG_SAVEDATAPOINTER: - case MSG_RESTOREPOINTERS: - /* save/restore of pointers are ignored */ - break; - default: - /* - * This should be handled in the pio data - * transfer phase, as the ATN should be raised - * before ACK goes false when rejecting a - * message. - */ - printf("%s: unknown message in: %x\n", - sea->sc_dev.dv_xname, tmp); - break; - } /* switch (tmp) */ - break; - case PH_MSGOUT: - len = 1; - data = &msgout; - /* sea->last_message = msgout; */ - sea_transfer_pio(sea, &phase, &len, &data); - if (msgout == MSG_ABORT) { - printf("%s: sent message abort to target\n", - sea->sc_dev.dv_xname); - s = splbio(); - sea->busy[scb->xs->sc_link->target] &= - ~(1 << scb->xs->sc_link->lun); - sea->nexus = NULL; - scb->flags = SCB_ABORTED; - splx(s); - /* enable interrupt from scsi */ - sea_done(sea, scb); - return; - } - msgout = MSG_NOOP; - break; - case PH_CMD: - len = scb->xs->cmdlen; - data = (char *) scb->xs->cmd; - sea_transfer_pio(sea, &phase, &len, &data); - break; - case PH_STAT: - len = 1; - data = &tmp; - sea_transfer_pio(sea, &phase, &len, &data); - scb->xs->status = tmp; - break; - default: - printf("sea: unknown phase\n"); - } /* switch (phase) */ - } /* for (...) */ - - /* If we get here we have got a timeout! */ - printf("%s: timeout in data transfer\n", sea->sc_dev.dv_xname); - scb->flags = SCB_TIMEOUT; - /* XXX Should I clear scsi-bus state? */ - sea_done(sea, scb); -} diff --git a/sys/dev/isa/wss.c b/sys/dev/isa/wss.c deleted file mode 100644 index 50ae7d4cc77..00000000000 --- a/sys/dev/isa/wss.c +++ /dev/null @@ -1,466 +0,0 @@ -/* $OpenBSD: wss.c,v 1.28 2015/05/09 10:27:32 jsg Exp $ */ -/* $NetBSD: wss.c,v 1.42 1998/01/19 22:18:23 augustss Exp $ */ - -/* - * Copyright (c) 1994 John Brezak - * Copyright (c) 1991-1993 Regents of the University of California. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the Computer Systems - * Engineering Group at Lawrence Berkeley Laboratory. - * 4. Neither the name of the University nor of the Laboratory may be used - * to endorse or promote products derived from this software without - * specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ - -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/syslog.h> -#include <sys/device.h> -#include <sys/buf.h> - -#include <machine/cpu.h> -#include <machine/intr.h> -#include <machine/bus.h> - -#include <sys/audioio.h> -#include <dev/audio_if.h> - -#include <dev/isa/isavar.h> -#include <dev/isa/isadmavar.h> - -#include <dev/ic/ad1848reg.h> -#include <dev/isa/ad1848var.h> -#include <dev/isa/wssreg.h> -#include <dev/isa/wssvar.h> -#include <dev/isa/madreg.h> - -#ifdef AUDIO_DEBUG -#define DPRINTF(x) if (wssdebug) printf x -int wssdebug = 0; -#else -#define DPRINTF(x) -#endif - -struct audio_device wss_device = { - "wss,ad1848", - "", - "WSS" -}; - -int wss_getdev(void *, struct audio_device *); - -int wss_mixer_set_port(void *, mixer_ctrl_t *); -int wss_mixer_get_port(void *, mixer_ctrl_t *); -int wss_query_devinfo(void *, mixer_devinfo_t *); - -/* - * Define our interface to the higher level audio driver. - */ - -struct audio_hw_if wss_hw_if = { - ad1848_open, - ad1848_close, - NULL, - ad1848_query_encoding, - ad1848_set_params, - ad1848_round_blocksize, - ad1848_commit_settings, - NULL, - NULL, - NULL, - NULL, - ad1848_halt_output, - ad1848_halt_input, - NULL, - wss_getdev, - NULL, - wss_mixer_set_port, - wss_mixer_get_port, - wss_query_devinfo, - ad1848_malloc, - ad1848_free, - ad1848_round, - ad1848_mappage, - ad1848_get_props, - ad1848_trigger_output, - ad1848_trigger_input, - NULL -}; - -/* - * Attach hardware to driver, attach hardware driver to audio - * pseudo-device driver . - */ -void -wssattach(sc) - struct wss_softc *sc; -{ - int version; - - madattach(sc); - - sc->sc_ih = isa_intr_establish(sc->sc_ic, sc->wss_irq, - IST_EDGE, IPL_AUDIO | IPL_MPSAFE, - ad1848_intr, &sc->sc_ad1848, sc->sc_dev.dv_xname); - - ad1848_attach(&sc->sc_ad1848); - - version = bus_space_read_1(sc->sc_iot, sc->sc_ioh, WSS_STATUS) & WSS_VERSMASK; - printf(" (vers %d)", version); - switch(sc->mad_chip_type) { - case MAD_82C928: - printf(", 82C928"); - break; - case MAD_OTI601D: - printf(", OTI-601D"); - break; - case MAD_82C929: - printf(", 82C929"); - break; - case MAD_82C931: - printf(", 82C931"); - break; - default: - break; - } - printf("\n"); - - sc->sc_ad1848.parent = sc; - - audio_attach_mi(&wss_hw_if, &sc->sc_ad1848, &sc->sc_dev); -} - -int -wss_getdev(addr, retp) - void *addr; - struct audio_device *retp; -{ - *retp = wss_device; - return 0; -} - -static ad1848_devmap_t mappings[] = { -{ WSS_MIC_IN_LVL, AD1848_KIND_LVL, AD1848_AUX2_CHANNEL }, -{ WSS_LINE_IN_LVL, AD1848_KIND_LVL, AD1848_AUX1_CHANNEL }, -{ WSS_DAC_LVL, AD1848_KIND_LVL, AD1848_DAC_CHANNEL }, -{ WSS_MON_LVL, AD1848_KIND_LVL, AD1848_MONO_CHANNEL }, -{ WSS_MIC_IN_MUTE, AD1848_KIND_MUTE, AD1848_AUX2_CHANNEL }, -{ WSS_LINE_IN_MUTE, AD1848_KIND_MUTE, AD1848_AUX1_CHANNEL }, -{ WSS_DAC_MUTE, AD1848_KIND_MUTE, AD1848_DAC_CHANNEL }, -{ WSS_REC_LVL, AD1848_KIND_RECORDGAIN, -1 }, -{ WSS_RECORD_SOURCE, AD1848_KIND_RECORDSOURCE, -1} -}; - -static int nummap = sizeof(mappings) / sizeof(mappings[0]); - -int -wss_mixer_set_port(addr, cp) - void *addr; - mixer_ctrl_t *cp; -{ - struct ad1848_softc *ac = addr; - - return (ad1848_mixer_set_port(ac, mappings, nummap, cp)); -} - -int -wss_mixer_get_port(addr, cp) - void *addr; - mixer_ctrl_t *cp; -{ - struct ad1848_softc *ac = addr; - - return (ad1848_mixer_get_port(ac, mappings, nummap, cp)); -} - -int -wss_query_devinfo(addr, dip) - void *addr; - mixer_devinfo_t *dip; -{ - DPRINTF(("wss_query_devinfo: index=%d\n", dip->index)); - - switch(dip->index) { - case WSS_MIC_IN_LVL: /* Microphone */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = WSS_INPUT_CLASS; - dip->prev = AUDIO_MIXER_LAST; - dip->next = WSS_MIC_IN_MUTE; - strlcpy(dip->label.name, AudioNmicrophone, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, sizeof dip->un.v.units.name); - break; - - case WSS_LINE_IN_LVL: /* line/CD */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = WSS_INPUT_CLASS; - dip->prev = AUDIO_MIXER_LAST; - dip->next = WSS_LINE_IN_MUTE; - strlcpy(dip->label.name, AudioNcd, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, sizeof dip->un.v.units.name); - break; - - case WSS_DAC_LVL: /* dacout */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = WSS_INPUT_CLASS; - dip->prev = AUDIO_MIXER_LAST; - dip->next = WSS_DAC_MUTE; - strlcpy(dip->label.name, AudioNdac, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, sizeof dip->un.v.units.name); - break; - - case WSS_REC_LVL: /* record level */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = WSS_RECORD_CLASS; - dip->prev = AUDIO_MIXER_LAST; - dip->next = WSS_RECORD_SOURCE; - strlcpy(dip->label.name, AudioNrecord, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, sizeof dip->un.v.units.name); - break; - - case WSS_MON_LVL: /* monitor level */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = WSS_MONITOR_CLASS; - dip->next = dip->prev = AUDIO_MIXER_LAST; - strlcpy(dip->label.name, AudioNmonitor, sizeof dip->label.name); - dip->un.v.num_channels = 1; - strlcpy(dip->un.v.units.name, AudioNvolume, sizeof dip->un.v.units.name); - break; - - case WSS_INPUT_CLASS: /* input class descriptor */ - dip->type = AUDIO_MIXER_CLASS; - dip->mixer_class = WSS_INPUT_CLASS; - dip->next = dip->prev = AUDIO_MIXER_LAST; - strlcpy(dip->label.name, AudioCinputs, sizeof dip->label.name); - break; - - case WSS_MONITOR_CLASS: /* monitor class descriptor */ - dip->type = AUDIO_MIXER_CLASS; - dip->mixer_class = WSS_MONITOR_CLASS; - dip->next = dip->prev = AUDIO_MIXER_LAST; - strlcpy(dip->label.name, AudioCmonitor, sizeof dip->label.name); - break; - - case WSS_RECORD_CLASS: /* record source class */ - dip->type = AUDIO_MIXER_CLASS; - dip->mixer_class = WSS_RECORD_CLASS; - dip->next = dip->prev = AUDIO_MIXER_LAST; - strlcpy(dip->label.name, AudioCrecord, sizeof dip->label.name); - break; - - case WSS_MIC_IN_MUTE: - dip->mixer_class = WSS_INPUT_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = WSS_MIC_IN_LVL; - dip->next = AUDIO_MIXER_LAST; - goto mute; - - case WSS_LINE_IN_MUTE: - dip->mixer_class = WSS_INPUT_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = WSS_LINE_IN_LVL; - dip->next = AUDIO_MIXER_LAST; - goto mute; - - case WSS_DAC_MUTE: - dip->mixer_class = WSS_INPUT_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = WSS_DAC_LVL; - dip->next = AUDIO_MIXER_LAST; - mute: - strlcpy(dip->label.name, AudioNmute, sizeof dip->label.name); - dip->un.e.num_mem = 2; - strlcpy(dip->un.e.member[0].label.name, AudioNoff, - sizeof dip->un.e.member[0].label.name); - dip->un.e.member[0].ord = 0; - strlcpy(dip->un.e.member[1].label.name, AudioNon, - sizeof dip->un.e.member[1].label.name); - dip->un.e.member[1].ord = 1; - break; - - case WSS_RECORD_SOURCE: - dip->mixer_class = WSS_RECORD_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = WSS_REC_LVL; - dip->next = AUDIO_MIXER_LAST; - strlcpy(dip->label.name, AudioNsource, sizeof dip->label.name); - dip->un.e.num_mem = 3; - strlcpy(dip->un.e.member[0].label.name, AudioNmicrophone, - sizeof dip->un.e.member[0].label.name); - dip->un.e.member[0].ord = WSS_MIC_IN_LVL; - strlcpy(dip->un.e.member[1].label.name, AudioNcd, - sizeof dip->un.e.member[1].label.name); - dip->un.e.member[1].ord = WSS_LINE_IN_LVL; - strlcpy(dip->un.e.member[2].label.name, AudioNdac, - sizeof dip->un.e.member[2].label.name); - dip->un.e.member[2].ord = WSS_DAC_LVL; - break; - - default: - return ENXIO; - /*NOTREACHED*/ - } - DPRINTF(("AUDIO_MIXER_DEVINFO: name=%s\n", dip->label.name)); - - return 0; -} - - -/* - * Copyright by Hannu Savolainen 1994 - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. 2. - * Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY - * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR - * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER - * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ -/* - * Initialization code for OPTi MAD16 compatible audio chips. Including - * - * OPTi 82C928 MAD16 (replaced by C929) - * OAK OTI-601D Mozart - * OPTi 82C929 MAD16 Pro - * - */ - -u_int -mad_read(sc, port) - struct wss_softc *sc; - int port; -{ - u_int tmp; - int pwd; - - switch (sc->mad_chip_type) { /* Output password */ - case MAD_82C928: - case MAD_OTI601D: - pwd = M_PASSWD_928; - break; - case MAD_82C929: - pwd = M_PASSWD_929; - break; - case MAD_82C931: - pwd = M_PASSWD_931; - break; - default: - panic("mad_read: Bad chip type=%d", sc->mad_chip_type); - } - mtx_enter(&audio_lock); /* don't want an interrupt between outb&inb */ - bus_space_write_1(sc->sc_iot, sc->mad_ioh, MC_PASSWD_REG, pwd); - tmp = bus_space_read_1(sc->sc_iot, sc->mad_ioh, port); - mtx_leave(&audio_lock); - return tmp; -} - -void -mad_write(sc, port, value) - struct wss_softc *sc; - int port; - int value; -{ - int pwd; - - switch (sc->mad_chip_type) { /* Output password */ - case MAD_82C928: - case MAD_OTI601D: - pwd = M_PASSWD_928; - break; - case MAD_82C929: - pwd = M_PASSWD_929; - break; - case MAD_82C931: - pwd = M_PASSWD_931; - break; - default: - panic("mad_write: Bad chip type=%d", sc->mad_chip_type); - } - mtx_enter(&audio_lock); - bus_space_write_1(sc->sc_iot, sc->mad_ioh, MC_PASSWD_REG, pwd); - bus_space_write_1(sc->sc_iot, sc->mad_ioh, port, value & 0xff); - mtx_leave(&audio_lock); -} - -void -madattach(sc) - struct wss_softc *sc; -{ - unsigned char cs4231_mode; - int joy; - - if (sc->mad_chip_type == MAD_NONE) - return; - - /* Do we want the joystick disabled? */ - joy = sc->sc_dev.dv_cfdata->cf_flags & 2 ? MC1_JOYDISABLE : 0; - - /* enable WSS emulation at the I/O port */ - mad_write(sc, MC1_PORT, M_WSS_PORT_SELECT(sc->mad_ioindex) | joy); - mad_write(sc, MC2_PORT, 0x03); /* ? */ - mad_write(sc, MC3_PORT, 0xf0); /* Disable SB */ - - cs4231_mode = - strncmp(sc->sc_ad1848.chip_name, "CS4248", 6) == 0 || - strncmp(sc->sc_ad1848.chip_name, "CS4231", 6) == 0 ? 0x02 : 0; - - if (sc->mad_chip_type == MAD_82C929) { - mad_write(sc, MC4_PORT, 0x92); - mad_write(sc, MC5_PORT, 0xA5 | cs4231_mode); - mad_write(sc, MC6_PORT, 0x03); /* Disable MPU401 */ - } else { - mad_write(sc, MC4_PORT, 0x02); - mad_write(sc, MC5_PORT, 0x30 | cs4231_mode); - } - -#ifdef AUDIO_DEBUG - if (wssdebug) { - int i; - for (i = MC1_PORT; i <= MC7_PORT; i++) - DPRINTF(("port %03x after init = %02x\n", i, mad_read(sc, i))); - } -#endif -} diff --git a/sys/dev/isa/wss_isa.c b/sys/dev/isa/wss_isa.c deleted file mode 100644 index ea328fe4b1e..00000000000 --- a/sys/dev/isa/wss_isa.c +++ /dev/null @@ -1,365 +0,0 @@ -/* $OpenBSD: wss_isa.c,v 1.6 2014/09/14 14:17:25 jsg Exp $ */ -/* $NetBSD: wss_isa.c,v 1.1 1998/01/19 22:18:24 augustss Exp $ */ - -/* - * Copyright (c) 1994 John Brezak - * Copyright (c) 1991-1993 Regents of the University of California. - * All rights reserved. - * - * MAD support: - * Copyright (c) 1996 Lennart Augustsson - * Based on code which is - * Copyright (c) 1994 Hannu Savolainen - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the Computer Systems - * Engineering Group at Lawrence Berkeley Laboratory. - * 4. Neither the name of the University nor of the Laboratory may be used - * to endorse or promote products derived from this software without - * specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/syslog.h> -#include <sys/device.h> -#include <sys/buf.h> - -#include <machine/cpu.h> -#include <machine/intr.h> -#include <machine/bus.h> - -#include <sys/audioio.h> -#include <dev/audio_if.h> - -#include <dev/isa/isavar.h> -#include <dev/isa/isadmavar.h> - -#include <dev/ic/ad1848reg.h> -#include <dev/isa/ad1848var.h> -#include <dev/isa/wssreg.h> -#include <dev/isa/wssvar.h> -#include <dev/isa/madreg.h> - -#ifdef AUDIO_DEBUG -#define DPRINTF(x) if (wssdebug) printf x -extern int wssdebug; -#else -#define DPRINTF(x) -#endif - -static int wssfind(struct device *, struct wss_softc *, struct isa_attach_args *); - -static void madprobe(struct wss_softc *, int); -static void madunmap(struct wss_softc *); -static int detect_mad16(struct wss_softc *, int); - -int wss_isa_probe(struct device *, void *, void *); -void wss_isa_attach(struct device *, struct device *, void *); - -struct cfattach wss_isa_ca = { - sizeof(struct wss_softc), wss_isa_probe, wss_isa_attach -}; - -struct cfdriver wss_cd = { - NULL, "wss", DV_DULL -}; - -/* - * Probe for the Microsoft Sound System hardware. - */ -int -wss_isa_probe(parent, match, aux) - struct device *parent; - void *match; - void *aux; -{ - struct wss_softc probesc, *sc = &probesc; - - bzero(sc, sizeof *sc); - sc->sc_dev.dv_cfdata = ((struct device *)match)->dv_cfdata; - if (wssfind(parent, sc, aux)) { - bus_space_unmap(sc->sc_iot, sc->sc_ioh, WSS_CODEC); - ad1848_unmap(&sc->sc_ad1848); - madunmap(sc); - return 1; - } else - /* Everything is already unmapped */ - return 0; -} - -static int -wssfind(parent, sc, ia) - struct device *parent; - struct wss_softc *sc; - struct isa_attach_args *ia; -{ - static u_char interrupt_bits[12] = { - -1, -1, -1, -1, -1, 0x0, -1, 0x08, -1, 0x10, 0x18, 0x20 - }; - static u_char dma_bits[4] = {1, 2, 0, 3}; - - sc->sc_iot = ia->ia_iot; - if (sc->sc_dev.dv_cfdata->cf_flags & 1) - madprobe(sc, ia->ia_iobase); - else - sc->mad_chip_type = MAD_NONE; - - if (!WSS_BASE_VALID(ia->ia_iobase)) { - DPRINTF(("wss: configured iobase %x invalid\n", ia->ia_iobase)); - goto bad1; - } - - /* Map the ports upto the AD1848 port */ - if (bus_space_map(sc->sc_iot, ia->ia_iobase, WSS_CODEC, 0, &sc->sc_ioh)) - goto bad1; - - sc->sc_ad1848.sc_iot = sc->sc_iot; - - /* Is there an ad1848 chip at (WSS iobase + WSS_CODEC)? */ - if (ad1848_mapprobe(&sc->sc_ad1848, ia->ia_iobase + WSS_CODEC) == 0) - goto bad; - - ia->ia_iosize = WSS_NPORT; - - /* Setup WSS interrupt and DMA */ - if (!WSS_DRQ_VALID(ia->ia_drq)) { - DPRINTF(("wss: configured dma chan %d invalid\n", ia->ia_drq)); - goto bad; - } - sc->wss_drq = ia->ia_drq; - - if (sc->wss_drq != DRQUNK && !isa_drq_isfree(parent, sc->wss_drq)) - goto bad; - - if (!WSS_IRQ_VALID(ia->ia_irq)) { - DPRINTF(("wss: configured interrupt %d invalid\n", ia->ia_irq)); - goto bad; - } - - sc->wss_irq = ia->ia_irq; - - if (sc->sc_ad1848.mode <= 1) - ia->ia_drq2 = DRQUNK; - sc->wss_recdrq = - sc->sc_ad1848.mode > 1 && ia->ia_drq2 != DRQUNK ? - ia->ia_drq2 : ia->ia_drq; - if (sc->wss_recdrq != sc->wss_drq && !isa_drq_isfree(parent, sc->wss_recdrq)) - goto bad; - - /* XXX recdrq */ - bus_space_write_1(sc->sc_iot, sc->sc_ioh, WSS_CONFIG, - (interrupt_bits[ia->ia_irq] | dma_bits[ia->ia_drq])); - - return 1; - -bad: - bus_space_unmap(sc->sc_iot, sc->sc_ioh, WSS_CODEC); -bad1: - madunmap(sc); - return 0; -} - -/* - * Attach hardware to driver, attach hardware driver to audio - * pseudo-device driver . - */ -void -wss_isa_attach(parent, self, aux) - struct device *parent, *self; - void *aux; -{ - struct wss_softc *sc = (struct wss_softc *)self; - struct isa_attach_args *ia = (struct isa_attach_args *)aux; - - if (!wssfind(parent, sc, ia)) { - printf("%s: wssfind failed\n", sc->sc_dev.dv_xname); - return; - } - - sc->sc_ic = ia->ia_ic; - sc->sc_ad1848.sc_isa = parent; - - wssattach(sc); -} - -/* - * Copyright by Hannu Savolainen 1994 - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. 2. - * Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY - * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR - * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER - * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ - -/* - * Initialization code for OPTi MAD16 compatible audio chips. Including - * - * OPTi 82C928 MAD16 (replaced by C929) - * OAK OTI-601D Mozart - * OPTi 82C929 MAD16 Pro - * OPTi 82C931 - */ - -static int -detect_mad16(sc, chip_type) - struct wss_softc *sc; - int chip_type; -{ - unsigned char tmp, tmp2; - - sc->mad_chip_type = chip_type; - /* - * Check that reading a register doesn't return bus float (0xff) - * when the card is accessed using password. This may fail in case - * the card is in low power mode. Normally at least the power saving mode - * bit should be 0. - */ - if ((tmp = mad_read(sc, MC1_PORT)) == 0xff) { - DPRINTF(("MC1_PORT returned 0xff\n")); - return 0; - } - - /* - * Now check that the gate is closed on first I/O after writing - * the password. (This is how a MAD16 compatible card works). - */ - if ((tmp2 = bus_space_read_1(sc->sc_iot, sc->mad_ioh, MC1_PORT)) == tmp) { - DPRINTF(("MC1_PORT didn't close after read (0x%02x)\n", tmp2)); - return 0; - } - - mad_write(sc, MC1_PORT, tmp ^ 0x80); /* Toggle a bit */ - - /* Compare the bit */ - if ((tmp2 = mad_read(sc, MC1_PORT)) != (tmp ^ 0x80)) { - mad_write(sc, MC1_PORT, tmp); /* Restore */ - DPRINTF(("Bit revert test failed (0x%02x, 0x%02x)\n", tmp, tmp2)); - return 0; - } - - mad_write(sc, MC1_PORT, tmp); /* Restore */ - return 1; -} - -static void -madprobe(sc, iobase) - struct wss_softc *sc; - int iobase; -{ - static int valid_ports[M_WSS_NPORTS] = - { M_WSS_PORT0, M_WSS_PORT1, M_WSS_PORT2, M_WSS_PORT3 }; - int i; - - /* Allocate bus space that the MAD chip wants */ - if (bus_space_map(sc->sc_iot, MAD_BASE, MAD_NPORT, 0, &sc->mad_ioh)) - goto bad0; - if (bus_space_map(sc->sc_iot, MAD_REG1, MAD_LEN1, 0, &sc->mad_ioh1)) - goto bad1; - if (bus_space_map(sc->sc_iot, MAD_REG2, MAD_LEN2, 0, &sc->mad_ioh2)) - goto bad2; - if (bus_space_map(sc->sc_iot, MAD_REG3, MAD_LEN3, 0, &sc->mad_ioh3)) - goto bad3; - - DPRINTF(("mad: Detect using password = 0xE2\n")); - if (!detect_mad16(sc, MAD_82C928)) { - /* No luck. Try different model */ - DPRINTF(("mad: Detect using password = 0xE3\n")); - if (!detect_mad16(sc, MAD_82C929)) - goto bad; - sc->mad_chip_type = MAD_82C929; - DPRINTF(("mad: 82C929 detected\n")); - } else { - sc->mad_chip_type = MAD_82C928; - if ((mad_read(sc, MC3_PORT) & 0x03) == 0x03) { - DPRINTF(("mad: Mozart detected\n")); - sc->mad_chip_type = MAD_OTI601D; - } else { - DPRINTF(("mad: 82C928 detected?\n")); - sc->mad_chip_type = MAD_82C928; - } - } - -#ifdef AUDIO_DEBUG - if (wssdebug) - for (i = MC1_PORT; i <= MC7_PORT; i++) - printf("mad: port %03x = %02x\n", i, mad_read(sc, i)); -#endif - - /* Set the WSS address. */ - for (i = 0; i < M_WSS_NPORTS; i++) - if (valid_ports[i] == iobase) - break; - if (i >= M_WSS_NPORTS) { /* Not a valid port */ - printf("mad: Bad WSS base address 0x%x\n", iobase); - goto bad; - } - sc->mad_ioindex = i; - /* enable WSS emulation at the I/O port, no joystick */ - mad_write(sc, MC1_PORT, M_WSS_PORT_SELECT(i) | MC1_JOYDISABLE); - mad_write(sc, MC2_PORT, 0x03); /* ? */ - mad_write(sc, MC3_PORT, 0xf0); /* Disable SB */ - return; - -bad: - bus_space_unmap(sc->sc_iot, sc->mad_ioh3, MAD_LEN3); -bad3: - bus_space_unmap(sc->sc_iot, sc->mad_ioh2, MAD_LEN2); -bad2: - bus_space_unmap(sc->sc_iot, sc->mad_ioh1, MAD_LEN1); -bad1: - bus_space_unmap(sc->sc_iot, sc->mad_ioh, MAD_NPORT); -bad0: - sc->mad_chip_type = MAD_NONE; -} - -static void -madunmap(sc) - struct wss_softc *sc; -{ - if (sc->mad_chip_type == MAD_NONE) - return; - bus_space_unmap(sc->sc_iot, sc->mad_ioh, MAD_NPORT); - bus_space_unmap(sc->sc_iot, sc->mad_ioh1, MAD_LEN1); - bus_space_unmap(sc->sc_iot, sc->mad_ioh2, MAD_LEN2); - bus_space_unmap(sc->sc_iot, sc->mad_ioh3, MAD_LEN3); -} diff --git a/sys/dev/isa/wss_isapnp.c b/sys/dev/isa/wss_isapnp.c deleted file mode 100644 index c46630415e9..00000000000 --- a/sys/dev/isa/wss_isapnp.c +++ /dev/null @@ -1,120 +0,0 @@ -/* $OpenBSD: wss_isapnp.c,v 1.9 2014/09/14 14:17:25 jsg Exp $ */ -/* $NetBSD: wss_isapnp.c,v 1.5 1998/11/25 22:17:07 augustss Exp $ */ - -/* - * Copyright (c) 1997 The NetBSD Foundation, Inc. - * All rights reserved. - * - * This code is derived from software contributed to The NetBSD Foundation - * by Lennart Augustsson (augustss@netbsd.org). - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS - * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED - * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS - * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/syslog.h> -#include <sys/device.h> - -#include <machine/bus.h> - -#include <sys/audioio.h> -#include <dev/audio_if.h> - -#include <dev/isa/isavar.h> -#include <dev/isa/isadmavar.h> - -#include <dev/isa/isapnpreg.h> - -#include <dev/isa/ad1848var.h> -#include <dev/ic/ad1848reg.h> -#include <dev/isa/madreg.h> -#include <dev/isa/wssreg.h> -#include <dev/isa/wssvar.h> - -int wss_isapnp_match(struct device *, void *, void *); -void wss_isapnp_attach(struct device *, struct device *, void *); - -struct cfattach wss_isapnp_ca = { - sizeof(struct wss_softc), wss_isapnp_match, wss_isapnp_attach -}; - - -/* - * Probe / attach routines. - */ - -/* - * Probe for the WSS hardware. - */ -int -wss_isapnp_match(parent, match, aux) - struct device *parent; - void *match, *aux; -{ - return 1; -} - -/* - * Attach hardware to driver, attach hardware driver to audio - * pseudo-device driver. - */ -void -wss_isapnp_attach(parent, self, aux) - struct device *parent, *self; - void *aux; -{ - struct isapnp_softc *pnp = (struct isapnp_softc *)parent; - struct wss_softc *sc = (struct wss_softc *)self; - struct ad1848_softc *ac = &sc->sc_ad1848; - struct isa_attach_args *ipa = aux; - - /* probably broken */ - isapnp_write_reg(pnp, ISAPNP_CONFIG_CONTROL, 0x02); - - sc->sc_iot = ipa->ia_iot; - sc->sc_ioh = ipa->ipa_io[0].h; - sc->mad_chip_type = MAD_NONE; - -/* Set up AD1848 I/O handle. */ - ac->sc_iot = sc->sc_iot; - ac->sc_isa = parent->dv_parent; - ac->sc_ioh = sc->sc_ioh; - ac->mode = 2; - ac->sc_iooffs = 0; - - sc->sc_ic = ipa->ia_ic; - sc->wss_irq = ipa->ipa_irq[0].num; - sc->wss_drq = ipa->ipa_drq[0].num; - sc->wss_recdrq = ipa->ipa_ndrq > 1 ? ipa->ipa_drq[1].num : - ipa->ipa_drq[0].num; - - if (ad1848_probe(&sc->sc_ad1848)==0) { - printf("%s: probe failed\n", ac->sc_dev.dv_xname); - return; - } - - wssattach(sc); -} - diff --git a/sys/dev/isa/wssreg.h b/sys/dev/isa/wssreg.h deleted file mode 100644 index f3678dca1d7..00000000000 --- a/sys/dev/isa/wssreg.h +++ /dev/null @@ -1,62 +0,0 @@ -/* $OpenBSD: wssreg.h,v 1.4 2000/03/28 14:07:43 espie Exp $ */ -/* $NetBSD: wssreg.h,v 1.3 1995/07/07 02:15:15 brezak Exp $ */ - -/* - * Copyright (c) 1991-1993 Regents of the University of California. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the Computer Systems - * Engineering Group at Lawrence Berkeley Laboratory. - * 4. Neither the name of the University nor of the Laboratory may be used - * to endorse or promote products derived from this software without - * specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ -/* - * Copyright (c) 1993 Analog Devices Inc. All rights reserved - */ - -/* - * Macros to detect valid hardware configuration data. - */ -#define WSS_IRQ_VALID(irq) ((irq) == 5 || (irq) == 7 || (irq) == 9 || \ - (irq) == 10 || (irq) == 11) -#define WSS_DRQ_VALID(chan) ((chan) == 0 || (chan) == 1 || (chan) == 3) -#define WSS_BASE_VALID(base) ((base) == 0x0530 || \ - (base) == 0x0604 || \ - (base) == 0x0e80 || \ - (base) == 0x0f40) - -/* WSS registers */ -#define WSS_CONFIG 0x00 /* write only */ -#define WSS_STATUS 0x03 /* read only */ -#define WSS_CODEC 0x04 /* ad1848 codec registers (0x04-0x07) */ -#define WSS_NPORT 8 - -/* WSS status register bits */ -#define WSS_16SLOT 0x80 -#define WSS_IRQACTIVE 0x40 -#define WSS_VERS 0x04 -#define WSS_VERSMASK 0x3f diff --git a/sys/dev/isa/wssvar.h b/sys/dev/isa/wssvar.h deleted file mode 100644 index c1ef7bd7cb8..00000000000 --- a/sys/dev/isa/wssvar.h +++ /dev/null @@ -1,83 +0,0 @@ -/* $OpenBSD: wssvar.h,v 1.2 2002/03/14 01:26:57 millert Exp $ */ -/* $NetBSD: wssvar.h,v 1.1 1998/01/19 22:18:25 augustss Exp $ */ - -/* - * Copyright (c) 1994 John Brezak - * Copyright (c) 1991-1993 Regents of the University of California. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the Computer Systems - * Engineering Group at Lawrence Berkeley Laboratory. - * 4. Neither the name of the University nor of the Laboratory may be used - * to endorse or promote products derived from this software without - * specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ - -/* - * Mixer devices - */ -#define WSS_MIC_IN_LVL 0 -#define WSS_LINE_IN_LVL 1 -#define WSS_DAC_LVL 2 -#define WSS_REC_LVL 3 -#define WSS_MON_LVL 4 -#define WSS_MIC_IN_MUTE 5 -#define WSS_LINE_IN_MUTE 6 -#define WSS_DAC_MUTE 7 - -#define WSS_RECORD_SOURCE 8 - -/* Classes */ -#define WSS_INPUT_CLASS 9 -#define WSS_RECORD_CLASS 10 -#define WSS_MONITOR_CLASS 11 - -struct wss_softc { - struct device sc_dev; /* base device */ - struct isadev sc_id; /* ISA device */ - void *sc_ih; /* interrupt vectoring */ - bus_space_tag_t sc_iot; /* tag */ - bus_space_handle_t sc_ioh; /* handle */ - isa_chipset_tag_t sc_ic; - - struct ad1848_softc sc_ad1848; -#define wss_irq sc_ad1848.sc_irq -#define wss_drq sc_ad1848.sc_drq -#define wss_recdrq sc_ad1848.sc_recdrq - - int mic_mute, cd_mute, dac_mute; - - int mad_chip_type; /* chip type if MAD emulation of WSS */ - int mad_ioindex; - bus_space_handle_t mad_ioh; /* MAD handle */ - bus_space_handle_t mad_ioh1, mad_ioh2, mad_ioh3; -}; - -void wssattach(struct wss_softc *); - -u_int mad_read(struct wss_softc *, int); -void mad_write(struct wss_softc *, int, int); -void madattach(struct wss_softc *); diff --git a/sys/dev/isa/ym.c b/sys/dev/isa/ym.c deleted file mode 100644 index e78ab41a72f..00000000000 --- a/sys/dev/isa/ym.c +++ /dev/null @@ -1,869 +0,0 @@ -/* $OpenBSD: ym.c,v 1.19 2014/09/14 14:17:25 jsg Exp $ */ - - -/* - * Copyright (c) 1998 Constantine Sapuntzakis. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. The name of the author may not be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR - * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. - * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, - * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT - * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF - * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#include "midi.h" - -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/syslog.h> -#include <sys/device.h> -#include <sys/buf.h> - -#include <machine/cpu.h> -#include <machine/intr.h> -#include <machine/bus.h> - -#include <sys/audioio.h> -#include <dev/audio_if.h> -#include <dev/midi_if.h> - -#include <dev/isa/isavar.h> -#include <dev/isa/isadmavar.h> - -#include <dev/ic/ad1848reg.h> -#include <dev/isa/ad1848var.h> -#include <dev/ic/mpuvar.h> -#include <dev/isa/ymvar.h> - -/* - * YAMAHA YMF715x (OPL3 Single-chip Audio System 3; OPL3-SA3) - * control register description - * - * Other ports (SBpro, WSS CODEC, MPU401, OPL3, etc.) are NOT listed here. - */ - -/* - * direct registers - */ - -/* offset from the base address */ -#define SA3_CTL_INDEX 0 /* Index port (R/W) */ -#define SA3_CTL_DATA 1 /* Data register port (R/W) */ - -#define SA3_CTL_NPORT 2 /* number of ports */ - -/* - * indirect registers - */ - -#define SA3_PWR_MNG 0x01 /* Power management (R/W) */ -#define SA3_PWR_MNG_ADOWN 0x20 /* Analog Down */ -#define SA3_PWR_MNG_PSV 0x04 /* Power save */ -#define SA3_PWR_MNG_PDN 0x02 /* Power down */ -#define SA3_PWR_MNG_PDX 0x01 /* Oscillation stop */ -#define SA3_PWR_MNG_DEFAULT 0x00 /* default value */ - -#define SA3_SYS_CTL 0x02 /* System control (R/W) */ -#define SA3_SYS_CTL_SBHE 0x80 /* 0: AT-bus, 1: XT-bus */ -#define SA3_SYS_CTL_YMODE 0x30 /* 3D Enhancement mode */ -#define SA3_SYS_CTL_YMODE0 0x00 /* Desktop mode (speaker 5-12cm) */ -#define SA3_SYS_CTL_YMODE1 0x10 /* Notebook PC mode (1) (3cm) */ -#define SA3_SYS_CTL_YMODE2 0x20 /* Notebook PC mode (2) (1.5cm) */ -#define SA3_SYS_CTL_YMODE3 0x30 /* Hi-Fi mode (16-38cm) */ -#define SA3_SYS_CTL_IDSEL 0x06 /* Specify DSP version of SBPro */ -#define SA3_SYS_CTL_IDSEL0 0x00 /* major 0x03, minor 0x01 */ -#define SA3_SYS_CTL_IDSEL1 0x02 /* major 0x02, minor 0x01 */ -#define SA3_SYS_CTL_IDSEL2 0x04 /* major 0x01, minor 0x05 */ -#define SA3_SYS_CTL_IDSEL3 0x06 /* major 0x00, minor 0x00 */ -#define SA3_SYS_CTL_VZE 0x01 /* ZV */ -#define SA3_SYS_CTL_DEFAULT 0x00 /* default value */ - -#define SA3_IRQ_CONF 0x03 /* Interrupt Channel config (R/W) */ -#define SA3_IRQ_CONF_OPL3_B 0x80 /* OPL3 uses IRQ-B */ -#define SA3_IRQ_CONF_MPU_B 0x40 /* MPU401 uses IRQ-B */ -#define SA3_IRQ_CONF_SB_B 0x20 /* Sound Blaster uses IRQ-B */ -#define SA3_IRQ_CONF_WSS_B 0x10 /* WSS CODEC uses IRQ-B */ -#define SA3_IRQ_CONF_OPL3_A 0x08 /* OPL3 uses IRQ-A */ -#define SA3_IRQ_CONF_MPU_A 0x04 /* MPU401 uses IRQ-A */ -#define SA3_IRQ_CONF_SB_A 0x02 /* Sound Blaster uses IRQ-A */ -#define SA3_IRQ_CONF_WSS_A 0x01 /* WSS CODEC uses IRQ-A */ -#define SA3_IRQ_CONF_DEFAULT (SA3_IRQ_CONF_MPU_B | SA3_IRQ_CONF_SB_B | \ - SA3_IRQ_CONF_OPL3_A | SA3_IRQ_CONF_WSS_A) - -#define SA3_IRQA_STAT 0x04 /* Interrupt (IRQ-A) STATUS (RO) */ -#define SA3_IRQB_STAT 0x05 /* Interrupt (IRQ-B) STATUS (RO) */ -#define SA3_IRQ_STAT_MV 0x40 /* Hardware Volume Interrupt */ -#define SA3_IRQ_STAT_OPL3 0x20 /* Internal FM-synthesizer timer */ -#define SA3_IRQ_STAT_MPU 0x10 /* MPU401 Interrupt */ -#define SA3_IRQ_STAT_SB 0x08 /* Sound Blaster Playback Interrupt */ -#define SA3_IRQ_STAT_TI 0x04 /* Timer Flag of CODEC */ -#define SA3_IRQ_STAT_CI 0x02 /* Recording Flag of CODEC */ -#define SA3_IRQ_STAT_PI 0x01 /* Playback Flag of CODEC */ - -#define SA3_DMA_CONF 0x06 /* DMA configuration (R/W) */ -#define SA3_DMA_CONF_SB_B 0x40 /* Sound Blaster playback uses DMA-B */ -#define SA3_DMA_CONF_WSS_R_B 0x20 /* WSS CODEC recording uses DMA-B */ -#define SA3_DMA_CONF_WSS_P_B 0x10 /* WSS CODEC playback uses DMA-B */ -#define SA3_DMA_CONF_SB_A 0x04 /* Sound Blaster playback uses DMA-A */ -#define SA3_DMA_CONF_WSS_R_A 0x02 /* WSS CODEC recording uses DMA-A */ -#define SA3_DMA_CONF_WSS_P_A 0x01 /* WSS CODEC playback uses DMA-A */ -#define SA3_DMA_CONF_DEFAULT (SA3_DMA_CONF_SB_B | SA3_DMA_CONF_WSS_R_B | \ - SA3_DMA_CONF_WSS_P_A) - -#define SA3_VOL_L 0x07 /* Master Volume Lch (R/W) */ -#define SA3_VOL_R 0x08 /* Master Volume Rch (R/W) */ -#define SA3_VOL_MUTE 0x80 /* Mute the channel */ -#define SA3_VOL_MV 0x0f /* Master Volume bits */ -#define SA3_VOL_MV_0 0x00 /* 0dB (maximum volume) */ -#define SA3_VOL_MV_2 0x01 /* -2dB */ -#define SA3_VOL_MV_4 0x02 /* -4dB */ -#define SA3_VOL_MV_6 0x03 /* -6dB */ -#define SA3_VOL_MV_8 0x04 /* -8dB */ -#define SA3_VOL_MV_10 0x05 /* -10dB */ -#define SA3_VOL_MV_12 0x06 /* -12dB */ -#define SA3_VOL_MV_14 0x07 /* -14dB (default) */ -#define SA3_VOL_MV_16 0x08 /* -16dB */ -#define SA3_VOL_MV_18 0x09 /* -18dB */ -#define SA3_VOL_MV_20 0x0a /* -20dB */ -#define SA3_VOL_MV_22 0x0b /* -22dB */ -#define SA3_VOL_MV_24 0x0c /* -24dB */ -#define SA3_VOL_MV_26 0x0d /* -26dB */ -#define SA3_VOL_MV_28 0x0e /* -28dB */ -#define SA3_VOL_MV_30 0x0f /* -30dB (minimum volume) */ -#define SA3_VOL_DEFAULT SA3_VOL_MV_14 - -#define SA3_MIC_VOL 0x09 /* MIC Volume (R/W) */ -#define SA3_MIC_MUTE 0x80 /* Mute Mic Volume */ -#define SA3_MIC_MCV 0x1f /* Mic volume bits */ -#define SA3_MIC_MCV12 0x00 /* +12.0dB (maximum volume) */ -#define SA3_MIC_MCV10_5 0x01 /* +10.5dB */ -#define SA3_MIC_MCV9 0x02 /* +9.0dB */ -#define SA3_MIC_MCV7_5 0x03 /* +7.5dB */ -#define SA3_MIC_MCV6 0x04 /* +6.0dB */ -#define SA3_MIC_MCV4_5 0x05 /* +4.5dB */ -#define SA3_MIC_MCV3 0x06 /* +3.0dB */ -#define SA3_MIC_MCV1_5 0x07 /* +1.5dB */ -#define SA3_MIC_MCV_0 0x08 /* 0.0dB (default) */ -#define SA3_MIC_MCV_1_5 0x09 /* -1.5dB */ -#define SA3_MIC_MCV_3_0 0x0a /* -3.0dB */ -#define SA3_MIC_MCV_4_5 0x0b /* -4.5dB */ -#define SA3_MIC_MCV_6 0x0c /* -6.0dB */ -#define SA3_MIC_MCV_7_5 0x0d /* -7.5dB */ -#define SA3_MIC_MCV_9 0x0e /* -9.0dB */ -#define SA3_MIC_MCV_10_5 0x0f /* -10.5dB */ -#define SA3_MIC_MCV_12 0x10 /* -12.0dB */ -#define SA3_MIC_MCV_13_5 0x11 /* -13.5dB */ -#define SA3_MIC_MCV_15 0x12 /* -15.0dB */ -#define SA3_MIC_MCV_16_5 0x13 /* -16.5dB */ -#define SA3_MIC_MCV_18 0x14 /* -18.0dB */ -#define SA3_MIC_MCV_19_5 0x15 /* -19.5dB */ -#define SA3_MIC_MCV_21 0x16 /* -21.0dB */ -#define SA3_MIC_MCV_22_5 0x17 /* -22.5dB */ -#define SA3_MIC_MCV_24 0x18 /* -24.0dB */ -#define SA3_MIC_MCV_25_5 0x19 /* -25.5dB */ -#define SA3_MIC_MCV_27 0x1a /* -27.0dB */ -#define SA3_MIC_MCV_28_5 0x1b /* -28.5dB */ -#define SA3_MIC_MCV_30 0x1c /* -30.0dB */ -#define SA3_MIC_MCV_31_5 0x1d /* -31.5dB */ -#define SA3_MIC_MCV_33 0x1e /* -33.0dB */ -#define SA3_MIC_MCV_34_5 0x1f /* -34.5dB (minimum volume) */ -#define SA3_MIC_VOL_DEFAULT (SA3_MIC_MUTE | SA3_MIC_MCV_0) - -#define SA3_MISC 0x0a /* Miscellaneous */ -#define SA3_MISC_VEN 0x80 /* Enable hardware volume control */ -#define SA3_MISC_MCSW 0x10 /* A/D is connected to 0: Rch of Mic, - 1: loopback of monaural output */ -#define SA3_MISC_MODE 0x08 /* 0: SB mode, 1: WSS mode (RO) */ -#define SA3_MISC_VER 0x07 /* Version of OPL3-SA3 (RO) */ - /* (4 or 5?) */ -/*#define SA3_MISC_DEFAULT (SA3_MISC_VEN | (4 or 5?)) */ - -/* WSS DMA Base counters (R/W) used for suspend/resume */ -#define SA3_DMA_CNT_PLAY_LOW 0x0b /* Playback Base Counter (Low) */ -#define SA3_DMA_CNT_PLAY_HIGH 0x0c /* Playback Base Counter (High) */ -#define SA3_DMA_CNT_REC_LOW 0x0d /* Recording Base Counter (Low) */ -#define SA3_DMA_CNT_REC_HIGH 0x0e /* Recording Base Counter (High) */ - -#define SA3_WSS_INT_SCAN 0x0f /* WSS Interrupt Scan out/in (R/W) */ -#define SA3_WSS_INT_SCAN_STI 0x04 /* 1: TI = "1" and IRQ active */ -#define SA3_WSS_INT_SCAN_SCI 0x02 /* 1: CI = "1" and IRQ active */ -#define SA3_WSS_INT_SCAN_SPI 0x01 /* 1: PI = "1" and IRQ active */ -#define SA3_WSS_INT_DEFAULT 0x00 /* default value */ - -#define SA3_SB_SCAN 0x10 /* SB Internal State Scan out/in (R/W)*/ -#define SA3_SB_SCAN_SBPDA 0x80 /* Sound Blaster Power Down ack */ -#define SA3_SB_SCAN_SS 0x08 /* Scan Select */ -#define SA3_SB_SCAN_SM 0x04 /* Scan Mode 1: read out, 0: write in */ -#define SA3_SB_SCAN_SE 0x02 /* Scan Enable */ -#define SA3_SB_SCAN_SBPDR 0x01 /* Sound Blaster Power Down Request */ -#define SA3_SB_SCAN_DEFAULT 0x00 /* default value */ - -#define SA3_SB_SCAN_DATA 0x11 /* SB Internal State Scan Data (R/W)*/ - -#define SA3_DPWRDWN 0x12 /* Digital Partial Power Down (R/W) */ -#define SA3_DPWRDWN_JOY 0x80 /* Joystick power down */ -#define SA3_DPWRDWN_MPU 0x40 /* MPU401 power down */ -#define SA3_DPWRDWN_MCLKO 0x20 /* Master Clock disable */ -#define SA3_DPWRDWN_FM 0x10 /* FM (OPL3) power down */ -#define SA3_DPWRDWN_WSS_R 0x08 /* WSS recording power down */ -#define SA3_DPWRDWN_WSS_P 0x04 /* WSS playback power down */ -#define SA3_DPWRDWN_SB 0x02 /* Sound Blaster power down */ -#define SA3_DPWRDWN_PNP 0x01 /* PnP power down */ -#define SA3_DPWRDWN_DEFAULT 0x00 /* default value */ - -#define SA3_APWRDWN 0x13 /* Analog Partial Power Down (R/W) */ -#define SA3_APWRDWN_FMDAC 0x10 /* FMDAC for OPL3 power down */ -#define SA3_APWRDWN_AD 0x08 /* A/D for WSS recording power down */ -#define SA3_APWRDWN_DA 0x04 /* D/A for WSS playback power down */ -#define SA3_APWRDWN_SBDAC 0x02 /* D/A for SB power down */ -#define SA3_APWRDWN_WIDE 0x01 /* Wide Stereo power down */ -#define SA3_APWRDWN_DEFAULT 0x00 /* default value */ - -#define SA3_3D_WIDE 0x14 /* 3D Enhanced control (WIDE) (R/W) */ -#define SA3_3D_WIDE_WIDER 0x70 /* Rch of wide 3D enhanced control */ -#define SA3_3D_WIDE_WIDEL 0x07 /* Lch of wide 3D enhanced control */ -#define SA3_3D_WIDE_DEFAULT 0x00 /* default value */ - -#define SA3_3D_BASS 0x15 /* 3D Enhanced control (BASS) (R/W) */ -#define SA3_3D_BASS_BASSR 0x70 /* Rch of bass 3D enhanced control */ -#define SA3_3D_BASS_BASSL 0x07 /* Lch of bass 3D enhanced control */ -#define SA3_3D_BASS_DEFAULT 0x00 /* default value */ - -#define SA3_3D_TREBLE 0x16 /* 3D Enhanced control (TREBLE) (R/W) */ -#define SA3_3D_TREBLE_TRER 0x70 /* Rch of treble 3D enhanced control */ -#define SA3_3D_TREBLE_TREL 0x07 /* Lch of treble 3D enhanced control */ -#define SA3_3D_TREBLE_DEFAULT 0x00 /* default value */ - -/* common to the 3D enhance registers */ -#define SA3_3D_BITS 0x07 -#define SA3_3D_LSHIFT 0 -#define SA3_3D_RSHIFT 4 - -#define SA3_HVOL_INTR_CNF 0x17 /* Hardware Volume Intr Channel (R/W) */ -#define SA3_HVOL_INTR_CNF_B 0x20 /* Hardware Volume uses IRQ-B */ -#define SA3_HVOL_INTR_CNF_A 0x10 /* Hardware Volume uses IRQ-A */ -#define SA3_HVOL_INTR_CNF_DEFAULT 0x00 - -#define SA3_MULTI_STAT 0x18 /* Multi-purpose Select Pin Stat (RO) */ -#define SA3_MULTI_STAT_SEL 0x70 /* State of SEL2-0 pins */ - -int ym_getdev(void *, struct audio_device *); -int ym_mixer_set_port(void *, mixer_ctrl_t *); -int ym_mixer_get_port(void *, mixer_ctrl_t *); -int ym_query_devinfo(void *, mixer_devinfo_t *); -int ym_intr(void *); - -static void ym_mute(struct ym_softc *, int, int); -static void ym_set_master_gain(struct ym_softc *, struct ad1848_volume *); -static void ym_set_mic_gain(struct ym_softc *, int); -static void ym_set_3d(struct ym_softc *, mixer_ctrl_t *, - struct ad1848_volume *, int); - -struct audio_hw_if ym_hw_if = { - ad1848_open, - ad1848_close, - NULL, - ad1848_query_encoding, - ad1848_set_params, - ad1848_round_blocksize, - ad1848_commit_settings, - NULL, - NULL, - NULL, - NULL, - ad1848_halt_output, - ad1848_halt_input, - NULL, - ym_getdev, - NULL, - ym_mixer_set_port, - ym_mixer_get_port, - ym_query_devinfo, - ad1848_malloc, - ad1848_free, - ad1848_round, - ad1848_mappage, - ad1848_get_props, - ad1848_trigger_output, - ad1848_trigger_input, - NULL -}; - - -struct cfdriver ym_cd = { - NULL, "ym", DV_DULL -}; - -struct audio_device ym_device = { - "ym,ad1848", - "", - "ym" -}; - -static __inline int ym_read(struct ym_softc *, int); -static __inline void ym_write(struct ym_softc *, int, int); - -#if NMIDI > 0 -int ym_mpu401_open(void *, int, void (*iintr)(void *, int), - void (*ointr)(void *), void *arg); -void ym_mpu401_close(void *); -int ym_mpu401_output(void *, int); -void ym_mpu401_getinfo(void *, struct midi_info *); - -struct midi_hw_if ym_mpu401_hw_if = { - ym_mpu401_open, - ym_mpu401_close, - ym_mpu401_output, - 0, /* flush */ - ym_mpu401_getinfo, - 0, /* ioctl */ -}; -#endif - -int -ym_intr(v) - void *v; -{ -#if NMIDI > 0 - struct ym_softc *sc = v; - - if ( /* XXX && */ sc->sc_hasmpu) - mpu_intr(&sc->sc_mpu_sc); -#endif - return ad1848_intr(v); -} - -void -ym_attach(sc) - struct ym_softc *sc; - -{ - struct ad1848_volume vol_mid = {220, 220}; -#if NMIDI > 0 - struct midi_hw_if *mhw = &ym_mpu401_hw_if; -#endif - - sc->sc_ih = isa_intr_establish(sc->sc_ic, sc->ym_irq, - IST_EDGE, IPL_AUDIO | IPL_MPSAFE, - ym_intr, &sc->sc_ad1848, sc->sc_dev.dv_xname); - - ad1848_attach(&sc->sc_ad1848); - printf("\n"); - sc->sc_ad1848.parent = sc; - - /* Establish chip in well known mode */ - ym_set_master_gain(sc, &vol_mid); - ym_set_mic_gain(sc, 0); - sc->master_mute = 0; - ym_mute(sc, SA3_VOL_L, sc->master_mute); - ym_mute(sc, SA3_VOL_R, sc->master_mute); - - sc->mic_mute = 1; - ym_mute(sc, SA3_MIC_VOL, sc->mic_mute); - -#if NMIDI > 0 - sc->sc_hasmpu = 0; - if (sc->sc_mpu_sc.iobase) { - sc->sc_mpu_sc.iot = sc->sc_iot; - if (mpu_find(&sc->sc_mpu_sc)) { - sc->sc_hasmpu = 1; - mhw = &ym_mpu401_hw_if; - } - } - midi_attach_mi(mhw, sc, &sc->sc_dev); -#endif - - audio_attach_mi(&ym_hw_if, &sc->sc_ad1848, &sc->sc_dev); -} - -static __inline int -ym_read(sc, reg) - struct ym_softc *sc; - int reg; -{ - bus_space_write_1(sc->sc_iot, sc->sc_controlioh, SA3_CTL_INDEX, - (reg & 0xff)); - return (bus_space_read_1(sc->sc_iot, sc->sc_controlioh, SA3_CTL_DATA)); -} - -static __inline void -ym_write(sc, reg, data) - struct ym_softc *sc; - int reg; - int data; -{ - bus_space_write_1(sc->sc_iot, sc->sc_controlioh, SA3_CTL_INDEX, - (reg & 0xff)); - bus_space_write_1(sc->sc_iot, sc->sc_controlioh, SA3_CTL_DATA, - (data & 0xff)); -} - - - -int -ym_getdev(addr, retp) - void *addr; - struct audio_device *retp; -{ - *retp = ym_device; - return 0; -} - - -static ad1848_devmap_t mappings[] = { - { YM_MIDI_LVL, AD1848_KIND_LVL, AD1848_AUX2_CHANNEL }, - { YM_CD_LVL, AD1848_KIND_LVL, AD1848_AUX1_CHANNEL }, - { YM_DAC_LVL, AD1848_KIND_LVL, AD1848_DAC_CHANNEL }, - { YM_LINE_LVL, AD1848_KIND_LVL, AD1848_LINE_CHANNEL }, - { YM_SPEAKER_LVL, AD1848_KIND_LVL, AD1848_MONO_CHANNEL }, - { YM_MONITOR_LVL, AD1848_KIND_LVL, AD1848_MONITOR_CHANNEL }, - { YM_MIDI_MUTE, AD1848_KIND_MUTE, AD1848_AUX2_CHANNEL }, - { YM_CD_MUTE, AD1848_KIND_MUTE, AD1848_AUX1_CHANNEL }, - { YM_DAC_MUTE, AD1848_KIND_MUTE, AD1848_DAC_CHANNEL }, - { YM_LINE_MUTE, AD1848_KIND_MUTE, AD1848_LINE_CHANNEL }, - { YM_SPEAKER_MUTE, AD1848_KIND_MUTE, AD1848_MONO_CHANNEL }, - { YM_MONITOR_MUTE, AD1848_KIND_MUTE, AD1848_MONITOR_CHANNEL }, - { YM_REC_LVL, AD1848_KIND_RECORDGAIN, -1 }, - { YM_RECORD_SOURCE, AD1848_KIND_RECORDSOURCE, -1 } -}; - -#define NUMMAP (sizeof(mappings) / sizeof(mappings[0])) - - -static void -ym_mute(sc, left_reg, mute) - struct ym_softc *sc; - int left_reg; - int mute; -{ - u_int8_t reg; - - reg = ym_read(sc, left_reg); - if (mute) - ym_write(sc, left_reg, reg | 0x80); - else - ym_write(sc, left_reg, reg & ~0x80); -} - -static void -ym_set_master_gain(sc, vol) - struct ym_softc *sc; - struct ad1848_volume *vol; -{ - u_int atten; - - sc->master_gain = *vol; - - atten = ((AUDIO_MAX_GAIN - vol->left) * (SA3_VOL_MV + 1)) / - (AUDIO_MAX_GAIN + 1); - - ym_write(sc, SA3_VOL_L, (ym_read(sc, SA3_VOL_L) & ~SA3_VOL_MV) | atten); - - atten = ((AUDIO_MAX_GAIN - vol->right) * (SA3_VOL_MV + 1)) / - (AUDIO_MAX_GAIN + 1); - - ym_write(sc, SA3_VOL_R, (ym_read(sc, SA3_VOL_R) & ~SA3_VOL_MV) | atten); -} - -static void -ym_set_mic_gain(sc, vol) - struct ym_softc *sc; - int vol; -{ - u_int atten; - - sc->mic_gain = vol; - - atten = ((AUDIO_MAX_GAIN - vol) * (SA3_MIC_MCV + 1)) / - (AUDIO_MAX_GAIN + 1); - - ym_write(sc, SA3_MIC_VOL, - (ym_read(sc, SA3_MIC_VOL) & ~SA3_MIC_MCV) | atten); -} - -static void -ym_set_3d(sc, cp, val, reg) - struct ym_softc *sc; - mixer_ctrl_t *cp; - struct ad1848_volume *val; - int reg; -{ - u_int8_t e; - - ad1848_to_vol(cp, val); - - e = (val->left * (SA3_3D_BITS + 1) + (SA3_3D_BITS + 1) / 2) / - (AUDIO_MAX_GAIN + 1) << SA3_3D_LSHIFT | - (val->right * (SA3_3D_BITS + 1) + (SA3_3D_BITS + 1) / 2) / - (AUDIO_MAX_GAIN + 1) << SA3_3D_RSHIFT; - - ym_write(sc, reg, e); -} - -int -ym_mixer_set_port(addr, cp) - void *addr; - mixer_ctrl_t *cp; -{ - struct ad1848_softc *ac = addr; - struct ym_softc *sc = ac->parent; - struct ad1848_volume vol; - int error = ad1848_mixer_set_port(ac, mappings, NUMMAP, cp); - - if (error != ENXIO) - return (error); - - error = 0; - - switch (cp->dev) { - case YM_OUTPUT_LVL: - ad1848_to_vol(cp, &vol); - ym_set_master_gain(sc, &vol); - break; - - case YM_OUTPUT_MUTE: - sc->master_mute = (cp->un.ord != 0); - ym_mute(sc, SA3_VOL_L, sc->master_mute); - ym_mute(sc, SA3_VOL_R, sc->master_mute); - break; - - case YM_MIC_LVL: - if (cp->un.value.num_channels != 1) - error = EINVAL; - else - ym_set_mic_gain(sc, - cp->un.value.level[AUDIO_MIXER_LEVEL_MONO]); - break; - - case YM_MASTER_EQMODE: - sc->sc_eqmode = cp->un.ord & SA3_SYS_CTL_YMODE; - ym_write(sc, SA3_SYS_CTL, (ym_read(sc, SA3_SYS_CTL) & - ~SA3_SYS_CTL_YMODE) | sc->sc_eqmode); - break; - - case YM_MASTER_TREBLE: - ym_set_3d(sc, cp, &sc->sc_treble, SA3_3D_TREBLE); - break; - - case YM_MASTER_BASS: - ym_set_3d(sc, cp, &sc->sc_bass, SA3_3D_BASS); - break; - - case YM_MASTER_WIDE: - ym_set_3d(sc, cp, &sc->sc_wide, SA3_3D_WIDE); - break; - - case YM_MIC_MUTE: - sc->mic_mute = (cp->un.ord != 0); - ym_mute(sc, SA3_MIC_VOL, sc->mic_mute); - break; - - default: - return ENXIO; - /* NOTREACHED */ - } - - return (error); -} - -int -ym_mixer_get_port(addr, cp) - void *addr; - mixer_ctrl_t *cp; -{ - struct ad1848_softc *ac = addr; - struct ym_softc *sc = ac->parent; - - int error = ad1848_mixer_get_port(ac, mappings, NUMMAP, cp); - - if (error != ENXIO) - return (error); - - error = 0; - - switch (cp->dev) { - case YM_OUTPUT_LVL: - ad1848_from_vol(cp, &sc->master_gain); - break; - - case YM_OUTPUT_MUTE: - cp->un.ord = sc->master_mute; - break; - - case YM_MIC_LVL: - if (cp->un.value.num_channels != 1) - error = EINVAL; - cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] = sc->mic_gain; - break; - - case YM_MASTER_EQMODE: - cp->un.ord = sc->sc_eqmode; - break; - - case YM_MASTER_TREBLE: - ad1848_from_vol(cp, &sc->sc_treble); - break; - - case YM_MASTER_BASS: - ad1848_from_vol(cp, &sc->sc_bass); - break; - - case YM_MASTER_WIDE: - ad1848_from_vol(cp, &sc->sc_wide); - break; - - case YM_MIC_MUTE: - cp->un.ord = sc->mic_mute; - break; - - default: - error = ENXIO; - break; - } - - return (error); -} - -static char *mixer_classes[] = { - AudioCinputs, AudioCrecord, AudioCoutputs, AudioCmonitor, - AudioCequalization -}; - -int -ym_query_devinfo(addr, dip) - void *addr; - mixer_devinfo_t *dip; -{ - static char *mixer_port_names[] = { AudioNmidi, AudioNcd, AudioNdac, - AudioNline, AudioNspeaker, AudioNmicrophone, AudioNmonitor - }; - - dip->next = dip->prev = AUDIO_MIXER_LAST; - - switch (dip->index) { - case YM_INPUT_CLASS: /* input class descriptor */ - case YM_OUTPUT_CLASS: - case YM_MONITOR_CLASS: - case YM_RECORD_CLASS: - case YM_EQ_CLASS: - dip->type = AUDIO_MIXER_CLASS; - dip->mixer_class = dip->index; - strlcpy(dip->label.name, - mixer_classes[dip->index - YM_INPUT_CLASS], - sizeof dip->label.name); - break; - - case YM_MIDI_LVL: - case YM_CD_LVL: - case YM_DAC_LVL: - case YM_LINE_LVL: - case YM_SPEAKER_LVL: - case YM_MIC_LVL: - case YM_MONITOR_LVL: - dip->type = AUDIO_MIXER_VALUE; - if (dip->index == YM_MONITOR_LVL) - dip->mixer_class = YM_MONITOR_CLASS; - else - dip->mixer_class = YM_INPUT_CLASS; - - dip->next = dip->index + 7; - - strlcpy(dip->label.name, - mixer_port_names[dip->index - YM_MIDI_LVL], - sizeof dip->label.name); - - if (dip->index == YM_SPEAKER_LVL || - dip->index == YM_MIC_LVL) - dip->un.v.num_channels = 1; - else - dip->un.v.num_channels = 2; - - strlcpy(dip->un.v.units.name, AudioNvolume, - sizeof dip->un.v.units.name); - break; - - case YM_MIDI_MUTE: - case YM_CD_MUTE: - case YM_DAC_MUTE: - case YM_LINE_MUTE: - case YM_SPEAKER_MUTE: - case YM_MIC_MUTE: - case YM_MONITOR_MUTE: - if (dip->index == YM_MONITOR_MUTE) - dip->mixer_class = YM_MONITOR_CLASS; - else - dip->mixer_class = YM_INPUT_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = dip->index - 7; -mute: - strlcpy(dip->label.name, AudioNmute, sizeof dip->label.name); - dip->un.e.num_mem = 2; - strlcpy(dip->un.e.member[0].label.name, AudioNoff, - sizeof dip->un.e.member[0].label.name); - dip->un.e.member[0].ord = 0; - strlcpy(dip->un.e.member[1].label.name, AudioNon, - sizeof dip->un.e.member[1].label.name); - dip->un.e.member[1].ord = 1; - break; - - - case YM_OUTPUT_LVL: - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = YM_OUTPUT_CLASS; - dip->next = YM_OUTPUT_MUTE; - strlcpy(dip->label.name, AudioNmaster, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, - sizeof dip->un.v.units.name); - break; - - case YM_OUTPUT_MUTE: - dip->mixer_class = YM_OUTPUT_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = YM_OUTPUT_LVL; - goto mute; - - case YM_REC_LVL: /* record level */ - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = YM_RECORD_CLASS; - dip->next = YM_RECORD_SOURCE; - strlcpy(dip->label.name, AudioNrecord, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNvolume, - sizeof dip->un.v.units.name); - break; - - - case YM_RECORD_SOURCE: - dip->mixer_class = YM_RECORD_CLASS; - dip->type = AUDIO_MIXER_ENUM; - dip->prev = YM_REC_LVL; - strlcpy(dip->label.name, AudioNsource, sizeof dip->label.name); - dip->un.e.num_mem = 4; - strlcpy(dip->un.e.member[0].label.name, AudioNmicrophone, - sizeof dip->un.e.member[0].label.name); - dip->un.e.member[0].ord = MIC_IN_PORT; - strlcpy(dip->un.e.member[1].label.name, AudioNline, - sizeof dip->un.e.member[1].label.name); - dip->un.e.member[1].ord = LINE_IN_PORT; - strlcpy(dip->un.e.member[2].label.name, AudioNdac, - sizeof dip->un.e.member[2].label.name); - dip->un.e.member[2].ord = DAC_IN_PORT; - strlcpy(dip->un.e.member[3].label.name, AudioNcd, - sizeof dip->un.e.member[3].label.name); - dip->un.e.member[3].ord = AUX1_IN_PORT; - break; - - case YM_MASTER_EQMODE: - dip->type = AUDIO_MIXER_ENUM; - dip->mixer_class = YM_EQ_CLASS; - strlcpy(dip->label.name, AudioNmode, sizeof dip->label.name); - strlcpy(dip->un.v.units.name, AudioNmode, - sizeof dip->un.v.units.name); - dip->un.e.num_mem = 4; - strlcpy(dip->un.e.member[0].label.name, AudioNdesktop, - sizeof dip->un.e.member[0].label.name); - dip->un.e.member[0].ord = SA3_SYS_CTL_YMODE0; - strlcpy(dip->un.e.member[1].label.name, AudioNlaptop, - sizeof dip->un.e.member[1].label.name); - dip->un.e.member[1].ord = SA3_SYS_CTL_YMODE1; - strlcpy(dip->un.e.member[2].label.name, AudioNsubnote, - sizeof dip->un.e.member[2].label.name); - dip->un.e.member[2].ord = SA3_SYS_CTL_YMODE2; - strlcpy(dip->un.e.member[3].label.name, AudioNhifi, - sizeof dip->un.e.member[3].label.name); - dip->un.e.member[3].ord = SA3_SYS_CTL_YMODE3; - break; - - case YM_MASTER_TREBLE: - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = YM_EQ_CLASS; - strlcpy(dip->label.name, AudioNtreble, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNtreble, - sizeof dip->un.v.units.name); - break; - - case YM_MASTER_BASS: - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = YM_EQ_CLASS; - strlcpy(dip->label.name, AudioNbass, sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNbass, - sizeof dip->un.v.units.name); - break; - - case YM_MASTER_WIDE: - dip->type = AUDIO_MIXER_VALUE; - dip->mixer_class = YM_EQ_CLASS; - strlcpy(dip->label.name, AudioNsurround, - sizeof dip->label.name); - dip->un.v.num_channels = 2; - strlcpy(dip->un.v.units.name, AudioNsurround, - sizeof dip->un.v.units.name); - break; - - default: - return ENXIO; - /* NOTREACHED */ - } - - return 0; -} -#if NMIDI > 0 - -#define YMMPU(a) (&((struct ym_softc *)addr)->sc_mpu_sc) - -int -ym_mpu401_open(addr, flags, iintr, ointr, arg) - void *addr; - int flags; - void (*iintr)(void *, int); - void (*ointr)(void *); - void *arg; -{ - return mpu_open(YMMPU(addr), flags, iintr, ointr, arg); -} - -int -ym_mpu401_output(addr, d) - void *addr; - int d; -{ - return mpu_output(YMMPU(addr), d); -} - -void -ym_mpu401_close(addr) - void *addr; -{ - mpu_close(YMMPU(addr)); -} - -void -ym_mpu401_getinfo(addr, mi) - void *addr; - struct midi_info *mi; -{ - mi->name = "YM MPU-401 UART"; - mi->props = 0; -} -#endif diff --git a/sys/dev/isa/ym_isapnp.c b/sys/dev/isa/ym_isapnp.c deleted file mode 100644 index 55e644cc2a9..00000000000 --- a/sys/dev/isa/ym_isapnp.c +++ /dev/null @@ -1,123 +0,0 @@ -/* $OpenBSD: ym_isapnp.c,v 1.10 2014/09/14 14:17:25 jsg Exp $ */ - - -/* - * Copyright (c) 1998 Constantine Sapuntzakis. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. The name of the author may not be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR - * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. - * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, - * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT - * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF - * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -/* - * Driver for the Yamaha OPL3-SA3 chipset. This is found on many laptops - * and Pentium (II) motherboards. - */ - -#include "midi.h" - -#include <sys/param.h> -#include <sys/systm.h> -#include <sys/errno.h> -#include <sys/ioctl.h> -#include <sys/syslog.h> -#include <sys/device.h> - -#include <sys/audioio.h> -#include <dev/audio_if.h> -#include <dev/midi_if.h> - -#include <dev/isa/isavar.h> -#include <dev/isa/isadmavar.h> - -#include <dev/ic/ad1848reg.h> -#include <dev/isa/ad1848var.h> - -#include <dev/ic/cs4231reg.h> -#include <dev/isa/cs4231var.h> -#include <dev/ic/mpuvar.h> - -#include <dev/isa/wssreg.h> -#include <dev/isa/ymvar.h> - -int ym_isapnp_match(struct device *, void *, void *); -void ym_isapnp_attach(struct device *, struct device *, void *); - -struct cfattach ym_isapnp_ca = { - sizeof(struct ym_softc), ym_isapnp_match, ym_isapnp_attach -}; - -/* - * Probe / attach routines. - */ - -/* - * Probe for the soundblaster hardware. - */ -int -ym_isapnp_match(parent, match, aux) - struct device *parent; - void *match, *aux; -{ - struct isa_attach_args *ia = aux; - - if (ia->ipa_nio < 5) - return 0; - return 1; -} - -/* - * Attach hardware to driver, attach hardware driver to audio - * pseudo-device driver. - */ -void -ym_isapnp_attach(parent, self, aux) - struct device *parent, *self; - void *aux; -{ - struct ym_softc *sc = (struct ym_softc *)self; - struct isa_attach_args *ia = aux; - - sc->sc_iot = ia->ia_iot; - sc->sc_ioh = ia->ipa_io[1].h; - sc->sc_ic = ia->ia_ic; - - sc->ym_irq = ia->ipa_irq[0].num; - sc->ym_drq = ia->ipa_drq[0].num; - sc->ym_recdrq = ia->ipa_drq[1].num; - - sc->sc_controlioh = ia->ipa_io[4].h; - - sc->sc_ad1848.sc_ioh = sc->sc_ioh; - sc->sc_ad1848.sc_isa = parent->dv_parent; - sc->sc_ad1848.sc_iot = sc->sc_iot; - sc->sc_ad1848.sc_iooffs = WSS_CODEC; - sc->sc_ad1848.mode = 2; - sc->sc_ad1848.MCE_bit = MODE_CHANGE_ENABLE; - sc->sc_ad1848.sc_flags = AD1848_FLAG_32REGS; - -#if NMIDI > 0 - sc->sc_mpu_sc.iobase = ia->ipa_io[3].base; - sc->sc_mpu_sc.ioh = ia->ipa_io[3].h; -#endif - - ym_attach(sc); -} diff --git a/sys/dev/isa/ymvar.h b/sys/dev/isa/ymvar.h deleted file mode 100644 index b53272c8ef2..00000000000 --- a/sys/dev/isa/ymvar.h +++ /dev/null @@ -1,101 +0,0 @@ -/* $OpenBSD: ymvar.h,v 1.5 2002/03/14 01:26:57 millert Exp $ */ -/* $NetBSD: wssvar.h,v 1.1 1998/01/19 22:18:25 augustss Exp $ */ - -/* - * Copyright (c) 1998 Constantine Sapuntzakis. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. The name of the author may not be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR - * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. - * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, - * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT - * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF - * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -/* - * Mixer devices - */ -#define YM_MIDI_LVL 0 -#define YM_CD_LVL 1 -#define YM_DAC_LVL 2 -#define YM_LINE_LVL 3 -#define YM_SPEAKER_LVL 4 -#define YM_MIC_LVL 5 -#define YM_MONITOR_LVL 6 -#define YM_MIDI_MUTE 7 -#define YM_CD_MUTE 8 -#define YM_DAC_MUTE 9 -#define YM_LINE_MUTE 10 -#define YM_SPEAKER_MUTE 11 -#define YM_MIC_MUTE 12 -#define YM_MONITOR_MUTE 13 - -#define YM_REC_LVL 14 -#define YM_RECORD_SOURCE 15 - -#define YM_OUTPUT_LVL 16 -#define YM_OUTPUT_MUTE 17 - -#define YM_MASTER_EQMODE 18 -#define YM_MASTER_TREBLE 19 -#define YM_MASTER_BASS 20 -#define YM_MASTER_WIDE 21 - -/* Classes - don't change this without looking at mixer_classes array */ -#define YM_CLASS_TOP 22 -#define YM_INPUT_CLASS (YM_CLASS_TOP + 0) -#define YM_RECORD_CLASS (YM_CLASS_TOP + 1) -#define YM_OUTPUT_CLASS (YM_CLASS_TOP + 2) -#define YM_MONITOR_CLASS (YM_CLASS_TOP + 3) -#define YM_EQ_CLASS (YM_CLASS_TOP + 4) - -#define AudioNmode "mode" -#define AudioNdesktop "desktop" -#define AudioNlaptop "laptop" -#define AudioNsubnote "subnote" -#define AudioNhifi "hifi" - -struct ym_softc { - struct device sc_dev; /* base device */ - struct isadev sc_id; /* ISA device */ - void *sc_ih; /* interrupt vectoring */ - bus_space_tag_t sc_iot; /* tag */ - bus_space_handle_t sc_ioh; /* handle */ - isa_chipset_tag_t sc_ic; - - bus_space_handle_t sc_controlioh; - - struct ad1848_softc sc_ad1848; -#define ym_irq sc_ad1848.sc_irq -#define ym_drq sc_ad1848.sc_drq -#define ym_recdrq sc_ad1848.sc_recdrq - - int master_mute, mic_mute; - struct ad1848_volume master_gain; - u_int8_t mic_gain; - - /* 3D enhancement */ - u_int8_t sc_eqmode; - struct ad1848_volume sc_treble, sc_bass, sc_wide; -#if NMIDI > 0 - int sc_hasmpu; - struct mpu_softc sc_mpu_sc; /* MPU401 Uart state */ -#endif -}; - -void ym_attach(struct ym_softc *); |