Commit 992f9884 authored by Martin K. Petersen's avatar Martin K. Petersen
Browse files

Merge patch series "NCR5380: Bug fixes and other improvements"

Finn Thain <fthain@linux-m68k.org> says:

This series begins with some work on the mac_scsi driver to improve
compatibility with SCSI2SD v5 devices. Better error handling is needed
there because the PDMA hardware does not tolerate the write latency
spikes which SD cards can produce.

A bug is fixed in the 5380 core driver so that scatter/gather can be
enabled in mac_scsi.

Several patches at the end of this series improve robustness and
correctness in the core driver.

This series has been tested on a variety of mac_scsi hosts. A variety
of SCSI targets was also tested, including Quantum HDD, Fujitsu HDD,
Iomega FDD, Ricoh CD-RW, Matsushita CD-ROM, SCSI2SD and BlueSCSI.

Link: https://lore.kernel.org/r/cover.1723001788.git.fthain@linux-m68k.org


Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parents f856e57d a8ebca90
Loading
Loading
Loading
Loading
+116 −117
Original line number Diff line number Diff line
@@ -157,7 +157,6 @@ static inline void initialize_SCp(struct scsi_cmnd *cmd)
	}

	ncmd->status = 0;
	ncmd->message = 0;
}

static inline void advance_sg_buffer(struct NCR5380_cmd *ncmd)
@@ -199,7 +198,6 @@ static inline void set_resid_from_SCp(struct scsi_cmnd *cmd)
 * Polls the chip in a reasonably efficient manner waiting for an
 * event to occur. After a short quick poll we begin to yield the CPU
 * (if possible). In irq contexts the time-out is arbitrarily limited.
 * Callers may hold locks as long as they are held in irq mode.
 *
 * Returns 0 if either or both event(s) occurred otherwise -ETIMEDOUT.
 */
@@ -1228,24 +1226,15 @@ static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
	return ret;
}

/*
 * Function : int NCR5380_transfer_pio (struct Scsi_Host *instance,
 * unsigned char *phase, int *count, unsigned char **data)
 *
 * Purpose : transfers data in given phase using polled I/O
 *
 * Inputs : instance - instance of driver, *phase - pointer to
 * what phase is expected, *count - pointer to number of
 * bytes to transfer, **data - pointer to data pointer,
 * can_sleep - 1 or 0 when sleeping is permitted or not, respectively.
 *
 * Returns : -1 when different phase is entered without transferring
 * maximum number of bytes, 0 if all bytes are transferred or exit
 * is in same phase.
 *
 * Also, *phase, *count, *data are modified in place.
/**
 * NCR5380_transfer_pio() - transfers data in given phase using polled I/O
 * @instance: instance of driver
 * @phase: pointer to what phase is expected
 * @count: pointer to number of bytes to transfer
 * @data: pointer to data pointer
 * @can_sleep: 1 or 0 when sleeping is permitted or not, respectively
 *
 * XXX Note : handling for bus free may be useful.
 * Returns: void. *phase, *count, *data are modified in place.
 */

/*
@@ -1254,7 +1243,7 @@ static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
 * counts, we will always do a pseudo DMA or DMA transfer.
 */

static int NCR5380_transfer_pio(struct Scsi_Host *instance,
static void NCR5380_transfer_pio(struct Scsi_Host *instance,
				 unsigned char *phase, int *count,
				 unsigned char **data, unsigned int can_sleep)
{
@@ -1277,8 +1266,8 @@ static int NCR5380_transfer_pio(struct Scsi_Host *instance,
		 * valid
		 */

		if (NCR5380_poll_politely(hostdata, STATUS_REG, SR_REQ, SR_REQ,
					  HZ * can_sleep) < 0)
		if (NCR5380_poll_politely(hostdata, STATUS_REG, SR_REQ | SR_BSY,
					  SR_REQ | SR_BSY, HZ * can_sleep) < 0)
			break;

		dsprintk(NDEBUG_HANDSHAKE, instance, "REQ asserted\n");
@@ -1330,15 +1319,17 @@ static int NCR5380_transfer_pio(struct Scsi_Host *instance,
		dsprintk(NDEBUG_HANDSHAKE, instance, "REQ negated, handshake complete\n");

		/*
 * We have several special cases to consider during REQ/ACK handshaking :
 * 1.  We were in MSGOUT phase, and we are on the last byte of the
 * message.  ATN must be dropped as ACK is dropped.
		 * We have several special cases to consider during REQ/ACK
		 * handshaking:
		 *
 * 2.  We are in a MSGIN phase, and we are on the last byte of the
		 * 1.  We were in MSGOUT phase, and we are on the last byte of
		 * the message. ATN must be dropped as ACK is dropped.
		 *
		 * 2.  We are in MSGIN phase, and we are on the last byte of the
		 * message. We must exit with ACK asserted, so that the calling
		 * code may raise ATN before dropping ACK to reject the message.
		 *
 * 3.  ACK and ATN are clear and the target may proceed as normal.
		 * 3.  ACK and ATN are clear & the target may proceed as normal.
		 */
		if (!(p == PHASE_MSGIN && c == 1)) {
			if (p == PHASE_MSGOUT && c > 1)
@@ -1361,11 +1352,6 @@ static int NCR5380_transfer_pio(struct Scsi_Host *instance,
		*phase = tmp & PHASE_MASK;
	else
		*phase = PHASE_UNKNOWN;

	if (!c || (*phase == p))
		return 0;
	else
		return -1;
}

/**
@@ -1485,6 +1471,7 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
				unsigned char **data)
{
	struct NCR5380_hostdata *hostdata = shost_priv(instance);
	struct NCR5380_cmd *ncmd = NCR5380_to_ncmd(hostdata->connected);
	int c = *count;
	unsigned char p = *phase;
	unsigned char *d = *data;
@@ -1496,7 +1483,7 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
		return -1;
	}

	NCR5380_to_ncmd(hostdata->connected)->phase = p;
	ncmd->phase = p;

	if (p & SR_IO) {
		if (hostdata->read_overruns)
@@ -1583,38 +1570,40 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
	 * conditions. For non-scatter-gather operations, we can wait until REQ
	 * and ACK both go false, or until a phase mismatch occurs. Gather-sends
	 * are nastier, since the device will be expecting more data than we
 * are prepared to send it, and REQ will remain asserted.  On a 53C8[01] we
 * could test Last Byte Sent to assure transfer (I imagine this is precisely
 * why this signal was added to the newer chips) but on the older 538[01]
 * this signal does not exist.  The workaround for this lack is a watchdog;
 * we bail out of the wait-loop after a modest amount of wait-time if
 * the usual exit conditions are not met.  Not a terribly clean or
 * correct solution :-%
 *
 * DMA receive is equally tricky due to a nasty characteristic of the NCR5380.
 * If the chip is in DMA receive mode, it will respond to a target's
 * REQ by latching the SCSI data into the INPUT DATA register and asserting
 * ACK, even if it has _already_ been notified by the DMA controller that
 * the current DMA transfer has completed!  If the NCR5380 is then taken
 * out of DMA mode, this already-acknowledged byte is lost. This is
 * not a problem for "one DMA transfer per READ command", because
 * the situation will never arise... either all of the data is DMA'ed
 * properly, or the target switches to MESSAGE IN phase to signal a
 * disconnection (either operation bringing the DMA to a clean halt).
 * However, in order to handle scatter-receive, we must work around the
 * problem.  The chosen fix is to DMA fewer bytes, then check for the
 * condition before taking the NCR5380 out of DMA mode.  One or two extra
 * bytes are transferred via PIO as necessary to fill out the original
 * request.
 */

	if (hostdata->flags & FLAG_DMA_FIXUP) {
		if (p & SR_IO) {
	 * are prepared to send it, and REQ will remain asserted. On a 53C8[01]
	 * we could test Last Byte Sent to assure transfer (I imagine this is
	 * precisely why this signal was added to the newer chips) but on the
	 * older 538[01] this signal does not exist. The workaround for this
	 * lack is a watchdog; we bail out of the wait-loop after a modest
	 * amount of wait-time if the usual exit conditions are not met.
	 * Not a terribly clean or correct solution :-%
	 *
	 * DMA receive is equally tricky due to a nasty characteristic of the
	 * NCR5380. If the chip is in DMA receive mode, it will respond to a
	 * target's REQ by latching the SCSI data into the INPUT DATA register
	 * and asserting ACK, even if it has _already_ been notified by the
	 * DMA controller that the current DMA transfer has completed! If the
	 * NCR5380 is then taken out of DMA mode, this already-acknowledged
	 * byte is lost.
	 *
	 * This is not a problem for "one DMA transfer per READ
	 * command", because the situation will never arise... either all of
	 * the data is DMA'ed properly, or the target switches to MESSAGE IN
	 * phase to signal a disconnection (either operation bringing the DMA
	 * to a clean halt). However, in order to handle scatter-receive, we
	 * must work around the problem. The chosen fix is to DMA fewer bytes,
	 * then check for the condition before taking the NCR5380 out of DMA
	 * mode. One or two extra bytes are transferred via PIO as necessary
	 * to fill out the original request.
	 */

	if ((hostdata->flags & FLAG_DMA_FIXUP) &&
	    (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
		/*
		 * The workaround was to transfer fewer bytes than we
			 * intended to with the pseudo-DMA read function, wait for
		 * intended to with the pseudo-DMA receive function, wait for
		 * the chip to latch the last byte, read it, and then disable
			 * pseudo-DMA mode.
		 * DMA mode.
		 *
		 * After REQ is asserted, the NCR5380 asserts DRQ and ACK.
		 * REQ is deasserted when ACK is asserted, and not reasserted
@@ -1623,30 +1612,29 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
		 * the DMA port or we take the NCR5380 out of DMA mode, we
		 * can guarantee that we won't handshake another extra
		 * byte.
			 */

			if (NCR5380_poll_politely(hostdata, BUS_AND_STATUS_REG,
			                          BASR_DRQ, BASR_DRQ, 0) < 0) {
		 *
		 * If sending, wait for the last byte to be sent. If REQ is
		 * being asserted for the byte we're interested, we'll ACK it
		 * and it will go false.
		 */
		if (!NCR5380_poll_politely(hostdata, BUS_AND_STATUS_REG,
					   BASR_DRQ, BASR_DRQ, 0)) {
			if ((p & SR_IO) &&
			    (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
				if (!NCR5380_poll_politely(hostdata, STATUS_REG,
							   SR_REQ, 0, 0)) {
					d[c] = NCR5380_read(INPUT_DATA_REG);
					--ncmd->this_residual;
				} else {
					result = -1;
				shost_printk(KERN_ERR, instance, "PDMA read: DRQ timeout\n");
					scmd_printk(KERN_ERR, hostdata->connected,
						    "PDMA fixup: !REQ timeout\n");
				}
			if (NCR5380_poll_politely(hostdata, STATUS_REG,
			                          SR_REQ, 0, 0) < 0) {
				result = -1;
				shost_printk(KERN_ERR, instance, "PDMA read: !REQ timeout\n");
			}
			d[*count - 1] = NCR5380_read(INPUT_DATA_REG);
		} else {
			/*
			 * Wait for the last byte to be sent.  If REQ is being asserted for
			 * the byte we're interested, we'll ACK it and it will go false.
			 */
			if (NCR5380_poll_politely2(hostdata,
			     BUS_AND_STATUS_REG, BASR_DRQ, BASR_DRQ,
			     BUS_AND_STATUS_REG, BASR_PHASE_MATCH, 0, 0) < 0) {
		} else if (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH) {
			result = -1;
				shost_printk(KERN_ERR, instance, "PDMA write: DRQ and phase timeout\n");
			}
			scmd_printk(KERN_ERR, hostdata->connected,
				    "PDMA fixup: DRQ timeout\n");
		}
	}

@@ -1666,9 +1654,6 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
 * Side effects : SCSI things happen, the disconnected queue will be
 * modified if a command disconnects, *instance->connected will
 * change.
 *
 * XXX Note : we need to watch for bus free or a reset condition here
 * to recover from an unexpected bus free condition.
 */

static void NCR5380_information_transfer(struct Scsi_Host *instance)
@@ -1807,9 +1792,11 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
				return;
			case PHASE_MSGIN:
				len = 1;
				tmp = 0xff;
				data = &tmp;
				NCR5380_transfer_pio(instance, &phase, &len, &data, 0);
				ncmd->message = tmp;
				if (tmp == 0xff)
					break;

				switch (tmp) {
				case ABORT:
@@ -1996,6 +1983,7 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
				break;
			case PHASE_STATIN:
				len = 1;
				tmp = ncmd->status;
				data = &tmp;
				NCR5380_transfer_pio(instance, &phase, &len, &data, 0);
				ncmd->status = tmp;
@@ -2005,9 +1993,20 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
				NCR5380_dprint(NDEBUG_ANY, instance);
			} /* switch(phase) */
		} else {
			int err;

			spin_unlock_irq(&hostdata->lock);
			NCR5380_poll_politely(hostdata, STATUS_REG, SR_REQ, SR_REQ, HZ);
			err = NCR5380_poll_politely(hostdata, STATUS_REG,
						    SR_REQ, SR_REQ, HZ);
			spin_lock_irq(&hostdata->lock);

			if (err < 0 && hostdata->connected &&
			    !(NCR5380_read(STATUS_REG) & SR_BSY)) {
				scmd_printk(KERN_ERR, hostdata->connected,
					    "BSY signal lost\n");
				do_reset(instance);
				bus_reset_cleanup(instance);
			}
		}
	}
}
+10 −10
Original line number Diff line number Diff line
@@ -231,7 +231,6 @@ struct NCR5380_cmd {
	int this_residual;
	struct scatterlist *buffer;
	int status;
	int message;
	int phase;
	struct list_head list;
};
@@ -286,8 +285,9 @@ static const char *NCR5380_info(struct Scsi_Host *instance);
static void NCR5380_reselect(struct Scsi_Host *instance);
static bool NCR5380_select(struct Scsi_Host *, struct scsi_cmnd *);
static int NCR5380_transfer_dma(struct Scsi_Host *instance, unsigned char *phase, int *count, unsigned char **data);
static int NCR5380_transfer_pio(struct Scsi_Host *instance, unsigned char *phase, int *count, unsigned char **data,
				unsigned int can_sleep);
static void NCR5380_transfer_pio(struct Scsi_Host *instance,
				 unsigned char *phase, int *count,
				 unsigned char **data, unsigned int can_sleep);
static int NCR5380_poll_politely2(struct NCR5380_hostdata *,
                                  unsigned int, u8, u8,
                                  unsigned int, u8, u8, unsigned long);
+88 −82
Original line number Diff line number Diff line
@@ -102,11 +102,15 @@ __setup("mac5380=", mac_scsi_setup);
 * Linux SCSI drivers lack knowledge of the timing behaviour of SCSI targets
 * so bus errors are unavoidable.
 *
 * If a MOVE.B instruction faults, we assume that zero bytes were transferred
 * and simply retry. That assumption probably depends on target behaviour but
 * seems to hold up okay. The NOP provides synchronization: without it the
 * fault can sometimes occur after the program counter has moved past the
 * offending instruction. Post-increment addressing can't be used.
 * If a MOVE.B instruction faults during a receive operation, we assume the
 * target sent nothing and try again. That assumption probably depends on
 * target firmware but it seems to hold up okay. If a fault happens during a
 * send operation, the target may or may not have seen /ACK and got the byte.
 * It's uncertain so the whole SCSI command gets retried.
 *
 * The NOP is needed for synchronization because the fault address in the
 * exception stack frame may or may not be the instruction that actually
 * caused the bus error. Post-increment addressing can't be used.
 */

#define MOVE_BYTE(operands) \
@@ -208,8 +212,6 @@ __setup("mac5380=", mac_scsi_setup);
		".previous                     \n" \
		: "+a" (addr), "+r" (n), "+r" (result) : "a" (io))

#define MAC_PDMA_DELAY		32

static inline int mac_pdma_recv(void __iomem *io, unsigned char *start, int n)
{
	unsigned char *addr = start;
@@ -245,22 +247,21 @@ static inline int mac_pdma_send(unsigned char *start, void __iomem *io, int n)
	if (n >= 1) {
		MOVE_BYTE("%0@,%3@");
		if (result)
			goto out;
			return -1;
	}
	if (n >= 1 && ((unsigned long)addr & 1)) {
		MOVE_BYTE("%0@,%3@");
		if (result)
			goto out;
			return -2;
	}
	while (n >= 32)
		MOVE_16_WORDS("%0@+,%3@");
	while (n >= 2)
		MOVE_WORD("%0@+,%3@");
	if (result)
		return start - addr; /* Negated to indicate uncertain length */
		return start - addr - 1; /* Negated to indicate uncertain length */
	if (n == 1)
		MOVE_BYTE("%0@,%3@");
out:
	return addr - start;
}

@@ -274,25 +275,56 @@ static inline void write_ctrl_reg(struct NCR5380_hostdata *hostdata, u32 value)
	out_be32(hostdata->io + (CTRL_REG << 4), value);
}

static inline int macscsi_wait_for_drq(struct NCR5380_hostdata *hostdata)
{
	unsigned int n = 1; /* effectively multiplies NCR5380_REG_POLL_TIME */
	unsigned char basr;

again:
	basr = NCR5380_read(BUS_AND_STATUS_REG);

	if (!(basr & BASR_PHASE_MATCH))
		return 1;

	if (basr & BASR_IRQ)
		return -1;

	if (basr & BASR_DRQ)
		return 0;

	if (n-- == 0) {
		NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
		dsprintk(NDEBUG_PSEUDO_DMA, hostdata->host,
			 "%s: DRQ timeout\n", __func__);
		return -1;
	}

	NCR5380_poll_politely2(hostdata,
			       BUS_AND_STATUS_REG, BASR_DRQ, BASR_DRQ,
			       BUS_AND_STATUS_REG, BASR_PHASE_MATCH, 0, 0);
	goto again;
}

static inline int macscsi_pread(struct NCR5380_hostdata *hostdata,
                                unsigned char *dst, int len)
{
	u8 __iomem *s = hostdata->pdma_io + (INPUT_DATA_REG << 4);
	unsigned char *d = dst;
	int result = 0;

	hostdata->pdma_residual = len;

	while (!NCR5380_poll_politely(hostdata, BUS_AND_STATUS_REG,
	                              BASR_DRQ | BASR_PHASE_MATCH,
	                              BASR_DRQ | BASR_PHASE_MATCH, 0)) {
		int bytes;
	while (macscsi_wait_for_drq(hostdata) == 0) {
		int bytes, chunk_bytes;

		if (macintosh_config->ident == MAC_MODEL_IIFX)
			write_ctrl_reg(hostdata, CTRL_HANDSHAKE_MODE |
			                         CTRL_INTERRUPTS_ENABLE);

		bytes = mac_pdma_recv(s, d, min(hostdata->pdma_residual, 512));
		chunk_bytes = min(hostdata->pdma_residual, 512);
		bytes = mac_pdma_recv(s, d, chunk_bytes);

		if (macintosh_config->ident == MAC_MODEL_IIFX)
			write_ctrl_reg(hostdata, CTRL_INTERRUPTS_ENABLE);

		if (bytes > 0) {
			d += bytes;
@@ -300,37 +332,25 @@ static inline int macscsi_pread(struct NCR5380_hostdata *hostdata,
		}

		if (hostdata->pdma_residual == 0)
			goto out;
			break;

		if (NCR5380_poll_politely2(hostdata, STATUS_REG, SR_REQ, SR_REQ,
		                           BUS_AND_STATUS_REG, BASR_ACK,
		                           BASR_ACK, 0) < 0)
			scmd_printk(KERN_DEBUG, hostdata->connected,
			            "%s: !REQ and !ACK\n", __func__);
		if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH))
			goto out;
		if (bytes > 0)
			continue;

		if (bytes == 0)
			udelay(MAC_PDMA_DELAY);
		NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
		dsprintk(NDEBUG_PSEUDO_DMA, hostdata->host,
			 "%s: bus error [%d/%d] (%d/%d)\n",
			 __func__, d - dst, len, bytes, chunk_bytes);

		if (bytes >= 0)
		if (bytes == 0)
			continue;

		dsprintk(NDEBUG_PSEUDO_DMA, hostdata->host,
		         "%s: bus error (%d/%d)\n", __func__, d - dst, len);
		NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
		result = -1;
		goto out;
		if (macscsi_wait_for_drq(hostdata) <= 0)
			set_host_byte(hostdata->connected, DID_ERROR);
		break;
	}

	scmd_printk(KERN_ERR, hostdata->connected,
	            "%s: phase mismatch or !DRQ\n", __func__);
	NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
	result = -1;
out:
	if (macintosh_config->ident == MAC_MODEL_IIFX)
		write_ctrl_reg(hostdata, CTRL_INTERRUPTS_ENABLE);
	return result;
	return 0;
}

static inline int macscsi_pwrite(struct NCR5380_hostdata *hostdata,
@@ -338,67 +358,47 @@ static inline int macscsi_pwrite(struct NCR5380_hostdata *hostdata,
{
	unsigned char *s = src;
	u8 __iomem *d = hostdata->pdma_io + (OUTPUT_DATA_REG << 4);
	int result = 0;

	hostdata->pdma_residual = len;

	while (!NCR5380_poll_politely(hostdata, BUS_AND_STATUS_REG,
	                              BASR_DRQ | BASR_PHASE_MATCH,
	                              BASR_DRQ | BASR_PHASE_MATCH, 0)) {
		int bytes;
	while (macscsi_wait_for_drq(hostdata) == 0) {
		int bytes, chunk_bytes;

		if (macintosh_config->ident == MAC_MODEL_IIFX)
			write_ctrl_reg(hostdata, CTRL_HANDSHAKE_MODE |
			                         CTRL_INTERRUPTS_ENABLE);

		bytes = mac_pdma_send(s, d, min(hostdata->pdma_residual, 512));
		chunk_bytes = min(hostdata->pdma_residual, 512);
		bytes = mac_pdma_send(s, d, chunk_bytes);

		if (macintosh_config->ident == MAC_MODEL_IIFX)
			write_ctrl_reg(hostdata, CTRL_INTERRUPTS_ENABLE);

		if (bytes > 0) {
			s += bytes;
			hostdata->pdma_residual -= bytes;
		}

		if (hostdata->pdma_residual == 0) {
			if (NCR5380_poll_politely(hostdata, TARGET_COMMAND_REG,
			                          TCR_LAST_BYTE_SENT,
			                          TCR_LAST_BYTE_SENT,
			                          0) < 0) {
				scmd_printk(KERN_ERR, hostdata->connected,
				            "%s: Last Byte Sent timeout\n", __func__);
				result = -1;
			}
			goto out;
		}
		if (hostdata->pdma_residual == 0)
			break;

		if (NCR5380_poll_politely2(hostdata, STATUS_REG, SR_REQ, SR_REQ,
		                           BUS_AND_STATUS_REG, BASR_ACK,
		                           BASR_ACK, 0) < 0)
			scmd_printk(KERN_DEBUG, hostdata->connected,
			            "%s: !REQ and !ACK\n", __func__);
		if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH))
			goto out;
		if (bytes > 0)
			continue;

		if (bytes == 0)
			udelay(MAC_PDMA_DELAY);
		NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
		dsprintk(NDEBUG_PSEUDO_DMA, hostdata->host,
			 "%s: bus error [%d/%d] (%d/%d)\n",
			 __func__, s - src, len, bytes, chunk_bytes);

		if (bytes >= 0)
		if (bytes == 0)
			continue;

		dsprintk(NDEBUG_PSEUDO_DMA, hostdata->host,
		         "%s: bus error (%d/%d)\n", __func__, s - src, len);
		NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
		result = -1;
		goto out;
		if (macscsi_wait_for_drq(hostdata) <= 0)
			set_host_byte(hostdata->connected, DID_ERROR);
		break;
	}

	scmd_printk(KERN_ERR, hostdata->connected,
	            "%s: phase mismatch or !DRQ\n", __func__);
	NCR5380_dprint(NDEBUG_PSEUDO_DMA, hostdata->host);
	result = -1;
out:
	if (macintosh_config->ident == MAC_MODEL_IIFX)
		write_ctrl_reg(hostdata, CTRL_INTERRUPTS_ENABLE);
	return result;
	return 0;
}

static int macscsi_dma_xfer_len(struct NCR5380_hostdata *hostdata,
@@ -432,7 +432,7 @@ static struct scsi_host_template mac_scsi_template = {
	.eh_host_reset_handler	= macscsi_host_reset,
	.can_queue		= 16,
	.this_id		= 7,
	.sg_tablesize		= 1,
	.sg_tablesize		= SG_ALL,
	.cmd_per_lun		= 2,
	.dma_boundary		= PAGE_SIZE - 1,
	.cmd_size		= sizeof(struct NCR5380_cmd),
@@ -470,6 +470,9 @@ static int __init mac_scsi_probe(struct platform_device *pdev)
	if (setup_hostid >= 0)
		mac_scsi_template.this_id = setup_hostid & 7;

	if (macintosh_config->ident == MAC_MODEL_IIFX)
		mac_scsi_template.sg_tablesize = 1;

	instance = scsi_host_alloc(&mac_scsi_template,
	                           sizeof(struct NCR5380_hostdata));
	if (!instance)
@@ -491,6 +494,9 @@ static int __init mac_scsi_probe(struct platform_device *pdev)

	host_flags |= setup_toshiba_delay > 0 ? FLAG_TOSHIBA_DELAY : 0;

	if (instance->sg_tablesize > 1)
		host_flags |= FLAG_DMA_FIXUP;

	error = NCR5380_init(instance, host_flags | FLAG_LATE_DMA_SETUP);
	if (error)
		goto fail_init;
+1 −1

File changed.

Contains only whitespace changes.