[PATCH 1/5] AIC7xxx : remove qfrozen This patch remove the need for platform_data->qfrozen. Similar to his aic79xx couterpart. Signed-off-by: Emmanuel Fusté <emmanuel.fuste@xxxxxxxxxxx> --- Accédez au courrier électronique de La Poste : www.laposte.net ; 3615 LAPOSTENET (0,34 ?/mn) ; tél : 08 92 68 13 50 (0,34?/mn)
diff -upN linux-source-2.6.16-orig3/drivers/scsi/aic7xxx/aic7xxx_osm.c linux-source-2.6.16/drivers/scsi/aic7xxx/aic7xxx_osm.c --- linux-source-2.6.16-orig3/drivers/scsi/aic7xxx/aic7xxx_osm.c 2006-03-27 16:58:49.000000000 +0200 +++ linux-source-2.6.16/drivers/scsi/aic7xxx/aic7xxx_osm.c 2006-03-27 17:59:50.000000000 +0200 @@ -373,8 +373,6 @@ static void ahc_linux_handle_scsi_status struct scb *); static void ahc_linux_queue_cmd_complete(struct ahc_softc *ahc, struct scsi_cmnd *cmd); -static void ahc_linux_freeze_simq(struct ahc_softc *ahc); -static void ahc_linux_release_simq(struct ahc_softc *ahc); static int ahc_linux_queue_recovery_cmd(struct scsi_cmnd *cmd, scb_flag flag); static void ahc_linux_initialize_scsi_bus(struct ahc_softc *ahc); static u_int ahc_linux_user_tagdepth(struct ahc_softc *ahc, @@ -475,18 +473,13 @@ ahc_linux_queue(struct scsi_cmnd * cmd, { struct ahc_softc *ahc; struct ahc_linux_device *dev = scsi_transport_device_data(cmd->device); - int rtn = SCSI_MLQUEUE_HOST_BUSY; - unsigned long flags; + int rtn; ahc = *(struct ahc_softc **)cmd->device->host->hostdata; - ahc_lock(ahc, &flags); - if (ahc->platform_data->qfrozen == 0) { - cmd->scsi_done = scsi_done; - cmd->result = CAM_REQ_INPROG << 16; - rtn = ahc_linux_run_command(ahc, dev, cmd); - } - ahc_unlock(ahc, &flags); + cmd->scsi_done = scsi_done; + cmd->result = CAM_REQ_INPROG << 16; + rtn = ahc_linux_run_command(ahc, dev, cmd); return rtn; } @@ -747,14 +740,11 @@ ahc_linux_bus_reset(struct scsi_cmnd *cm { struct ahc_softc *ahc; int found; - unsigned long flags; ahc = *(struct ahc_softc **)cmd->device->host->hostdata; - ahc_lock(ahc, &flags); found = ahc_reset_channel(ahc, scmd_channel(cmd) + 'A', /*initiate reset*/TRUE); - ahc_unlock(ahc, &flags); if (bootverbose) printf("%s: SCSI bus reset delivered. " @@ -1175,9 +1165,9 @@ ahc_linux_initialize_scsi_bus(struct ahc ahc_unlock(ahc, &s); /* Give the bus some time to recover */ if ((ahc->flags & (AHC_RESET_BUS_A|AHC_RESET_BUS_B)) != 0) { - ahc_linux_freeze_simq(ahc); + scsi_block_requests(ahc->platform_data->host); msleep(AIC7XXX_RESET_DELAY); - ahc_linux_release_simq(ahc); + scsi_unblock_requests(ahc->platform_data->host); } } @@ -1420,13 +1410,9 @@ ahc_linux_run_command(struct ahc_softc * struct ahc_tmode_tstate *tstate; uint16_t mask; struct scb_tailq *untagged_q = NULL; + unsigned long flags; - /* - * Schedule us to run later. The only reason we are not - * running is because the whole controller Q is frozen. - */ - if (ahc->platform_data->qfrozen != 0) - return SCSI_MLQUEUE_HOST_BUSY; + ahc_lock(ahc, &flags); /* * We only allow one untagged transaction @@ -1440,18 +1426,22 @@ ahc_linux_run_command(struct ahc_softc * target_offset = cmd->device->id + cmd->device->channel * 8; untagged_q = &(ahc->untagged_queues[target_offset]); - if (!TAILQ_EMPTY(untagged_q)) + if (!TAILQ_EMPTY(untagged_q)) { /* if we're already executing an untagged command * we're busy to another */ + ahc_unlock(ahc, &flags); return SCSI_MLQUEUE_DEVICE_BUSY; + } } /* * Get an scb to use. */ scb = ahc_get_scb(ahc); - if (!scb) + if (!scb) { + ahc_unlock(ahc, &flags); return SCSI_MLQUEUE_HOST_BUSY; + } scb->io_ctx = cmd; scb->platform_data->dev = dev; @@ -1602,6 +1592,9 @@ ahc_linux_run_command(struct ahc_softc * scb->flags |= SCB_UNTAGGEDQ; } ahc_queue_scb(ahc, scb); + + ahc_unlock(ahc, &flags); + return 0; } @@ -1637,7 +1630,6 @@ ahc_send_async(struct ahc_softc *ahc, ch { char buf[80]; struct scsi_target *starget; - struct ahc_linux_target *targ; struct info_str info; struct ahc_initiator_tinfo *tinfo; struct ahc_tmode_tstate *tstate; @@ -1676,7 +1668,6 @@ ahc_send_async(struct ahc_softc *ahc, ch starget = ahc->platform_data->starget[target_offset]; if (starget == NULL) break; - targ = scsi_transport_target_data(starget); target_ppr_options = (spi_dt(starget) ? MSG_EXT_PPR_DT_REQ : 0) @@ -2036,47 +2027,6 @@ ahc_linux_queue_cmd_complete(struct ahc_ cmd->scsi_done(cmd); } -static void -ahc_linux_freeze_simq(struct ahc_softc *ahc) -{ - unsigned long s; - - ahc_lock(ahc, &s); - ahc->platform_data->qfrozen++; - if (ahc->platform_data->qfrozen == 1) { - scsi_block_requests(ahc->platform_data->host); - - /* XXX What about Twin channels? */ - ahc_platform_abort_scbs(ahc, CAM_TARGET_WILDCARD, ALL_CHANNELS, - CAM_LUN_WILDCARD, SCB_LIST_NULL, - ROLE_INITIATOR, CAM_REQUEUE_REQ); - } - ahc_unlock(ahc, &s); -} - -static void -ahc_linux_release_simq(struct ahc_softc *ahc) -{ - u_long s; - int unblock_reqs; - - unblock_reqs = 0; - ahc_lock(ahc, &s); - if (ahc->platform_data->qfrozen > 0) - ahc->platform_data->qfrozen--; - if (ahc->platform_data->qfrozen == 0) - unblock_reqs = 1; - ahc_unlock(ahc, &s); - /* - * There is still a race here. The mid-layer - * should keep its own freeze count and use - * a bottom half handler to run the queues - * so we can unblock with our own lock held. - */ - if (unblock_reqs) - scsi_unblock_requests(ahc->platform_data->host); -} - static int ahc_linux_queue_recovery_cmd(struct scsi_cmnd *cmd, scb_flag flag) { @@ -2341,19 +2291,24 @@ done: ahc->platform_data->eh_done = &done; ahc_unlock(ahc, &flags); - printf("Recovery code sleeping\n"); + printf("%s: Recovery code sleeping\n", ahc_name(ahc)); if (!wait_for_completion_timeout(&done, 5 * HZ)) { ahc_lock(ahc, &flags); ahc->platform_data->eh_done = NULL; ahc_unlock(ahc, &flags); - - printf("Timer Expired\n"); + printf("%s: Timer Expired (active %d)\n", + ahc_name(ahc), dev->active); retval = FAILED; } printf("Recovery code awake\n"); } else ahc_unlock(ahc, &flags); - return (retval); + + if (retval != SUCCESS) + printf("%s: Command abort returning 0x%x\n", + ahc_name(ahc), retval); + + return retval; } void diff -upN linux-source-2.6.16-orig3/drivers/scsi/aic7xxx/aic7xxx_osm.h linux-source-2.6.16/drivers/scsi/aic7xxx/aic7xxx_osm.h --- linux-source-2.6.16-orig3/drivers/scsi/aic7xxx/aic7xxx_osm.h 2006-03-27 16:58:49.000000000 +0200 +++ linux-source-2.6.16/drivers/scsi/aic7xxx/aic7xxx_osm.h 2006-03-27 17:36:25.000000000 +0200 @@ -368,7 +368,6 @@ struct ahc_platform_data { struct scsi_target *starget[AHC_NUM_TARGETS]; spinlock_t spin_lock; - u_int qfrozen; struct completion *eh_done; struct Scsi_Host *host; /* pointer to scsi host */ #define AHC_LINUX_NOIRQ ((uint32_t)~0) Common subdirectories: linux-source-2.6.16-orig3/drivers/scsi/aic7xxx/aicasm and linux-source-2.6.16/drivers/scsi/aic7xxx/aicasm