Source-Changes-HG archive

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

[src/trunk]: src/sys/dev/ic create a funcion, siop_busreset(), to reset the s...



details:   https://anonhg.NetBSD.org/src/rev/2a710076aaa5
branches:  trunk
changeset: 495236:2a710076aaa5
user:      bouyer <bouyer%NetBSD.org@localhost>
date:      Mon Jul 24 15:15:00 2000 +0000

description:
create a funcion, siop_busreset(), to reset the scsibus.
Reset the scsi bus at attach time, to be sure all devices start in narrow/async
mode.
Defer sync/wide negotiation until after whe have a valid
xs->sc_link->device_softc, so that we can honnor the NOSYNC/NOWIDE quirks.

diffstat:

 sys/dev/ic/siop.c           |  43 +++++++++++++++++++++++++------------------
 sys/dev/ic/siop_common.c    |  41 ++++++++++++++++++++++++++++++-----------
 sys/dev/ic/siopvar_common.h |   3 ++-
 3 files changed, 57 insertions(+), 30 deletions(-)

diffs (199 lines):

diff -r 79dc6c34c0a2 -r 2a710076aaa5 sys/dev/ic/siop.c
--- a/sys/dev/ic/siop.c Mon Jul 24 15:07:02 2000 +0000
+++ b/sys/dev/ic/siop.c Mon Jul 24 15:15:00 2000 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: siop.c,v 1.25 2000/07/19 16:07:00 pk Exp $     */
+/*     $NetBSD: siop.c,v 1.26 2000/07/24 15:15:00 bouyer Exp $ */
 
 /*
  * Copyright (c) 2000 Manuel Bouyer.
@@ -250,6 +250,11 @@
        }
        if (sc->maxsync == 255 || sc->minsync == 0)
                panic("siop: can't find my sync parameters\n");
+       /* Do a bus reset, so that devices fall back to narrow/async */
+       siop_resetbus(sc);
+       /*
+        * siop_reset() will reset the chip, thus clearing pending interrupts
+        */
        siop_reset(sc);
 #ifdef DUMP_SCRIPT
        siop_dump_script(sc);
@@ -357,7 +362,7 @@
        struct siop_target *siop_target;
        struct siop_cmd *siop_cmd;
        struct scsipi_xfer *xs;
-       int istat, sist0, sist1, sstat1, dstat, scntl1;
+       int istat, sist0, sist1, sstat1, dstat;
        u_int32_t irqcode;
        int need_reset = 0;
        int offset, target, lun;
@@ -601,12 +606,7 @@
        if (need_reset) {
 reset:
                /* fatal error, reset the bus */
-               scntl1 = bus_space_read_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1);
-               bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1,
-                   scntl1 | SCNTL1_RST);
-               /* minimum 25 us, more time won't hurt */
-               delay(100);
-               bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1, scntl1);
+               siop_resetbus(sc);
                /* no table to flush here */
                return 1;
        }
@@ -685,6 +685,13 @@
                                        printf("%s: target %d using 8bit "
                                            "transfers\n", sc->sc_dev.dv_xname,
                                            xs->sc_link->scsipi_scsi.target);
+                                       if (xs->sc_link->quirks & SDEV_NOSYNC) {
+                                               siop_cmd->siop_target->status =
+                                                   TARST_OK;
+                                               /* no table to flush here */
+                                               CALL_SCRIPT(Ent_msgin_ack);
+                                               return 1;
+                                       }
                                        siop_target->status = TARST_SYNC_NEG;
                                        siop_cmd->siop_table->msg_out[0] =
                                            MSG_EXTENDED;
@@ -789,6 +796,8 @@
                                            BUS_DMASYNC_PREWRITE);
                                        CALL_SCRIPT(Ent_send_msgout);
                                        break;
+                               case SIOP_NEG_ACK:
+                                       CALL_SCRIPT(Ent_msgin_ack);
                                default:
                                        panic("invalid retval from "
                                            "siop_wdtr_neg()");
@@ -905,7 +914,8 @@
                                siop_start(sc);
                                return 1;
                        }
-                       if (siop_target->status == TARST_PROBING)
+                       if (siop_target->status == TARST_PROBING &&
+                           xs->sc_link->device_softc != NULL)
                                siop_target->status = TARST_ASYNC;
 #ifdef DEBUG_INTR
                        printf("done, DSA=0x%lx target id 0x%x last msg "
@@ -1177,7 +1187,8 @@
        siop_cmd->siop_table->msg_out[2] = 0;
 #endif
        if (sc->targets[target]->status == TARST_ASYNC) {
-               if (sc->features & SF_BUS_WIDE) {
+               if (sc->features & SF_BUS_WIDE &&
+                   (xs->sc_link->quirks & SDEV_NOWIDE) == 0) {
                        sc->targets[target]->status = TARST_WIDE_NEG;
                        siop_cmd->siop_table->msg_out[1] = MSG_EXTENDED;
                        siop_cmd->siop_table->msg_out[2] = MSG_EXT_WDTR_LEN;
@@ -1186,7 +1197,7 @@
                            MSG_EXT_WDTR_BUS_16_BIT;
                        siop_cmd->siop_table->t_msgout.count=
                            htole32(MSG_EXT_WDTR_LEN + 2 + 1);
-               } else {
+               } else if ((xs->sc_link->quirks & SDEV_NOSYNC) == 0) {
                        sc->targets[target]->status = TARST_SYNC_NEG;
                        siop_cmd->siop_table->msg_out[1] = MSG_EXTENDED;
                        siop_cmd->siop_table->msg_out[2] = MSG_EXT_SDTR_LEN;
@@ -1195,6 +1206,8 @@
                        siop_cmd->siop_table->msg_out[5] = sc->maxoff;
                        siop_cmd->siop_table->t_msgout.count=
                            htole32(MSG_EXT_SDTR_LEN + 2 +1);
+               } else {
+                       sc->targets[target]->status = TARST_OK;
                }
        }
        siop_cmd->siop_table->status = htole32(0xff); /* set invalid status */
@@ -1394,19 +1407,13 @@
        struct siop_cmd *siop_cmd = v;
        struct siop_softc *sc = siop_cmd->siop_target->siop_sc;
        int s;
-       u_int8_t scntl1;
 
        scsi_print_addr(siop_cmd->xs->sc_link);
        printf("command timeout\n");
 
        s = splbio();
        /* reset the scsi bus */
-       scntl1 = bus_space_read_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1);
-       bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1,
-           scntl1 | SCNTL1_RST);
-       /* minimum 25 us, more time won't hurt */
-       delay(100);
-       bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1, scntl1);
+       siop_resetbus(sc);
 
        /* deactivate callout */
        callout_stop(&siop_cmd->xs->xs_callout);
diff -r 79dc6c34c0a2 -r 2a710076aaa5 sys/dev/ic/siop_common.c
--- a/sys/dev/ic/siop_common.c  Mon Jul 24 15:07:02 2000 +0000
+++ b/sys/dev/ic/siop_common.c  Mon Jul 24 15:15:00 2000 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: siop_common.c,v 1.5 2000/06/28 17:13:04 mrg Exp $      */
+/*     $NetBSD: siop_common.c,v 1.6 2000/07/24 15:15:01 bouyer Exp $   */
 
 /*
  * Copyright (c) 2000 Manuel Bouyer.
@@ -168,16 +168,22 @@
                    SIOP_SCNTL3,
                    (sc->targets[target]->id >> 24) & 0xff);
                /* we now need to do sync */
-               siop_target->status = TARST_SYNC_NEG;
-               siop_cmd->siop_table->msg_out[0] = MSG_EXTENDED;
-               siop_cmd->siop_table->msg_out[1] = MSG_EXT_SDTR_LEN;
-               siop_cmd->siop_table->msg_out[2] = MSG_EXT_SDTR;
-               siop_cmd->siop_table->msg_out[3] = sc->minsync;
-               siop_cmd->siop_table->msg_out[4] = sc->maxoff;
-               siop_cmd->siop_table->t_msgout.count =
-                   htole32(MSG_EXT_SDTR_LEN + 2);
-               siop_cmd->siop_table->t_msgout.addr = htole32(siop_cmd->dsa);
-               return SIOP_NEG_MSGOUT;
+               if ((siop_cmd->xs->sc_link->quirks & SDEV_NOSYNC) == 0) {
+                       siop_target->status = TARST_SYNC_NEG;
+                       siop_cmd->siop_table->msg_out[0] = MSG_EXTENDED;
+                       siop_cmd->siop_table->msg_out[1] = MSG_EXT_SDTR_LEN;
+                       siop_cmd->siop_table->msg_out[2] = MSG_EXT_SDTR;
+                       siop_cmd->siop_table->msg_out[3] = sc->minsync;
+                       siop_cmd->siop_table->msg_out[4] = sc->maxoff;
+                       siop_cmd->siop_table->t_msgout.count =
+                           htole32(MSG_EXT_SDTR_LEN + 2);
+                       siop_cmd->siop_table->t_msgout.addr =
+                           htole32(siop_cmd->dsa);
+                       return SIOP_NEG_MSGOUT;
+               } else {
+                       siop_target->status = TARST_OK;
+                       return SIOP_NEG_ACK;
+               }
        } else {
                /* target initiated wide negotiation */
                if (siop_cmd->siop_table->msg_in[3] >= MSG_EXT_WDTR_BUS_16_BIT
@@ -528,3 +534,16 @@
            sc->sc_dev.dv_xname);
        return 0;
 }
+
+void
+siop_resetbus(sc)
+       struct siop_softc *sc;
+{
+       int scntl1;
+       scntl1 = bus_space_read_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1);
+       bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1,
+           scntl1 | SCNTL1_RST);
+       /* minimum 25 us, more time won't hurt */
+       delay(100);
+       bus_space_write_1(sc->sc_rt, sc->sc_rh, SIOP_SCNTL1, scntl1);
+}
diff -r 79dc6c34c0a2 -r 2a710076aaa5 sys/dev/ic/siopvar_common.h
--- a/sys/dev/ic/siopvar_common.h       Mon Jul 24 15:07:02 2000 +0000
+++ b/sys/dev/ic/siopvar_common.h       Mon Jul 24 15:15:00 2000 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: siopvar_common.h,v 1.3 2000/06/12 20:13:41 bouyer Exp $        */
+/*     $NetBSD: siopvar_common.h,v 1.4 2000/07/24 15:15:01 bouyer Exp $        */
 
 /*
  * Copyright (c) 2000 Manuel Bouyer.
@@ -140,3 +140,4 @@
                caddr_t, int, struct proc *));
 void   siop_sdp __P((struct siop_cmd *));
 void   siop_clearfifo __P((struct siop_softc *));
+void   siop_resetbus __P((struct siop_softc *));



Home | Main Index | Thread Index | Old Index