Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/dev/mca Convert over to use the new MCA DMA facilities, ...



details:   https://anonhg.NetBSD.org/src/rev/323ac2a0d02f
branches:  trunk
changeset: 518064:323ac2a0d02f
user:      jdolecek <jdolecek%NetBSD.org@localhost>
date:      Fri Nov 23 22:53:09 2001 +0000

description:
Convert over to use the new MCA DMA facilities, which encapsulate
the MCA DMA controller access. This also means we gain >16MB RAM support.

While here, overhaul the driver to saner state, especially:
* simplify and clean the attach code a lot, and support the 'drive'
  locator
* pass proper dev_t to readdisklabel() - formerly, the passed value was
  completely broken (used incorrect major and wrong minor), but worked
  by accident
* worker thread is now spawned per controller, rather than per-drive;
  i/o cannot be done concurrently by different drivers, only one
  i/o can be pending at any time
* simplify the command queue code, just sleep appropriately when
  !poll case, g/c 'async' code formerly needed, move the bio code
  from ed_mca.c to edc_mca.c:edc_bio()
* put all string arrays used by edc_dump_status_block() within #ifdef EDC_DEBUG,
  and use numbers instead if it's not defined; this cuts object size by 5KB
* other misc cleanups

diffstat:

 sys/dev/mca/ed_mca.c  |  564 ++++++++-----------------------------------------
 sys/dev/mca/edc_mca.c |  501 ++++++++++++++++++++++++++------------------
 2 files changed, 396 insertions(+), 669 deletions(-)

diffs (truncated from 1632 to 300 lines):

diff -r 25989d070011 -r 323ac2a0d02f sys/dev/mca/ed_mca.c
--- a/sys/dev/mca/ed_mca.c      Fri Nov 23 22:35:46 2001 +0000
+++ b/sys/dev/mca/ed_mca.c      Fri Nov 23 22:53:09 2001 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: ed_mca.c,v 1.9 2001/11/13 07:46:25 lukem Exp $ */
+/*     $NetBSD: ed_mca.c,v 1.10 2001/11/23 22:53:10 jdolecek Exp $     */
 
 /*
  * Copyright (c) 2001 The NetBSD Foundation, Inc.
@@ -34,13 +34,14 @@
  */
 
 /*
- * Disk goo for MCA ESDI controller driver.
+ * Disk drive goo for MCA ESDI controller driver.
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ed_mca.c,v 1.9 2001/11/13 07:46:25 lukem Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ed_mca.c,v 1.10 2001/11/23 22:53:10 jdolecek Exp $");
 
 #include "rnd.h"
+#include "locators.h"
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -58,7 +59,6 @@
 #include <sys/syslog.h>
 #include <sys/proc.h>
 #include <sys/vnode.h>
-#include <sys/kthread.h>
 #if NRND > 0
 #include <sys/rnd.h>
 #endif
@@ -95,19 +95,11 @@
 
 extern struct cfdriver ed_cd;
 
-static int     ed_get_params __P((struct ed_softc *));
+static int     ed_get_params __P((struct ed_softc *, int *));
 static int     ed_lock __P((struct ed_softc *));
 static void    ed_unlock       __P((struct ed_softc *));
-static void    edgetdisklabel  __P((struct ed_softc *));
+static void    edgetdisklabel  __P((dev_t, struct ed_softc *));
 static void    edgetdefaultlabel __P((struct ed_softc *, struct disklabel *));
-static void    ed_shutdown __P((void*));
-static void    __edstart __P((struct ed_softc*, struct buf *));
-static void    bad144intern __P((struct ed_softc *));
-static void    edworker __P((void *));
-static void    ed_spawn_worker __P((void *));
-static void    edmcadone __P((struct ed_softc *, struct buf *));
-static void    ed_bio __P((struct ed_softc *, int, int));
-static void    ed_bio_done __P((struct ed_softc *));
 
 static struct dkdriver eddkdriver = { edmcastrategy };
 
@@ -115,22 +107,29 @@
  * Just check if it's possible to identify the disk.
  */
 static int
-ed_mca_probe(parent, match, aux)
+ed_mca_probe(parent, cf, aux)
        struct device *parent;
-       struct cfdata *match;
+       struct cfdata *cf;
        void *aux;
 {
        u_int16_t cmd_args[2];
        struct edc_mca_softc *sc = (void *) parent;
-       struct ed_attach_args *eda = (void *) aux;
+       struct ed_attach_args *eda = (struct ed_attach_args *) aux;
        int found = 1;
 
        /*
+        * Check we match hardwired config.
+        */
+       if (cf->edccf_unit != EDCCF_DRIVE_DEFAULT &&
+           cf->edccf_unit != eda->edc_drive)
+               return (0);
+
+       /*
         * Get Device Configuration (09).
         */
        cmd_args[0] = 14;       /* Options: 00s110, s: 0=Physical 1=Pseudo */
        cmd_args[1] = 0;
-       if (edc_run_cmd(sc, CMD_GET_DEV_CONF, eda->sc_devno, cmd_args, 2, 0, 1))
+       if (edc_run_cmd(sc, CMD_GET_DEV_CONF, eda->edc_drive, cmd_args, 2, 1))
                found = 0;
 
        return (found);
@@ -143,20 +142,20 @@
 {
        struct ed_softc *ed = (void *) self;
        struct edc_mca_softc *sc = (void *) parent;
-       struct ed_attach_args *eda = (void *) aux;
-       char pbuf[8];
-       int error, nsegs;
+       struct ed_attach_args *eda = (struct ed_attach_args *) aux;
+       char pbuf[8], lckname[10];
+       int drv_flags;
 
        ed->edc_softc = sc;
-       ed->sc_dmat = eda->sc_dmat;
-       ed->sc_devno = eda->sc_devno;
-       edc_add_disk(sc, ed, eda->sc_devno);
+       ed->sc_devno  = eda->edc_drive;
+       edc_add_disk(sc, ed);
 
        BUFQ_INIT(&ed->sc_q);
        simple_lock_init(&ed->sc_q_lock);
-       lockinit(&ed->sc_lock, PRIBIO | PCATCH, "edlck", 0, 0);
+       snprintf(lckname, sizeof(lckname), "%slck", ed->sc_dev.dv_xname);
+       lockinit(&ed->sc_lock, PRIBIO | PCATCH, lckname, 0, 0);
 
-       if (ed_get_params(ed)) {
+       if (ed_get_params(ed, &drv_flags)) {
                printf(": IDENTIFY failed, no disk found\n");
                return;
        }
@@ -170,88 +169,27 @@
 
        printf("%s: %u spares/cyl, %s, %s, %s, %s, %s\n",
                ed->sc_dev.dv_xname, ed->spares,
-               (ed->drv_flags & (1 << 0)) ? "NoRetries" : "Retries",
-               (ed->drv_flags & (1 << 1)) ? "Removable" : "Fixed",
-               (ed->drv_flags & (1 << 2)) ? "SkewedFormat" : "NoSkew",
-               (ed->drv_flags & (1 << 3)) ? "ZeroDefect" : "Defects",
-               (ed->drv_flags & (1 << 4)) ? "InvalidSecondary" : "SecondaryOK"
+               (drv_flags & (1 << 0)) ? "NoRetries" : "Retries",
+               (drv_flags & (1 << 1)) ? "Removable" : "Fixed",
+               (drv_flags & (1 << 2)) ? "SkewedFormat" : "NoSkew",
+               (drv_flags & (1 << 3)) ? "ZeroDefect" : "Defects",
+               (drv_flags & (1 << 4)) ? "InvalidSecondary" : "SecondaryOK"
                );
 
-       /* Create a DMA map for mapping individual transfer bufs */
-       if ((error = bus_dmamap_create(ed->sc_dmat, 65536, 1,
-               65536, 65536, BUS_DMA_WAITOK | BUS_DMA_ALLOCNOW,
-               &ed->dmamap_xfer)) != 0) {
-               printf("%s: unable to create xfer DMA map, error=%d\n",
-                       ed->sc_dev.dv_xname, error);
-               return;
-       }
-
-       /*
-        * Allocate DMA memory used in case where passed buf isn't
-        * physically contiguous.
-        */
-       ed->sc_dmam_sz = MAXPHYS;
-       if ((error = bus_dmamem_alloc(ed->sc_dmat, ed->sc_dmam_sz,
-               ed->sc_dmam_sz, 65536, ed->sc_dmam, 1, &nsegs,
-               BUS_DMA_WAITOK|BUS_DMA_STREAMING)) != 0) {
-               printf("%s: unable to allocate DMA memory for xfer, errno=%d\n",
-                               ed->sc_dev.dv_xname, error);
-               bus_dmamap_destroy(ed->sc_dmat, ed->dmamap_xfer);
-               return;
-       }
-       /*
-        * Map the memory.
-        */
-       if ((error = bus_dmamem_map(ed->sc_dmat, ed->sc_dmam, 1,
-               ed->sc_dmam_sz, &ed->sc_dmamkva, BUS_DMA_WAITOK)) != 0) {
-               printf("%s: unable to map DMA memory, error=%d\n",
-                       ed->sc_dev.dv_xname, error);
-               bus_dmamem_free(ed->sc_dmat, ed->sc_dmam, 1);
-               bus_dmamap_destroy(ed->sc_dmat, ed->dmamap_xfer);
-               return;
-       }
-
-
        /*
         * Initialize and attach the disk structure.
         */
        ed->sc_dk.dk_driver = &eddkdriver;
        ed->sc_dk.dk_name = ed->sc_dev.dv_xname;
        disk_attach(&ed->sc_dk);
-#if 0
-       wd->sc_wdc_bio.lp = wd->sc_dk.dk_label;
-#endif
-       ed->sc_sdhook = shutdownhook_establish(ed_shutdown, ed);
-       if (ed->sc_sdhook == NULL)
-               printf("%s: WARNING: unable to establish shutdown hook\n",
-                   ed->sc_dev.dv_xname);
 #if NRND > 0
        rnd_attach_source(&ed->rnd_source, ed->sc_dev.dv_xname,
                          RND_TYPE_DISK, 0);
 #endif
 
-       config_pending_incr();
-       kthread_create(ed_spawn_worker, (void *) ed);
-
        ed->sc_flags |= EDF_INIT;
 }
 
-void
-ed_spawn_worker(arg)
-       void *arg;
-{
-       struct ed_softc *ed = (struct ed_softc *) arg;
-       int error;
-
-       /* Now, everything is ready, start a kthread */
-       if ((error = kthread_create1(edworker, ed, &ed->sc_worker,
-                       "%s", ed->sc_dev.dv_xname))) {
-               printf("%s: cannot spawn worker thread: errno=%d\n",
-                       ed->sc_dev.dv_xname, error);
-               panic("ed_spawn_worker");
-       }
-}
-
 /*
  * Read/write routine for a buffer.  Validates the arguments and schedules the
  * transfer.  Does not wait for the transfer to complete.
@@ -260,12 +198,12 @@
 edmcastrategy(bp)
        struct buf *bp;
 {
-       struct ed_softc *wd = device_lookup(&ed_cd, DISKUNIT(bp->b_dev));
-       struct disklabel *lp = wd->sc_dk.dk_label;
+       struct ed_softc *ed = device_lookup(&ed_cd, DISKUNIT(bp->b_dev));
+       struct disklabel *lp = ed->sc_dk.dk_label;
        daddr_t blkno;
        int s;
 
-       WDCDEBUG_PRINT(("edmcastrategy (%s)\n", wd->sc_dev.dv_xname),
+       WDCDEBUG_PRINT(("edmcastrategy (%s)\n", ed->sc_dev.dv_xname),
            DEBUG_XFERS);
 
        /* Valid request?  */
@@ -277,7 +215,7 @@
        }
 
        /* If device invalidated (e.g. media change, door open), error. */
-       if ((wd->sc_flags & WDF_LOADED) == 0) {
+       if ((ed->sc_flags & WDF_LOADED) == 0) {
                bp->b_error = EIO;
                goto bad;
        }
@@ -291,8 +229,8 @@
         * If end of partition, just return.
         */
        if (DISKPART(bp->b_dev) != RAW_PART &&
-           bounds_check_with_label(bp, wd->sc_dk.dk_label,
-           (wd->sc_flags & (WDF_WLABEL|WDF_LABELLING)) != 0) <= 0)
+           bounds_check_with_label(bp, ed->sc_dk.dk_label,
+           (ed->sc_flags & (WDF_WLABEL|WDF_LABELLING)) != 0) <= 0)
                goto done;
 
        /*
@@ -311,13 +249,12 @@
 
        /* Queue transfer on drive, activate drive and controller if idle. */
        s = splbio();
-       simple_lock(&wd->sc_q_lock);
-       disksort_blkno(&wd->sc_q, bp);
-       simple_unlock(&wd->sc_q_lock);
+       simple_lock(&ed->sc_q_lock);
+       disksort_blkno(&ed->sc_q, bp);
+       simple_unlock(&ed->sc_q_lock);
 
        /* Ring the worker thread */
-       wd->sc_flags |= EDF_PROCESS_QUEUE;
-       wakeup_one(&wd->sc_q);
+       wakeup_one(ed->edc_softc);
 
        splx(s);
        return;
@@ -329,141 +266,6 @@
        biodone(bp);
 }
 
-static void
-ed_bio(struct ed_softc *ed, int async, int poll)
-{
-       u_int16_t cmd_args[4];
-       int error=0;
-       u_int16_t track;
-       u_int16_t cyl;
-       u_int8_t head;
-       u_int8_t sector;
-
-       /* Get physical bus mapping for buf. */
-       if (bus_dmamap_load(ed->sc_dmat, ed->dmamap_xfer,
-                       ed->sc_data, ed->sc_bcount, NULL,
-                       BUS_DMA_WAITOK|BUS_DMA_STREAMING) != 0) {
-
-               /*
-                * Use our DMA safe memory to get data to/from device.
-                */
-               if ((error = bus_dmamap_load(ed->sc_dmat, ed->dmamap_xfer,
-                       ed->sc_dmamkva, ed->sc_bcount, NULL,
-                       BUS_DMA_WAITOK|BUS_DMA_STREAMING)) != 0) {
-                       printf("%s: unable to load raw data for xfer, errno=%d\n",
-                               ed->sc_dev.dv_xname, error);
-                       goto out;
-               }
-               ed->sc_flags |= EDF_BOUNCEBUF;
-
-               /* If data write, copy the data to our bounce buffer. */
-               if (!ed->sc_read)



Home | Main Index | Thread Index | Old Index