Commit 8cac8145 authored by Christoph Hellwig's avatar Christoph Hellwig Committed by James Bottomley
Browse files

[SCSI] aic7xxx: semaphore to completion conversion



On Tue, Jan 31, 2006 at 06:20:18PM +0100, Christoph Hellwig wrote:
> switch eh_sem to a completion.  due to wait_for_completion_timeout this
> also nicely simplifies the code.  Unfortunately it's untested, so if
> someone with the hardware could give it a try that would be nice.  Once
> it works the same thing can be applied to aic79xx.

New version that switches to the common onstack completion and just a
pointer in the platform_data struct idiom.  This gets rid of all the
flags fiddling.

Signed-off-by: default avatarChristoph Hellwig <hch@lst.de>
Signed-off-by: default avatarJames Bottomley <James.Bottomley@SteelEye.com>
parent fe27381d
Loading
Loading
Loading
Loading
+11 −34
Original line number Diff line number Diff line
@@ -373,7 +373,6 @@ static void ahc_linux_handle_scsi_status(struct ahc_softc *,
					 struct scb *);
static void ahc_linux_queue_cmd_complete(struct ahc_softc *ahc,
					 struct scsi_cmnd *cmd);
static void ahc_linux_sem_timeout(u_long arg);
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);
@@ -1193,7 +1192,6 @@ ahc_platform_alloc(struct ahc_softc *ahc, void *platform_arg)
	memset(ahc->platform_data, 0, sizeof(struct ahc_platform_data));
	ahc->platform_data->irq = AHC_LINUX_NOIRQ;
	ahc_lockinit(ahc);
	init_MUTEX_LOCKED(&ahc->platform_data->eh_sem);
	ahc->seltime = (aic7xxx_seltime & 0x3) << 4;
	ahc->seltime_b = (aic7xxx_seltime & 0x3) << 4;
	if (aic7xxx_pci_parity == 0)
@@ -1830,10 +1828,9 @@ ahc_done(struct ahc_softc *ahc, struct scb *scb)
		if (ahc_get_transaction_status(scb) == CAM_BDR_SENT
		 || ahc_get_transaction_status(scb) == CAM_REQ_ABORTED)
			ahc_set_transaction_status(scb, CAM_CMD_TIMEOUT);
		if ((ahc->platform_data->flags & AHC_UP_EH_SEMAPHORE) != 0) {
			ahc->platform_data->flags &= ~AHC_UP_EH_SEMAPHORE;
			up(&ahc->platform_data->eh_sem);
		}

		if (ahc->platform_data->eh_done)
			complete(ahc->platform_data->eh_done);
	}

	ahc_free_scb(ahc, scb);
@@ -2039,22 +2036,6 @@ ahc_linux_queue_cmd_complete(struct ahc_softc *ahc, struct scsi_cmnd *cmd)
	cmd->scsi_done(cmd);
}

static void
ahc_linux_sem_timeout(u_long arg)
{
	struct	ahc_softc *ahc;
	u_long	s;

	ahc = (struct ahc_softc *)arg;

	ahc_lock(ahc, &s);
	if ((ahc->platform_data->flags & AHC_UP_EH_SEMAPHORE) != 0) {
		ahc->platform_data->flags &= ~AHC_UP_EH_SEMAPHORE;
		up(&ahc->platform_data->eh_sem);
	}
	ahc_unlock(ahc, &s);
}

static void
ahc_linux_freeze_simq(struct ahc_softc *ahc)
{
@@ -2355,25 +2336,21 @@ ahc_linux_queue_recovery_cmd(struct scsi_cmnd *cmd, scb_flag flag)
	if (paused)
		ahc_unpause(ahc);
	if (wait) {
		struct timer_list timer;
		int ret;
		DECLARE_COMPLETION(done);

		ahc->platform_data->flags |= AHC_UP_EH_SEMAPHORE;
		ahc->platform_data->eh_done = &done;
		ahc_unlock(ahc, &flags);

		init_timer(&timer);
		timer.data = (u_long)ahc;
		timer.expires = jiffies + (5 * HZ);
		timer.function = ahc_linux_sem_timeout;
		add_timer(&timer);
		printf("Recovery code sleeping\n");
		down(&ahc->platform_data->eh_sem);
		printf("Recovery code awake\n");
        	ret = del_timer_sync(&timer);
		if (ret == 0) {
		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");
			retval = FAILED;
		}
		printf("Recovery code awake\n");
	} else
		ahc_unlock(ahc, &flags);
	return (retval);
+1 −4
Original line number Diff line number Diff line
@@ -369,15 +369,12 @@ struct ahc_platform_data {

	spinlock_t		 spin_lock;
	u_int			 qfrozen;
	struct semaphore	 eh_sem;
	struct completion	*eh_done;
	struct Scsi_Host        *host;		/* pointer to scsi host */
#define AHC_LINUX_NOIRQ	((uint32_t)~0)
	uint32_t		 irq;		/* IRQ for this adapter */
	uint32_t		 bios_address;
	uint32_t		 mem_busaddr;	/* Mem Base Addr */

#define	AHC_UP_EH_SEMAPHORE	 0x1
	uint32_t		 flags;
};

/************************** OS Utility Wrappers *******************************/