Skip to contentSkip to conversation

Fixes, cleanups and modernization for NCR5380 drivers

PATCH Superseded Finn Thain 5 participants 100 messages Oct 27, 2014 – Nov 11, 2014 1 message not in the archive

Subsystems (5)

v2 of 3 Superseded Latest is v3 →

lore
Share & tools
lore

Finn Thain

author
#0 lore raw

v2 cover Fixes, cleanups and modernization for NCR5380 drivers

This patch series has fixes for bugs and compiler warnings as well as code cleanup and modernization. It covers all ten NCR5380 drivers and the three core NCR5380 drivers so it's fairly large.

These patches remove a lot of duplicated code and C pre-processor abuse. There are also patches for scsi_add_host() conversion for atari_scsi, mac_scsi and sun3_scsi.

Some steps are taken toward re-unification of the NCR5380 core driver forks by reducing divergence between them. Also, the atari_NCR5380.c core driver is generalized so it can be used by sun3_scsi.c (and others).

I have compile-tested all of the NCR5380 drivers (x86, ARM and m68k) and executed mac_scsi and dmx3191d on suitable hardware. I found no regressions but the core NCR5380 drivers have bugs unrelated to these patches.

Testing mac_scsi and dmx3191d provides only limited code coverage for these patches. Some testing on Sun 3, Atari ST and/or Atari TT would be nice (I don't have the hardware).

There are old bugs relating to exception handling and autosense in the core NCR5380 drivers that can make testing difficult. I'm working on a series of patches to address these bugs. Those patches are not yet ready for submission but they were helpful for the testing I did and may be helpful to other testers. Let me know if so.

Changes since v1:
- Re-based to v3.17.
- Addressed issues raised in code review (see relevant patches for details).
- Added patches 30 to 36, to remove sun3_NCR5380.c entirely and remove more static variables from atari_NCR5380.c.

This patch set stops short of parameterizing the drivers with platform_data and/or ops struct. IMHO, it would be premature to do such refactoring before drivers have been purged of static variables and certain #ifdefs. After that is done, entire modules could be replaced with platform devices.

Several patches in this set address issues with the tagged command queueing code (see patches 7, 33 and 34). I've since learned from recent discussions on the linux-scsi list that use of the tag member in struct scsi_cmnd is deprecated. If removal of the tag member is imminent then it may be better to remove TCQ support from all of the NCR5380 drivers instead of this cleanup. Or it could be done separately.

Removal of TCQ code might make re-unification easier, by bringing atari_NCR5380.c closer to NCR5380.c and eliminating some #ifdefs. Changes to the TCQ code would affect atari_scsi, being the only driver to #define SUPPORT_TAGS.

---
 MAINTAINERS                         |    1 
 arch/m68k/atari/config.c            |   27 
 arch/m68k/atari/stdma.c             |   61 
 arch/m68k/include/asm/atari_stdma.h |    4 
 arch/m68k/include/asm/macintosh.h   |    4 
 arch/m68k/mac/config.c              |  146 +
 arch/m68k/sun3/config.c             |   60 
 drivers/scsi/Kconfig                |    2 
 drivers/scsi/NCR5380.c              |  295 +--
 drivers/scsi/NCR5380.h              |   78 
 drivers/scsi/arm/cumana_1.c         |   18 
 drivers/scsi/arm/oak.c              |   23 
 drivers/scsi/atari_NCR5380.c        |  981 +++++-------
 drivers/scsi/atari_scsi.c           |  676 +++-----
 drivers/scsi/atari_scsi.h           |   60 
 drivers/scsi/dmx3191d.c             |   31 
 drivers/scsi/dtc.c                  |   85 -
 drivers/scsi/dtc.h                  |   26 
 drivers/scsi/g_NCR5380.c            |  224 --
 drivers/scsi/g_NCR5380.h            |   26 
 drivers/scsi/mac_scsi.c             |  542 ++----
 drivers/scsi/mac_scsi.h             |   74 
 drivers/scsi/pas16.c                |  106 -
 drivers/scsi/pas16.h                |   21 
 drivers/scsi/sun3_NCR5380.c         | 2933 ------------------------------------
 drivers/scsi/sun3_scsi.c            |  512 ++----
 drivers/scsi/sun3_scsi.h            |   84 -
 drivers/scsi/t128.c                 |   83 -
 drivers/scsi/t128.h                 |   23 
 29 files changed, 1745 insertions(+), 5461 deletions(-)
author
#1 lore raw

PATCH v2 1/36 ncr5380: Use printk() not pr_debug()

Having defined NDEBUG, and having set the console log level, I'd like to see some output. Don't use pr_debug(), it's annoying to have to define DEBUG as well.

---

Use of pr_debug() here was a bad idea of mine. Joe was right when he questioned it.

---
 drivers/scsi/NCR5380.h |    3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/scsi/NCR5380.h +2 -1
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -296,7 +296,8 @@ struct NCR5380_hostdata {
 #endif
 
 #define dprintk(flg, fmt, ...) \
-	do { if ((NDEBUG) & (flg)) pr_debug(fmt, ## __VA_ARGS__); } while (0)
+	do { if ((NDEBUG) & (flg)) \
+		printk(KERN_DEBUG fmt, ## __VA_ARGS__); } while (0)
 
 #if NDEBUG
 #define NCR5380_dprint(flg, arg) \
author
#2 lore raw

PATCH v2 2/36 ncr5380: Remove unused hostdata fields

In reply to Finn Thain

Remove unused fields from hostdata structs declared with the NCR5380_implementation_fields macro.

---
 drivers/scsi/dmx3191d.c  |    4 ++--
 drivers/scsi/mac_scsi.c  |   33 ---------------------------------
 drivers/scsi/mac_scsi.h  |    3 +--
 drivers/scsi/sun3_scsi.c |    2 --
 drivers/scsi/sun3_scsi.h |    3 +--
 5 files changed, 4 insertions(+), 41 deletions(-)
drivers/scsi/dmx3191d.c +2 -2
Index: linux/drivers/scsi/dmx3191d.c
===================================================================
@@ -38,8 +38,8 @@
 #define NCR5380_read(reg)		inb(port + reg)
 #define NCR5380_write(reg, value)	outb(value, port + reg)
 
-#define NCR5380_implementation_fields	unsigned int port
-#define NCR5380_local_declare()		NCR5380_implementation_fields
+#define NCR5380_implementation_fields	/* none */
+#define NCR5380_local_declare()		unsigned int port
 #define NCR5380_setup(instance)		port = instance->io_port
 
 /*
drivers/scsi/mac_scsi.c +0 -33
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -93,35 +93,6 @@ static volatile unsigned char *mac_scsi_
  * NCR 5380 register access functions
  */
 
-#if 0
-/* Debug versions */
-#define CTRL(p,v) (*ctrl = (v))
-
-static char macscsi_read(struct Scsi_Host *instance, int reg)
-{
-  int iobase = instance->io_port;
-  int i;
-  int *ctrl = &((struct NCR5380_hostdata *)instance->hostdata)->ctrl;
-
-  CTRL(iobase, 0);
-  i = in_8(iobase + (reg<<4));
-  CTRL(iobase, 0x40);
-
-  return i;
-}
-
-static void macscsi_write(struct Scsi_Host *instance, int reg, int value)
-{
-  int iobase = instance->io_port;
-  int *ctrl = &((struct NCR5380_hostdata *)instance->hostdata)->ctrl;
-
-  CTRL(iobase, 0);
-  out_8(iobase + (reg<<4), value);
-  CTRL(iobase, 0x40);
-}
-#else
-
-/* Fast versions */
 static __inline__ char macscsi_read(struct Scsi_Host *instance, int reg)
 {
   return in_8(instance->io_port + (reg<<4));
@@ -131,8 +102,6 @@ static __inline__ void macscsi_write(str
 {
   out_8(instance->io_port + (reg<<4), value);
 }
-#endif
-
 
 /*
  * Function : mac_scsi_setup(char *str)
@@ -279,8 +248,6 @@ int __init macscsi_detect(struct scsi_ho
 
     instance->n_io_port = 255;
 
-    ((struct NCR5380_hostdata *)instance->hostdata)->ctrl = 0;
-
     if (instance->irq != SCSI_IRQ_NONE)
 	if (request_irq(instance->irq, NCR5380_intr, 0, "ncr5380", instance)) {
 	    printk(KERN_WARNING "scsi%d: IRQ%d not free, interrupts disabled\n",
drivers/scsi/mac_scsi.h +1 -2
Index: linux/drivers/scsi/mac_scsi.h
===================================================================
@@ -47,8 +47,7 @@
 
 #include <scsi/scsicam.h>
 
-#define NCR5380_implementation_fields \
-    int port, ctrl
+#define NCR5380_implementation_fields /* none */
 
 #define NCR5380_local_declare() \
         struct Scsi_Host *_instance
drivers/scsi/sun3_scsi.c +0 -2
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -313,8 +313,6 @@ static int __init sun3scsi_detect(struct
 
 	instance->n_io_port = 32;
 
-        ((struct NCR5380_hostdata *)instance->hostdata)->ctrl = 0;
-
 	if (request_irq(instance->irq, scsi_sun3_intr,
 			     0, "Sun3SCSI-5380", instance)) {
 #ifndef REAL_DMA
drivers/scsi/sun3_scsi.h +1 -2
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -78,8 +78,7 @@ static int sun3scsi_release (struct Scsi
 #define SUN3_SCSI_NAME "Sun3 NCR5380 SCSI"
 #endif
 
-#define NCR5380_implementation_fields \
-    int port, ctrl
+#define NCR5380_implementation_fields /* none */
 
 #define NCR5380_local_declare() \
         struct Scsi_Host *_instance
author
#3 lore raw

PATCH v2 3/36 ncr5380: Fix compiler warnings and __setup options

In reply to Finn Thain

Some __setup() options mentioned in Documentation/scsi don't work because a few lines of code went missing sometime since Linux 2.4. Fix the options and thus fix some compiler warnings for both the non-modular case,

CC drivers/scsi/dtc.o
drivers/scsi/dtc.c:176:20: warning: 'dtc_setup' defined but not used [-Wunused-function]

and the modular case,

CC [M] drivers/scsi/pas16.o
drivers/scsi/pas16.c:335:20: warning: 'pas16_setup' defined but not used [-Wunused-function]

    CC [M]  drivers/scsi/t128.o

drivers/scsi/t128.c:147:20: warning: 't128_setup' defined but not used [-Wunused-function]

---
 drivers/scsi/dtc.c   |    8 +++++++-
 drivers/scsi/pas16.c |   10 +++++++++-
 drivers/scsi/t128.c  |   11 ++++++++++-
 3 files changed, 26 insertions(+), 3 deletions(-)
drivers/scsi/dtc.c +7 -1
Index: linux/drivers/scsi/dtc.c
===================================================================
@@ -173,10 +173,13 @@ static const struct signature {
  *
  */
 
-static void __init dtc_setup(char *str, int *ints)
+static int __init dtc_setup(char *str)
 {
 	static int commandline_current = 0;
 	int i;
+	int ints[10];
+
+	get_options(str, ARRAY_SIZE(ints), ints);
 	if (ints[0] != 2)
 		printk("dtc_setup: usage dtc=address,irq\n");
 	else if (commandline_current < NO_OVERRIDES) {
@@ -189,7 +192,10 @@ static void __init dtc_setup(char *str,
 			}
 		++commandline_current;
 	}
+	return 1;
 }
+
+__setup("dtc=", dtc_setup);
 #endif
 
 /* 
drivers/scsi/pas16.c +9 -1
Index: linux/drivers/scsi/pas16.c
===================================================================
@@ -337,6 +337,7 @@ static int __init
 }
 
 
+#ifndef MODULE
 /*
  * Function : pas16_setup(char *str, int *ints)
  *
@@ -347,10 +348,13 @@ static int __init
  *
  */
 
-void __init pas16_setup(char *str, int *ints)
+static int __init pas16_setup(char *str)
 {
     static int commandline_current = 0;
     int i;
+    int ints[10];
+
+    get_options(str, ARRAY_SIZE(ints), ints);
     if (ints[0] != 2) 
 	printk("pas16_setup : usage pas16=io_port,irq\n");
     else 
@@ -364,8 +368,12 @@ void __init pas16_setup(char *str, int *
 		}
 	    ++commandline_current;
 	}
+    return 1;
 }
 
+__setup("pas16=", pas16_setup);
+#endif
+
 /* 
  * Function : int pas16_detect(struct scsi_host_template * tpnt)
  *
drivers/scsi/t128.c +10 -1
Index: linux/drivers/scsi/t128.c
===================================================================
@@ -148,6 +148,7 @@ static struct signature {
 
 #define NO_SIGNATURES ARRAY_SIZE(signatures)
 
+#ifndef MODULE
 /*
  * Function : t128_setup(char *str, int *ints)
  *
@@ -158,9 +159,13 @@ static struct signature {
  *
  */
 
-void __init t128_setup(char *str, int *ints){
+static int __init t128_setup(char *str)
+{
     static int commandline_current = 0;
     int i;
+    int ints[10];
+
+    get_options(str, ARRAY_SIZE(ints), ints);
     if (ints[0] != 2) 
 	printk("t128_setup : usage t128=address,irq\n");
     else 
@@ -174,8 +179,12 @@ void __init t128_setup(char *str, int *i
 		}
 	    ++commandline_current;
 	}
+    return 1;
 }
 
+__setup("t128=", t128_setup);
+#endif
+
 /* 
  * Function : int t128_detect(struct scsi_host_template * tpnt)
  *
author
#5 lore raw

PATCH v2 5/36 ncr5380: Remove useless prototypes

In reply to Finn Thain

Add missing static qualifiers and remove the now pointless prototypes. The NCR5380_* prototypes are all declared in NCR5380.h and renamed using macros. Further declarations are redundant (some are completely unused). Remove them.

---
 drivers/scsi/atari_scsi.c |    5 -----
 drivers/scsi/dtc.h        |    7 -------
 drivers/scsi/g_NCR5380.c  |    6 +++---
 drivers/scsi/g_NCR5380.h  |    6 ------
 drivers/scsi/mac_scsi.c   |    2 --
 drivers/scsi/pas16.c      |    6 +++---
 drivers/scsi/pas16.h      |    6 ------
 drivers/scsi/sun3_scsi.c  |    4 +---
 drivers/scsi/sun3_scsi.h  |    7 -------
 drivers/scsi/t128.c       |    7 ++++---
 drivers/scsi/t128.h       |    6 ------
 11 files changed, 11 insertions(+), 51 deletions(-)
drivers/scsi/g_NCR5380.c +3 -3
Index: linux/drivers/scsi/g_NCR5380.c
===================================================================
@@ -272,7 +272,7 @@ static int __init do_DTC3181E_setup(char
  *	Locks: none
  */
 
-int __init generic_NCR5380_detect(struct scsi_host_template * tpnt)
+static int __init generic_NCR5380_detect(struct scsi_host_template *tpnt)
 {
 	static int current_override = 0;
 	int count;
@@ -484,7 +484,7 @@ int __init generic_NCR5380_detect(struct
  *	Report driver information for the NCR5380
  */
  	
-const char *generic_NCR5380_info(struct Scsi_Host *host)
+static const char *generic_NCR5380_info(struct Scsi_Host *host)
 {
 	static const char string[] = "Generic NCR5380/53C400 Driver";
 	return string;
@@ -499,7 +499,7 @@ const char *generic_NCR5380_info(struct
  *	Locks: none
  */
  
-int generic_NCR5380_release_resources(struct Scsi_Host *instance)
+static int generic_NCR5380_release_resources(struct Scsi_Host *instance)
 {
 	NCR5380_local_declare();
 	NCR5380_setup(instance);
drivers/scsi/pas16.c +3 -3
Index: linux/drivers/scsi/pas16.c
===================================================================
@@ -382,7 +382,7 @@ __setup("pas16=", pas16_setup);
  *
  */
 
-int __init pas16_detect(struct scsi_host_template * tpnt)
+static int __init pas16_detect(struct scsi_host_template *tpnt)
 {
     static int current_override = 0;
     static unsigned short current_base = 0;
@@ -512,8 +512,8 @@ int __init pas16_detect(struct scsi_host
  * and matching the H_C_S coordinates to what DOS uses.
  */
 
-int pas16_biosparam(struct scsi_device *sdev, struct block_device *dev,
-		sector_t capacity, int * ip)
+static int pas16_biosparam(struct scsi_device *sdev, struct block_device *dev,
+                           sector_t capacity, int *ip)
 {
   int size = capacity;
   ip[0] = 64;
drivers/scsi/sun3_scsi.c +1 -3
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -86,8 +86,6 @@ extern int sun3_map_test(unsigned long,
 
 
 static irqreturn_t scsi_sun3_intr(int irq, void *dummy);
-static inline unsigned char sun3scsi_read(int reg);
-static inline void sun3scsi_write(int reg, int value);
 
 static int setup_can_queue = -1;
 module_param(setup_can_queue, int, 0);
@@ -348,7 +346,7 @@ static int __init sun3scsi_detect(struct
 	return 1;
 }
 
-int sun3scsi_release (struct Scsi_Host *shpnt)
+static int sun3scsi_release(struct Scsi_Host *shpnt)
 {
 	if (shpnt->irq != SCSI_IRQ_NONE)
 		free_irq(shpnt->irq, shpnt);
drivers/scsi/t128.c +4 -3
Index: linux/drivers/scsi/t128.c
===================================================================
@@ -193,7 +193,8 @@ __setup("t128=", t128_setup);
  *
  */
 
-int __init t128_detect(struct scsi_host_template * tpnt){
+static int __init t128_detect(struct scsi_host_template *tpnt)
+{
     static int current_override = 0, current_base = 0;
     struct Scsi_Host *instance;
     unsigned long base;
@@ -325,8 +326,8 @@ static int t128_release(struct Scsi_Host
  * and matching the H_C_S coordinates to what DOS uses.
  */
 
-int t128_biosparam(struct scsi_device *sdev, struct block_device *bdev,
-		sector_t capacity, int * ip)
+static int t128_biosparam(struct scsi_device *sdev, struct block_device *bdev,
+                          sector_t capacity, int *ip)
 {
   ip[0] = 64;
   ip[1] = 32;
drivers/scsi/dtc.h +0 -7
Index: linux/drivers/scsi/dtc.h
===================================================================
@@ -32,13 +32,6 @@
 #define DTCDEBUG_INIT	0x1
 #define DTCDEBUG_TRANSFER 0x2
 
-static int dtc_abort(Scsi_Cmnd *);
-static int dtc_biosparam(struct scsi_device *, struct block_device *,
-		         sector_t, int*);
-static int dtc_detect(struct scsi_host_template *);
-static int dtc_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int dtc_bus_reset(Scsi_Cmnd *);
-
 #ifndef CMD_PER_LUN
 #define CMD_PER_LUN 2
 #endif
drivers/scsi/g_NCR5380.h +0 -6
Index: linux/drivers/scsi/g_NCR5380.h
===================================================================
@@ -39,12 +39,6 @@
 #endif
 
 #ifndef ASM
-static int generic_NCR5380_abort(Scsi_Cmnd *);
-static int generic_NCR5380_detect(struct scsi_host_template *);
-static int generic_NCR5380_release_resources(struct Scsi_Host *);
-static int generic_NCR5380_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int generic_NCR5380_bus_reset(Scsi_Cmnd *);
-static const char* generic_NCR5380_info(struct Scsi_Host *);
 
 #ifndef CMD_PER_LUN
 #define CMD_PER_LUN 2
drivers/scsi/mac_scsi.c +0 -2
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -56,8 +56,6 @@
 
 #define RESET_BOOT
 
-extern void via_scsi_clear(void);
-
 #ifdef RESET_BOOT
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
drivers/scsi/pas16.h +0 -6
Index: linux/drivers/scsi/pas16.h
===================================================================
@@ -114,12 +114,6 @@
 
 
 #ifndef ASM
-static int pas16_abort(Scsi_Cmnd *);
-static int pas16_biosparam(struct scsi_device *, struct block_device *,
-			   sector_t, int*);
-static int pas16_detect(struct scsi_host_template *);
-static int pas16_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int pas16_bus_reset(Scsi_Cmnd *);
 
 #ifndef CMD_PER_LUN
 #define CMD_PER_LUN 2
drivers/scsi/sun3_scsi.h +0 -7
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -43,13 +43,6 @@
 
 #define IOBASE_SUN3_VMESCSI 0xff200000
 
-static int sun3scsi_abort(struct scsi_cmnd *);
-static int sun3scsi_detect (struct scsi_host_template *);
-static const char *sun3scsi_info (struct Scsi_Host *);
-static int sun3scsi_bus_reset(struct scsi_cmnd *);
-static int sun3scsi_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int sun3scsi_release (struct Scsi_Host *);
-
 #ifndef CMD_PER_LUN
 #define CMD_PER_LUN 2
 #endif
drivers/scsi/t128.h +0 -6
Index: linux/drivers/scsi/t128.h
===================================================================
@@ -88,12 +88,6 @@
 #define T_DATA_REG_OFFSET	0x1e00	/* rw 512 bytes long */
 
 #ifndef ASM
-static int t128_abort(struct scsi_cmnd *);
-static int t128_biosparam(struct scsi_device *, struct block_device *,
-			  sector_t, int*);
-static int t128_detect(struct scsi_host_template *);
-static int t128_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int t128_bus_reset(struct scsi_cmnd *);
 
 #ifndef CMD_PER_LUN
 #define CMD_PER_LUN 2
drivers/scsi/atari_scsi.c +0 -5
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -181,12 +181,7 @@ static inline void DISABLE_IRQ(void)
 /***************************** Prototypes *****************************/
 
 #ifdef REAL_DMA
-static int scsi_dma_is_ignored_buserr(unsigned char dma_stat);
 static void atari_scsi_fetch_restbytes(void);
-static long atari_scsi_dma_residual(struct Scsi_Host *instance);
-static int falcon_classify_cmd(Scsi_Cmnd *cmd);
-static unsigned long atari_dma_xfer_len(unsigned long wanted_len,
-					Scsi_Cmnd *cmd, int write_flag);
 #endif
 static irqreturn_t scsi_tt_intr(int irq, void *dummy);
 static irqreturn_t scsi_falcon_intr(int irq, void *dummy);
Reviewed-by on v2 5/36
#6 lore raw

Re: [PATCH v2 05/36] ncr5380: Remove useless prototypes

Quoted 7 lines · Finn Thain

Add missing static qualifiers and remove the now pointless prototypes. The NCR5380_* prototypes are all declared in NCR5380.h and renamed using macros. Further declarations are redundant (some are completely unused). Remove them.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#7 lore raw

PATCH v2 6/36 ncr5380: Remove more useless prototypes

In reply to Finn Thain

Make use of the host template static initializer instead of assigning handlers at run-time. Move __maybe_unused qualifiers from declarations to definitions. Move the atari_scsi_bus_reset() wrapper after the definition of NCR5380_bus_reset(). All of the host template handler prototypes are now redundant so remove them.

The write_info() handler is only relevant to drivers using PSEUDO_DMA so this patch fixes the compiler warning in atari_NCR5380.c and sun3_NCR5380.c:

CC drivers/scsi/atari_scsi.o
drivers/scsi/NCR5380.h:329: warning: 'NCR5380_write_info' declared 'static' but never defined

---
 drivers/scsi/NCR5380.h       |    8 ----
 drivers/scsi/atari_NCR5380.c |    3 +
 drivers/scsi/atari_scsi.c    |   76 ++++++++++++++++++++-----------------------
 drivers/scsi/dtc.c           |    7 +--
 drivers/scsi/pas16.c         |    7 +--
 drivers/scsi/sun3_NCR5380.c  |    3 +
 drivers/scsi/t128.c          |    7 +--
 7 files changed, 50 insertions(+), 61 deletions(-)
drivers/scsi/NCR5380.h +0 -8
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -322,14 +322,6 @@ static irqreturn_t NCR5380_intr(int irq,
 #endif
 static void NCR5380_main(struct work_struct *work);
 static void __maybe_unused NCR5380_print_options(struct Scsi_Host *instance);
-static int NCR5380_abort(Scsi_Cmnd * cmd);
-static int NCR5380_bus_reset(Scsi_Cmnd * cmd);
-static int NCR5380_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int __maybe_unused NCR5380_show_info(struct seq_file *,
-	struct Scsi_Host *);
-static int __maybe_unused NCR5380_write_info(struct Scsi_Host *instance,
-	char *buffer, int length);
-
 static void NCR5380_reselect(struct Scsi_Host *instance);
 static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd * cmd, int tag);
 #if defined(PSEUDO_DMA) || defined(REAL_DMA) || defined(REAL_DMA_POLL)
drivers/scsi/dtc.c +3 -4
Index: linux/drivers/scsi/dtc.c
===================================================================
@@ -219,10 +219,6 @@ static int __init dtc_detect(struct scsi
 	void __iomem *base;
 	int sig, count;
 
-	tpnt->proc_name = "dtc3x80";
-	tpnt->show_info = dtc_show_info;
-	tpnt->write_info = dtc_write_info;
-
 	for (count = 0; current_override < NO_OVERRIDES; ++current_override) {
 		addr = 0;
 		base = NULL;
@@ -477,6 +473,9 @@ static struct scsi_host_template driver_
 	.name				= "DTC 3180/3280 ",
 	.detect				= dtc_detect,
 	.release			= dtc_release,
+	.proc_name			= "dtc3x80",
+	.show_info			= dtc_show_info,
+	.write_info			= dtc_write_info,
 	.queuecommand			= dtc_queue_command,
 	.eh_abort_handler		= dtc_abort,
 	.eh_bus_reset_handler		= dtc_bus_reset,
drivers/scsi/pas16.c +3 -4
Index: linux/drivers/scsi/pas16.c
===================================================================
@@ -390,10 +390,6 @@ static int __init pas16_detect(struct sc
     unsigned short io_port;
     int  count;
 
-    tpnt->proc_name = "pas16";
-    tpnt->show_info = pas16_show_info;
-    tpnt->write_info = pas16_write_info;
-
     if (pas16_addr != 0) {
 	overrides[0].io_port = pas16_addr;
 	/*
@@ -620,6 +616,9 @@ static struct scsi_host_template driver_
 	.name           = "Pro Audio Spectrum-16 SCSI",
 	.detect         = pas16_detect,
 	.release        = pas16_release,
+	.proc_name      = "pas16",
+	.show_info      = pas16_show_info,
+	.write_info     = pas16_write_info,
 	.queuecommand   = pas16_queue_command,
 	.eh_abort_handler = pas16_abort,
 	.eh_bus_reset_handler = pas16_bus_reset,
drivers/scsi/t128.c +3 -4
Index: linux/drivers/scsi/t128.c
===================================================================
@@ -201,10 +201,6 @@ static int __init t128_detect(struct scs
     void __iomem *p;
     int sig, count;
 
-    tpnt->proc_name = "t128";
-    tpnt->show_info = t128_show_info;
-    tpnt->write_info = t128_write_info;
-
     for (count = 0; current_override < NO_OVERRIDES; ++current_override) {
 	base = 0;
 	p = NULL;
@@ -435,6 +431,9 @@ static struct scsi_host_template driver_
 	.name           = "Trantor T128/T128F/T228",
 	.detect         = t128_detect,
 	.release        = t128_release,
+	.proc_name      = "t128",
+	.show_info      = t128_show_info,
+	.write_info     = t128_write_info,
 	.queuecommand   = t128_queue_command,
 	.eh_abort_handler = t128_abort,
 	.eh_bus_reset_handler    = t128_bus_reset,
drivers/scsi/atari_NCR5380.c +2 -1
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -772,7 +772,8 @@ static void show_Scsi_Cmnd(Scsi_Cmnd *cm
 	seq_printf(m, "\n");
 }
 
-static int NCR5380_show_info(struct seq_file *m, struct Scsi_Host *instance)
+static int __maybe_unused NCR5380_show_info(struct seq_file *m,
+                                            struct Scsi_Host *instance)
 {
 	struct NCR5380_hostdata *hostdata;
 	Scsi_Cmnd *ptr;
drivers/scsi/sun3_NCR5380.c +2 -1
Index: linux/drivers/scsi/sun3_NCR5380.c
===================================================================
@@ -718,7 +718,8 @@ static void show_Scsi_Cmnd(Scsi_Cmnd *cm
 	seq_printf(m, "\n");
 }
 
-static int NCR5380_show_info(struct seq_file *m, struct Scsi_Host *instance)
+static int __maybe_unused NCR5380_show_info(struct seq_file *m,
+                                            struct Scsi_Host *instance)
 {
 	struct NCR5380_hostdata *hostdata;
 	Scsi_Cmnd *ptr;
drivers/scsi/atari_scsi.c +37 -39

88 lines not on this page · raw message

#8 lore raw

Re: [PATCH v2 06/36] ncr5380: Remove more useless prototypes

Quoted 59 lines · Finn Thain

Make use of the host template static initializer instead of assigning handlers at run-time. Move __maybe_unused qualifiers from declarations to definitions. Move the atari_scsi_bus_reset() wrapper after the definition of NCR5380_bus_reset(). All of the host template handler prototypes are now redundant so remove them.

The write_info() handler is only relevant to drivers using PSEUDO_DMA so this patch fixes the compiler warning in atari_NCR5380.c and sun3_NCR5380.c:

CC drivers/scsi/atari_scsi.o
drivers/scsi/NCR5380.h:329: warning: 'NCR5380_write_info' declared 'static' but never defined

---
 drivers/scsi/NCR5380.h       |    8 ----
 drivers/scsi/atari_NCR5380.c |    3 +
 drivers/scsi/atari_scsi.c    |   76 ++++++++++++++++++++-----------------------
 drivers/scsi/dtc.c           |    7 +--
 drivers/scsi/pas16.c         |    7 +--
 drivers/scsi/sun3_NCR5380.c  |    3 +
 drivers/scsi/t128.c          |    7 +--
 7 files changed, 50 insertions(+), 61 deletions(-)

Index: linux/drivers/scsi/NCR5380.h
===================================================================

drivers/scsi/NCR5380.h +0 -8
@@ -322,14 +322,6 @@ static irqreturn_t NCR5380_intr(int irq,
 #endif
 static void NCR5380_main(struct work_struct *work);
 static void __maybe_unused NCR5380_print_options(struct Scsi_Host *instance);
-static int NCR5380_abort(Scsi_Cmnd * cmd);
-static int NCR5380_bus_reset(Scsi_Cmnd * cmd);
-static int NCR5380_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int __maybe_unused NCR5380_show_info(struct seq_file *,
-	struct Scsi_Host *);
-static int __maybe_unused NCR5380_write_info(struct Scsi_Host *instance,
-	char *buffer, int length);
-
 static void NCR5380_reselect(struct Scsi_Host *instance);
 static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd * cmd, int tag);
 #if defined(PSEUDO_DMA) || defined(REAL_DMA) || defined(REAL_DMA_POLL)

Index: linux/drivers/scsi/dtc.c
===================================================================

drivers/scsi/dtc.c +0 -4
@@ -219,10 +219,6 @@ static int __init dtc_detect(struct scsi
 	void __iomem *base;
 	int sig, count;
 
-	tpnt->proc_name = "dtc3x80";
-	tpnt->show_info = dtc_show_info;
-	tpnt->write_info = dtc_write_info;
-
 	for (count = 0; current_override < NO_OVERRIDES; ++current_override) {
 		addr = 0;
 		base = NULL;

drivers/scsi/dtc.c static struct scsi_host_template driver_ · line 481

Quoted 9 lines
drivers/scsi/dtc.c +3 -0
@@ -477,6 +473,9 @@ static struct scsi_host_template driver_
 	.name				= "DTC 3180/3280 ",
 	.detect				= dtc_detect,
 	.release			= dtc_release,
+	.proc_name			= "dtc3x80",
+	.show_info			= dtc_show_info,
+	.write_info			= dtc_write_info,
 	.queuecommand			= dtc_queue_command,
 	.eh_abort_handler		= dtc_abort,
 	.eh_bus_reset_handler		= dtc_bus_reset,

What is the current consensus on using '.proc_name' ? At one point is was claimed to be deprecated, yet the only driver actually following this seems to be lpfc.
(_And_ we have a patch in our tree to hook that back in).

Can't we just get it back for the time being and decide upon a proper solution later?

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#9 lore raw

Re: [PATCH v2 06/36] ncr5380: Remove more useless prototypes

Ping...

Quoted 82 lines · Hannes Reinecke
Quoted 59 lines · Finn Thain

Make use of the host template static initializer instead of assigning handlers at run-time. Move __maybe_unused qualifiers from declarations to definitions. Move the atari_scsi_bus_reset() wrapper after the definition of NCR5380_bus_reset(). All of the host template handler prototypes are now redundant so remove them.

The write_info() handler is only relevant to drivers using PSEUDO_DMA so this patch fixes the compiler warning in atari_NCR5380.c and sun3_NCR5380.c:

CC drivers/scsi/atari_scsi.o
drivers/scsi/NCR5380.h:329: warning: 'NCR5380_write_info' declared 'static' but never defined

---
 drivers/scsi/NCR5380.h       |    8 ----
 drivers/scsi/atari_NCR5380.c |    3 +
 drivers/scsi/atari_scsi.c    |   76 ++++++++++++++++++++-----------------------
 drivers/scsi/dtc.c           |    7 +--
 drivers/scsi/pas16.c         |    7 +--
 drivers/scsi/sun3_NCR5380.c  |    3 +
 drivers/scsi/t128.c          |    7 +--
 7 files changed, 50 insertions(+), 61 deletions(-)

Index: linux/drivers/scsi/NCR5380.h
===================================================================

drivers/scsi/NCR5380.h +0 -8
@@ -322,14 +322,6 @@ static irqreturn_t NCR5380_intr(int irq,
 #endif
 static void NCR5380_main(struct work_struct *work);
 static void __maybe_unused NCR5380_print_options(struct Scsi_Host *instance);
-static int NCR5380_abort(Scsi_Cmnd * cmd);
-static int NCR5380_bus_reset(Scsi_Cmnd * cmd);
-static int NCR5380_queue_command(struct Scsi_Host *, struct scsi_cmnd *);
-static int __maybe_unused NCR5380_show_info(struct seq_file *,
-	struct Scsi_Host *);
-static int __maybe_unused NCR5380_write_info(struct Scsi_Host *instance,
-	char *buffer, int length);
-
 static void NCR5380_reselect(struct Scsi_Host *instance);
 static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd * cmd, int tag);
 #if defined(PSEUDO_DMA) || defined(REAL_DMA) || defined(REAL_DMA_POLL)

Index: linux/drivers/scsi/dtc.c
===================================================================

drivers/scsi/dtc.c +0 -4
@@ -219,10 +219,6 @@ static int __init dtc_detect(struct scsi
 	void __iomem *base;
 	int sig, count;
 
-	tpnt->proc_name = "dtc3x80";
-	tpnt->show_info = dtc_show_info;
-	tpnt->write_info = dtc_write_info;
-
 	for (count = 0; current_override < NO_OVERRIDES; ++current_override) {
 		addr = 0;
 		base = NULL;

drivers/scsi/dtc.c static struct scsi_host_template driver_ · line 481

Quoted 9 lines
drivers/scsi/dtc.c +3 -0
@@ -477,6 +473,9 @@ static struct scsi_host_template driver_
 	.name				= "DTC 3180/3280 ",
 	.detect				= dtc_detect,
 	.release			= dtc_release,
+	.proc_name			= "dtc3x80",
+	.show_info			= dtc_show_info,
+	.write_info			= dtc_write_info,
 	.queuecommand			= dtc_queue_command,
 	.eh_abort_handler		= dtc_abort,
 	.eh_bus_reset_handler		= dtc_bus_reset,

What is the current consensus on using '.proc_name' ? At one point is was claimed to be deprecated, yet the only driver actually following this seems to be lpfc.
(_And_ we have a patch in our tree to hook that back in).

Can't we just get it back for the time being and decide upon a proper solution later?

Cheers,

Hannes

Reviewed-by
#10 lore raw

Re: [PATCH v2 06/36] ncr5380: Remove more useless prototypes

Quoted 3 lines · Finn Thain

Ping...

Ok, disregard the .proc_name issue for now.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 21284 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#11 lore raw

PATCH v2 7/36 ncr5380: Cleanup TAG_NEXT and TAG_NONE macros

In reply to Finn Thain

Both atari_NCR5380.c and sun3_NCR5380.c core drivers #undef TAG_NONE and then redefine it. But the original definition is unused because NCR5380.c lacks support for tagged queueing. So just define it once.

The TAG_NEXT macro only appears in the arguments to NCR5380_select() calls. But that routine doesn't use its tag argument as the tag was already assigned in NCR5380_main(). So remove the unused argument and the macro.

---
 drivers/scsi/NCR5380.c       |   29 +++++++++++++----------------
 drivers/scsi/NCR5380.h       |   11 ++++-------
 drivers/scsi/atari_NCR5380.c |   19 +++++--------------
 drivers/scsi/sun3_NCR5380.c  |   19 +++++--------------
 4 files changed, 27 insertions(+), 51 deletions(-)
drivers/scsi/atari_NCR5380.c +5 -14
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -316,10 +316,6 @@ static struct scsi_host_template *the_te
  * important: the tag bit must be cleared before 'nr_allocated' is decreased.
  */
 
-/* -1 for TAG_NONE is not possible with unsigned char cmd->tag */
-#undef TAG_NONE
-#define TAG_NONE 0xff
-
 typedef struct {
 	DECLARE_BITMAP(allocated, MAX_TAGS);
 	int nr_allocated;
@@ -1118,9 +1114,7 @@ static void NCR5380_main(struct work_str
 #ifdef SUPPORT_TAGS
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
-					if (!NCR5380_select(instance, tmp,
-					    (tmp->cmnd[0] == REQUEST_SENSE) ? TAG_NONE :
-					    TAG_NEXT)) {
+					if (!NCR5380_select(instance, tmp)) {
 						falcon_dont_release--;
 						/* release if target did not response! */
 						falcon_release_lock_if_possible(hostdata);
@@ -1351,17 +1345,14 @@ static void collect_stats(struct NCR5380
 #endif
 
 /*
- * Function : int NCR5380_select (struct Scsi_Host *instance, Scsi_Cmnd *cmd,
- *	int tag);
+ * Function : int NCR5380_select (struct Scsi_Host *instance, Scsi_Cmnd *cmd)
  *
  * Purpose : establishes I_T_L or I_T_L_Q nexus for new or existing command,
  *	including ARBITRATION, SELECTION, and initial message out for
  *	IDENTIFY and queue messages.
  *
  * Inputs : instance - instantiation of the 5380 driver on which this
- *	target lives, cmd - SCSI command to execute, tag - set to TAG_NEXT for
- *	new tag, TAG_NONE for untagged queueing, otherwise set to the tag for
- *	the command that is presently connected.
+ *	target lives, cmd - SCSI command to execute.
  *
  * Returns : -1 if selection could not execute for some reason,
  *	0 if selection succeeded or failed because the target
@@ -1381,7 +1372,7 @@ static void collect_stats(struct NCR5380
  *		cmd->result host byte set to DID_BAD_TARGET.
  */
 
-static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd *cmd, int tag)
+static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd *cmd)
 {
 	SETUP_HOSTDATA(instance);
 	unsigned char tmp[3], phase;
@@ -2758,7 +2749,7 @@ int NCR5380_abort(Scsi_Cmnd *cmd)
 			local_irq_restore(flags);
 			dprintk(NDEBUG_ABORT, "scsi%d: aborting disconnected command.\n", HOSTNO);
 
-			if (NCR5380_select(instance, cmd, (int)cmd->tag))
+			if (NCR5380_select(instance, cmd))
 				return FAILED;
 
 			dprintk(NDEBUG_ABORT, "scsi%d: nexus reestablished.\n", HOSTNO);
drivers/scsi/sun3_NCR5380.c +5 -14
Index: linux/drivers/scsi/sun3_NCR5380.c
===================================================================
@@ -305,10 +305,6 @@ static struct scsi_host_template *the_te
  * important: the tag bit must be cleared before 'nr_allocated' is decreased.
  */
 
-/* -1 for TAG_NONE is not possible with unsigned char cmd->tag */
-#undef TAG_NONE
-#define TAG_NONE 0xff
-
 /* For the m68k, the number of bits in 'allocated' must be a multiple of 32! */
 #if (MAX_TAGS % 32) != 0
 #error "MAX_TAGS must be a multiple of 32!"
@@ -1057,9 +1053,7 @@ static void NCR5380_main (struct work_st
 #ifdef SUPPORT_TAGS
 		    cmd_get_tag( tmp, tmp->cmnd[0] != REQUEST_SENSE );
 #endif
-		    if (!NCR5380_select(instance, tmp, 
-			    (tmp->cmnd[0] == REQUEST_SENSE) ? TAG_NONE : 
-			    TAG_NEXT)) {
+		    if (!NCR5380_select(instance, tmp)) {
 			break;
 		    } else {
 			local_irq_disable();
@@ -1292,16 +1286,14 @@ static void collect_stats(struct NCR5380
 
 /* 
  * Function : int NCR5380_select(struct Scsi_Host *instance,
- * 				 struct scsi_cmnd *cmd,	int tag);
+ *				 struct scsi_cmnd *cmd)
  *
  * Purpose : establishes I_T_L or I_T_L_Q nexus for new or existing command,
  *	including ARBITRATION, SELECTION, and initial message out for 
  *	IDENTIFY and queue messages. 
  *
  * Inputs : instance - instantiation of the 5380 driver on which this 
- * 	target lives, cmd - SCSI command to execute, tag - set to TAG_NEXT for 
- *	new tag, TAG_NONE for untagged queueing, otherwise set to the tag for 
- *	the command that is presently connected.
+ *	target lives, cmd - SCSI command to execute.
  * 
  * Returns : -1 if selection could not execute for some reason,
  *	0 if selection succeeded or failed because the target 
@@ -1321,8 +1313,7 @@ static void collect_stats(struct NCR5380
  *		cmd->result host byte set to DID_BAD_TARGET.
  */
 
-static int NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd,
-			  int tag)
+static int NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
 {
     SETUP_HOSTDATA(instance);
     unsigned char tmp[3], phase;
@@ -2736,7 +2727,7 @@ static int NCR5380_abort(struct scsi_cmn
             local_irq_restore(flags);
 	    dprintk(NDEBUG_ABORT, "scsi%d: aborting disconnected command.\n", HOSTNO);
   
-            if (NCR5380_select (instance, cmd, (int) cmd->tag)) 
+	    if (NCR5380_select(instance, cmd))
 		return FAILED;
 
 	    dprintk(NDEBUG_ABORT, "scsi%d: nexus reestablished.\n", HOSTNO);
drivers/scsi/NCR5380.c +13 -16
Index: linux/drivers/scsi/NCR5380.c
===================================================================
@@ -1073,14 +1073,14 @@ static void NCR5380_main(struct work_str
 					hostdata->selecting = NULL;
 					/* RvC: have to preset this to indicate a new command is being performed */
 
-					if (!NCR5380_select(instance, tmp,
-							    /* 
-							     * REQUEST SENSE commands are issued without tagged
-							     * queueing, even on SCSI-II devices because the 
-							     * contingent allegiance condition exists for the 
-							     * entire unit.
-							     */
-							    (tmp->cmnd[0] == REQUEST_SENSE) ? TAG_NONE : TAG_NEXT)) {
+					/*
+					 * REQUEST SENSE commands are issued without tagged
+					 * queueing, even on SCSI-II devices because the
+					 * contingent allegiance condition exists for the
+					 * entire unit.
+					 */
+
+					if (!NCR5380_select(instance, tmp)) {
 						break;
 					} else {
 						LIST(tmp, hostdata->issue_queue);
@@ -1097,7 +1097,7 @@ static void NCR5380_main(struct work_str
 		if (hostdata->selecting) {
 			tmp = (Scsi_Cmnd *) hostdata->selecting;
 			/* Selection will drop and retake the lock */
-			if (!NCR5380_select(instance, tmp, (tmp->cmnd[0] == REQUEST_SENSE) ? TAG_NONE : TAG_NEXT)) {
+			if (!NCR5380_select(instance, tmp)) {
 				/* Ok ?? */
 			} else {
 				/* RvC: device failed, so we wait a long time
@@ -1246,17 +1246,14 @@ static void collect_stats(struct NCR5380
 
 
 /* 
- * Function : int NCR5380_select (struct Scsi_Host *instance, Scsi_Cmnd *cmd, 
- *      int tag);
+ * Function : int NCR5380_select (struct Scsi_Host *instance, Scsi_Cmnd *cmd)
  *
  * Purpose : establishes I_T_L or I_T_L_Q nexus for new or existing command,
  *      including ARBITRATION, SELECTION, and initial message out for 
  *      IDENTIFY and queue messages. 
  *
  * Inputs : instance - instantiation of the 5380 driver on which this 
- *      target lives, cmd - SCSI command to execute, tag - set to TAG_NEXT for 
- *      new tag, TAG_NONE for untagged queueing, otherwise set to the tag for 
- *      the command that is presently connected.
+ *      target lives, cmd - SCSI command to execute.
  * 
  * Returns : -1 if selection could not execute for some reason,
  *      0 if selection succeeded or failed because the target 
@@ -1278,7 +1275,7 @@ static void collect_stats(struct NCR5380
  *	Locks: caller holds hostdata lock in IRQ mode
  */
  
-static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd * cmd, int tag) 
+static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd *cmd)
 {
 	NCR5380_local_declare();
 	struct NCR5380_hostdata *hostdata = (struct NCR5380_hostdata *) instance->hostdata;
@@ -2774,7 +2771,7 @@ static int NCR5380_abort(Scsi_Cmnd * cmd
 		if (cmd == tmp) {
 			dprintk(NDEBUG_ABORT, "scsi%d : aborting disconnected command.\n", instance->host_no);
 
-			if (NCR5380_select(instance, cmd, (int) cmd->tag))
+			if (NCR5380_select(instance, cmd))
 				return FAILED;
 			dprintk(NDEBUG_ABORT, "scsi%d : nexus reestablished.\n", instance->host_no);
 
drivers/scsi/NCR5380.h +4 -7
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -224,14 +224,11 @@
 #define DISCONNECT_LONG		2
 
 /* 
- * These are "special" values for the tag parameter passed to NCR5380_select.
+ * "Special" value for the (unsigned char) command tag, to indicate
+ * I_T_L nexus instead of I_T_L_Q.
  */
 
-#define TAG_NEXT	-1	/* Use next free tag */
-#define TAG_NONE	-2	/* 
-				 * Establish I_T_L nexus instead of I_T_L_Q
-				 * even on SCSI-II devices.
-				 */
+#define TAG_NONE	0xff
 
 /*
  * These are "special" values for the irq and dma_channel fields of the 
@@ -323,7 +320,7 @@ static irqreturn_t NCR5380_intr(int irq,
 static void NCR5380_main(struct work_struct *work);
 static void __maybe_unused NCR5380_print_options(struct Scsi_Host *instance);
 static void NCR5380_reselect(struct Scsi_Host *instance);
-static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd * cmd, int tag);
+static int NCR5380_select(struct Scsi_Host *instance, Scsi_Cmnd *cmd);
 #if defined(PSEUDO_DMA) || defined(REAL_DMA) || defined(REAL_DMA_POLL)
 static int NCR5380_transfer_dma(struct Scsi_Host *instance, unsigned char *phase, int *count, unsigned char **data);
 #endif
Reviewed-by on v2 7/36
#12 lore raw

Re: [PATCH v2 07/36] ncr5380: Cleanup TAG_NEXT and TAG_NONE macros

Quoted 9 lines · Finn Thain

Both atari_NCR5380.c and sun3_NCR5380.c core drivers #undef TAG_NONE and then redefine it. But the original definition is unused because NCR5380.c lacks support for tagged queueing. So just define it once.

The TAG_NEXT macro only appears in the arguments to NCR5380_select() calls. But that routine doesn't use its tag argument as the tag was already assigned in NCR5380_main(). So remove the unused argument and the macro.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#15 lore raw

PATCH v2 9/36 ncr5380: Remove duplicate comments

In reply to Finn Thain

The LIMIT_TRANSFERSIZE, PSEUDO_DMA, PARITY and UNSAFE options are all documented in the core drivers where they are used. The same goes for the chip databook reference. Remove the duplicate comments.

---
 drivers/scsi/dtc.c       |   17 +----------------
 drivers/scsi/dtc.h       |   16 ----------------
 drivers/scsi/g_NCR5380.c |   16 ----------------
 drivers/scsi/g_NCR5380.h |   12 ------------
 drivers/scsi/mac_scsi.c  |   12 ------------
 drivers/scsi/mac_scsi.h  |   12 ------------
 drivers/scsi/pas16.c     |   31 -------------------------------
 drivers/scsi/pas16.h     |   12 ------------
 drivers/scsi/sun3_scsi.c |   21 ---------------------
 drivers/scsi/sun3_scsi.h |   12 ------------
 drivers/scsi/t128.c      |   23 -----------------------
 drivers/scsi/t128.h      |   12 ------------
 12 files changed, 1 insertion(+), 195 deletions(-)
drivers/scsi/dtc.c +1 -16
Index: linux/drivers/scsi/dtc.c
===================================================================
@@ -19,24 +19,9 @@
  *      +1 (303) 440-4894
  *
  * DISTRIBUTION RELEASE 1.
- *
- * For more information, please consult 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
-*/
+ */
 
 /*
- * Options : 
- * PSEUDO_DMA - enables PSEUDO-DMA hardware, should give a 3-4X performance
- * increase compared to polled I/O.
- *
- * PARITY - enable parity checking.  Not supported.
- *
- * UNSAFE - leave interrupts enabled during pseudo-DMA transfers. 
- *		You probably want this.
- *
  * The card is detected and initialized in one of several ways : 
  * 1.  Autoprobe (default) - since the board is memory mapped, 
  *     a BIOS signature is scanned for to locate the registers.
drivers/scsi/g_NCR5380.c +0 -16
Index: linux/drivers/scsi/g_NCR5380.c
===================================================================
@@ -20,18 +20,6 @@
  * Thomas Sailer, [email protected]
  *
  * ALPHA RELEASE 1. 
- *
- * For more information, please consult 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 /* 
@@ -40,10 +28,6 @@
  */
 
 /*
- * Options :
- *
- * PARITY - enable parity checking.  Not supported.
- *
  * The card is detected and initialized in one of several ways : 
  * 1.  With command line overrides - NCR5380=port,irq may be 
  *     used on the LILO command line to override the defaults.
drivers/scsi/pas16.c +0 -31
Index: linux/drivers/scsi/pas16.c
===================================================================
@@ -22,40 +22,9 @@
  * Media Vision
  * (510) 770-8600
  * (800) 348-7116
- * 
- * and 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 /*
- * Options : 
- * LIMIT_TRANSFERSIZE - if defined, limit the pseudo-dma transfers to 512
- *      bytes at a time.  Since interrupts are disabled by default during
- *      these transfers, we might need this to give reasonable interrupt
- *      service time if the transfer size gets too large.
- *
- * PSEUDO_DMA - enables PSEUDO-DMA hardware, should give a 3-4X performance
- * increase compared to polled I/O.
- *
- * PARITY - enable parity checking.  Not supported.
- *
- * UNSAFE - leave interrupts enabled during pseudo-DMA transfers.  This
- *	    parameter comes from the NCR5380 code.  It is NOT unsafe with
- *	    the PAS16 and you should use it.  If you don't you will have
- *	    a problem with dropped characters during high speed
- *	    communications during SCSI transfers.  If you really don't
- *	    want to use UNSAFE you can try defining LIMIT_TRANSFERSIZE or
- *	    twiddle with the transfer size in the high level code.
- *
  * The card is detected and initialized in one of several ways : 
  * 1.  Autoprobe (default) - There are many different models of
  *     the Pro Audio Spectrum/Studio 16, and I only have one of
drivers/scsi/sun3_scsi.c +0 -21
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -22,27 +22,6 @@
  * Copyright 1995, Russell King
  *
  * ALPHA RELEASE 1.
- *
- * For more information, please consult
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
- */
-
-
-/*
- * This is from mac_scsi.h, but hey, maybe this is useful for Sun3 too! :)
- *
- * Options :
- *
- * PARITY - enable parity checking.  Not supported.
  */
 
 #include <linux/types.h>
drivers/scsi/t128.c +0 -23
Index: linux/drivers/scsi/t128.c
===================================================================
@@ -23,32 +23,9 @@
  * 5415 Randall Place
  * Fremont, CA 94538
  * 1+ (415) 770-1400, FAX 1+ (415) 770-9910
- * 
- * and 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 /*
- * Options : 
- * PSEUDO_DMA - enables PSEUDO-DMA hardware, should give a 3-4X performance
- * increase compared to polled I/O.
- *
- * PARITY - enable parity checking.  Not supported.
- *
- * UNSAFE - leave interrupts enabled during pseudo-DMA transfers.  You
- *          only really want to use this if you're having a problem with
- *          dropped characters during high speed communications, and even
- *          then, you're going to be better off twiddling with transfersize.
- *
  * The card is detected and initialized in one of several ways : 
  * 1.  Autoprobe (default) - since the board is memory mapped, 
  *     a BIOS signature is scanned for to locate the registers.
drivers/scsi/dtc.h +0 -16
Index: linux/drivers/scsi/dtc.h
===================================================================
@@ -7,22 +7,6 @@
  *      +1 (303) 440-4894
  *
  * DISTRIBUTION RELEASE 2. 
- *
- * For more information, please consult 
- *
- * 
- * 
- * and 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #ifndef DTC3280_H
drivers/scsi/g_NCR5380.h +0 -12
Index: linux/drivers/scsi/g_NCR5380.h
===================================================================
@@ -11,18 +11,6 @@
  *    [email protected]
  *
  * ALPHA RELEASE 1. 
- *
- * For more information, please consult 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #ifndef GENERIC_NCR5380_H
drivers/scsi/mac_scsi.c +0 -12
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -11,18 +11,6 @@
  * Copyright 1995, Russell King
  *
  * ALPHA RELEASE 1.
- *
- * For more information, please consult
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #include <linux/types.h>
drivers/scsi/mac_scsi.h +0 -12
Index: linux/drivers/scsi/mac_scsi.h
===================================================================
@@ -8,18 +8,6 @@
  *      +1 (303) 440-4894
  *
  * ALPHA RELEASE 1.
- *
- * For more information, please consult
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #ifndef MAC_NCR5380_H
drivers/scsi/pas16.h +0 -12
Index: linux/drivers/scsi/pas16.h
===================================================================
@@ -18,18 +18,6 @@
  * Media Vision
  * (510) 770-8600
  * (800) 348-7116
- * 
- * and 
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 
drivers/scsi/sun3_scsi.h +0 -12
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -15,18 +15,6 @@
  *      +1 (303) 440-4894
  *
  * ALPHA RELEASE 1.
- *
- * For more information, please consult
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #ifndef SUN3_SCSI_H
drivers/scsi/t128.h +0 -12
Index: linux/drivers/scsi/t128.h
===================================================================
@@ -20,18 +20,6 @@
  * 5415 Randall Place
  * Fremont, CA 94538
  * 1+ (415) 770-1400, FAX 1+ (415) 770-9910
- *
- * and
- *
- * NCR 5380 Family
- * SCSI Protocol Controller
- * Databook
- *
- * NCR Microelectronics
- * 1635 Aeroplaza Drive
- * Colorado Springs, CO 80916
- * 1+ (719) 578-3400
- * 1+ (800) 334-5454
  */
 
 #ifndef T128_H
Reviewed-by on v2 9/36
#16 lore raw

Re: [PATCH v2 09/36] ncr5380: Remove duplicate comments

Quoted 6 lines · Finn Thain

The LIMIT_TRANSFERSIZE, PSEUDO_DMA, PARITY and UNSAFE options are all documented in the core drivers where they are used. The same goes for the chip databook reference. Remove the duplicate comments.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
#18 lore raw

PATCH v2 10/36 ncr5380: Fix SCSI_IRQ_NONE bugs

Quoted 13 lines · Finn Thain

Oak scsi doesn't use any IRQ, but it sets irq = IRQ_NONE rather than SCSI_IRQ_NONE. Problem is, the core NCR5380 driver expects SCSI_IRQ_NONE if it is to issue IDENTIFY commands that prevent target disconnection. And, as Geert points out, IRQ_NONE is part of enum irqreturn.

Other drivers, when they can't get an IRQ or can't use one, will set host->irq = SCSI_IRQ_NONE (that is, 255). But when they exit they will attempt to free IRQ 255 which was never requested.

Fix these bugs by using NO_IRQ in place of SCSI_IRQ_NONE and IRQ_NONE. That means IRQ 0 is no longer probed by ISA drivers but I don't think this matters.

Quoted 7 lines

Setting IRQ = 255 for these ISA drivers is understood to mean no IRQ. This remains supported so as to avoid breaking existing ISA setups (which can be difficult to get working) and because existing documentation (SANE, TLDP etc) describes this usage for the ISA NCR5380 driver options.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
hare at suse.de			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: J. Hawn, J. Guild, F. Imend?rffer, HRB 16746 (AG N?rnberg)
author
#19 lore raw

PATCH v2 11/36 ncr5380: Remove NCR5380_STATS

In reply to Finn Thain

The NCR5380_STATS option is only enabled by g_NCR5380 yet it adds clutter to all three core drivers. The atari_NCR5380.c and sun3_NCR5380.c core drivers have a slightly different implementation of the NCR5380_STATS option.

Out of all ten NCR5380 drivers, only one of them (g_NCR5380) actually has the code to report on the collected stats. Aside from being unreadable, that code seems to be broken because there's no initialization of timebase. sun3_NCR5380.c and atari_NCR5380.c have the timebase initialization but lack the code to report the stats.

Remove all of this code to improve readability and reduce divergence between the three core drivers.

This patch and the next one completely eliminate the PRINTP and ANDP pre-processor abuse.

---
 drivers/scsi/NCR5380.c       |   64 ---------------------------------------
 drivers/scsi/NCR5380.h       |    9 -----
 drivers/scsi/atari_NCR5380.c |   65 ----------------------------------------
 drivers/scsi/g_NCR5380.c     |   45 ----------------------------
 drivers/scsi/sun3_NCR5380.c  |   69 -------------------------------------------
 5 files changed, 252 deletions(-)
drivers/scsi/NCR5380.c +0 -64
Index: linux/drivers/scsi/NCR5380.c
===================================================================
@@ -833,18 +833,6 @@ static int NCR5380_init(struct Scsi_Host
 	
 	INIT_DELAYED_WORK(&hostdata->coroutine, NCR5380_main);
 	
-#ifdef NCR5380_STATS
-	for (i = 0; i < 8; ++i) {
-		hostdata->time_read[i] = 0;
-		hostdata->time_write[i] = 0;
-		hostdata->bytes_read[i] = 0;
-		hostdata->bytes_write[i] = 0;
-	}
-	hostdata->timebase = 0;
-	hostdata->pendingw = 0;
-	hostdata->pendingr = 0;
-#endif
-
 	/* The CHECK code seems to break the 53C400. Will check it later maybe */
 	if (flags & FLAG_NCR53C400)
 		hostdata->flags = FLAG_HAS_LAST_BYTE_SENT | flags;
@@ -943,25 +931,6 @@ static int NCR5380_queue_command_lck(Scs
 	}
 #endif				/* (NDEBUG & NDEBUG_NO_WRITE) */
 
-#ifdef NCR5380_STATS
-	switch (cmd->cmnd[0]) {
-		case WRITE:
-		case WRITE_6:
-		case WRITE_10:
-			hostdata->time_write[cmd->device->id] -= (jiffies - hostdata->timebase);
-			hostdata->bytes_write[cmd->device->id] += scsi_bufflen(cmd);
-			hostdata->pendingw++;
-			break;
-		case READ:
-		case READ_6:
-		case READ_10:
-			hostdata->time_read[cmd->device->id] -= (jiffies - hostdata->timebase);
-			hostdata->bytes_read[cmd->device->id] += scsi_bufflen(cmd);
-			hostdata->pendingr++;
-			break;
-	}
-#endif
-
 	/* 
 	 * We use the host_scribble field as a pointer to the next command  
 	 * in a queue 
@@ -1207,35 +1176,6 @@ static irqreturn_t NCR5380_intr(int dumm
 
 #endif 
 
-/**
- *	collect_stats		-	collect stats on a scsi command
- *	@hostdata: adapter 
- *	@cmd: command being issued
- *
- *	Update the statistical data by parsing the command in question
- */
- 
-static void collect_stats(struct NCR5380_hostdata *hostdata, Scsi_Cmnd * cmd) 
-{
-#ifdef NCR5380_STATS
-	switch (cmd->cmnd[0]) {
-	case WRITE:
-	case WRITE_6:
-	case WRITE_10:
-		hostdata->time_write[scmd_id(cmd)] += (jiffies - hostdata->timebase);
-		hostdata->pendingw--;
-		break;
-	case READ:
-	case READ_6:
-	case READ_10:
-		hostdata->time_read[scmd_id(cmd)] += (jiffies - hostdata->timebase);
-		hostdata->pendingr--;
-		break;
-	}
-#endif
-}
-
-
 /* 
  * Function : int NCR5380_select (struct Scsi_Host *instance, Scsi_Cmnd *cmd)
  *
@@ -1464,7 +1404,6 @@ part2:
 			return -1;
 		}
 		cmd->result = DID_BAD_TARGET << 16;
-		collect_stats(hostdata, cmd);
 		cmd->scsi_done(cmd);
 		NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 		dprintk(NDEBUG_SELECTION, "scsi%d : target did not respond within 250ms\n", instance->host_no);
@@ -2216,7 +2155,6 @@ static void NCR5380_information_transfer
 					cmd->next_link->tag = cmd->tag;
 					cmd->result = cmd->SCp.Status | (cmd->SCp.Message << 8);
 					dprintk(NDEBUG_LINKED, "scsi%d : target %d lun %llu linked request done, calling scsi_done().\n", instance->host_no, cmd->device->id, cmd->device->lun);
-					collect_stats(hostdata, cmd);
 					cmd->scsi_done(cmd);
 					cmd = hostdata->connected;
 					break;
@@ -2268,7 +2206,6 @@ static void NCR5380_information_transfer
 						hostdata->issue_queue = (Scsi_Cmnd *) cmd;
 						dprintk(NDEBUG_QUEUES, "scsi%d : REQUEST SENSE added to head of issue queue\n", instance->host_no);
 					} else {
-						collect_stats(hostdata, cmd);
 						cmd->scsi_done(cmd);
 					}
 
@@ -2415,7 +2352,6 @@ static void NCR5380_information_transfer
 					hostdata->busy[cmd->device->id] &= ~(1 << (cmd->device->lun & 0xFF));
 					hostdata->connected = NULL;
 					cmd->result = DID_ERROR << 16;
-					collect_stats(hostdata, cmd);
 					cmd->scsi_done(cmd);
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					return;
drivers/scsi/NCR5380.h +0 -9
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -272,15 +272,6 @@ struct NCR5380_hostdata {
 	int select_time;			/* timer in select for target response */
 	volatile Scsi_Cmnd *selecting;
 	struct delayed_work coroutine;		/* our co-routine */
-#ifdef NCR5380_STATS
-	unsigned timebase;			/* Base for time calcs */
-	long time_read[8];			/* time to do reads */
-	long time_write[8];			/* time to do writes */
-	unsigned long bytes_read[8];		/* bytes read */
-	unsigned long bytes_write[8];		/* bytes written */
-	unsigned pendingr;
-	unsigned pendingw;
-#endif
 	struct scsi_eh_save ses;
 };
 
drivers/scsi/atari_NCR5380.c +0 -65

101 lines not on this page · raw message

drivers/scsi/g_NCR5380.c +0 -45

63 lines not on this page · raw message

drivers/scsi/sun3_NCR5380.c +0 -69

105 lines not on this page · raw message

Reviewed-by on v2 11/36
#20 lore raw

Re: [PATCH v2 11/36] ncr5380: Remove NCR5380_STATS

Quoted 11 lines · Finn Thain

The NCR5380_STATS option is only enabled by g_NCR5380 yet it adds clutter to all three core drivers. The atari_NCR5380.c and sun3_NCR5380.c core drivers have a slightly different implementation of the NCR5380_STATS option.

Out of all ten NCR5380 drivers, only one of them (g_NCR5380) actually has the code to report on the collected stats. Aside from being unreadable, that code seems to be broken because there's no initialization of timebase. sun3_NCR5380.c and atari_NCR5380.c have the timebase initialization but lack the code to report the stats.

Quoted 8 lines

Remove all of this code to improve readability and reduce divergence between the three core drivers.

This patch and the next one completely eliminate the PRINTP and ANDP pre-processor abuse.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
#22 lore raw

PATCH v2 12/36 ncr5380: Cleanup host info() methods

Quoted 8 lines · Finn Thain

If the host->info() method is not set, then host->name is used by default. For atari_scsi, that is exactly the same text. So remove the redundant info() method. Keep sun3_scsi.c in line with atari_scsi.

Some NCR5380 drivers return an empty string from the info() method (arm/cumana_1.c arm/oak.c mac_scsi.c) while other drivers use the default (dmx3191d dtc.c g_NCR5380.c pas16.c t128.c).

Quoted 9 lines

Implement a common info() method to replace a lot of duplicated code which the various drivers use to announce the same information.

This replaces most of the (deprecated) show_info() output and all of the NCR5380_print_info() output. This also eliminates a bunch of code in g_NCR5380 which just duplicates functionality in the core driver.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
hare at suse.de			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: J. Hawn, J. Guild, F. Imend?rffer, HRB 16746 (AG N?rnberg)
#24 lore raw

PATCH v2 13/36 ncr5380: Move static PDMA spin counters to host data

Quoted 6 lines · Finn Thain

Static variables from dtc.c and pas16.c should not appear in the core NCR5380.c driver. Aside from being a layering issue this worsens the divergence between the three core driver variants (atari_NCR5380.c and sun3_NCR5380.c don't support PSEUDO_DMA) and it can mean multiple hosts share the same counters.

Quoted 9 lines

Fix this by making the pseudo DMA spin counters in the core more generic. This also avoids the abuse of the {DTC,PAS16}_PUBLIC_RELEASE macros, so they can be removed.

oak.c doesn't use PDMA and hence it doesn't use the counters and hence it needs no write_info() method. Remove it.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
hare at suse.de			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: J. Hawn, J. Guild, F. Imend?rffer, HRB 16746 (AG N?rnberg)
author
#25 lore raw

PATCH v2 14/36 ncr5380: Remove pointless compiler command line override macros

In reply to Finn Thain

Compile-time override of scsi host defaults is pointless for drivers that provide module parameters and __setup options for that. Too many macros make the code hard to read so remove them.

---
 drivers/scsi/atari_scsi.c |    2 +-
 drivers/scsi/atari_scsi.h |    3 ---
 drivers/scsi/mac_scsi.c   |   19 +++++++++----------
 drivers/scsi/mac_scsi.h   |   16 ----------------
 drivers/scsi/sun3_scsi.c  |   20 ++++++++++----------
 drivers/scsi/sun3_scsi.h  |   18 ------------------
 6 files changed, 20 insertions(+), 58 deletions(-)
drivers/scsi/mac_scsi.c +9 -10
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -177,13 +177,12 @@ int __init macscsi_detect(struct scsi_ho
     if (macintosh_config->scsi_type != MAC_SCSI_OLD)
 	return( 0 );
 
-    /* setup variables */
-    tpnt->can_queue =
-	(setup_can_queue > 0) ? setup_can_queue : CAN_QUEUE;
-    tpnt->cmd_per_lun =
-	(setup_cmd_per_lun > 0) ? setup_cmd_per_lun : CMD_PER_LUN;
-    tpnt->sg_tablesize = 
-	(setup_sg_tablesize >= 0) ? setup_sg_tablesize : SG_TABLESIZE;
+	if (setup_can_queue > 0)
+		tpnt->can_queue = setup_can_queue;
+	if (setup_cmd_per_lun > 0)
+		tpnt->cmd_per_lun = setup_cmd_per_lun;
+	if (setup_sg_tablesize >= 0)
+		tpnt->sg_tablesize = setup_sg_tablesize;
 
     if (setup_hostid >= 0)
 	tpnt->this_id = setup_hostid;
@@ -194,7 +193,7 @@ int __init macscsi_detect(struct scsi_ho
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
-	setup_use_tagged_queuing = USE_TAGGED_QUEUING;
+	setup_use_tagged_queuing = 0;
 #endif
 
     /* Once we support multiple 5380s (e.g. DuoDock) we'll do
@@ -496,10 +495,10 @@ static struct scsi_host_template driver_
 	.queuecommand			= macscsi_queue_command,
 	.eh_abort_handler		= macscsi_abort,
 	.eh_bus_reset_handler		= macscsi_bus_reset,
-	.can_queue			= CAN_QUEUE,
+	.can_queue			= 16,
 	.this_id			= 7,
 	.sg_tablesize			= SG_ALL,
-	.cmd_per_lun			= CMD_PER_LUN,
+	.cmd_per_lun			= 2,
 	.use_clustering			= DISABLE_CLUSTERING
 };
 
drivers/scsi/mac_scsi.h +0 -16
Index: linux/drivers/scsi/mac_scsi.h
===================================================================
@@ -17,22 +17,6 @@
 
 #ifndef ASM
 
-#ifndef CMD_PER_LUN
-#define CMD_PER_LUN 2
-#endif
-
-#ifndef CAN_QUEUE
-#define CAN_QUEUE 16
-#endif
-
-#ifndef SG_TABLESIZE
-#define SG_TABLESIZE SG_NONE
-#endif
-
-#ifndef USE_TAGGED_QUEUING
-#define	USE_TAGGED_QUEUING 0
-#endif
-
 #include <scsi/scsicam.h>
 
 #define NCR5380_implementation_fields /* none */
drivers/scsi/sun3_scsi.c +10 -10
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -198,12 +198,12 @@ static int __init sun3scsi_detect(struct
 #endif
 
 	/* setup variables */
-	tpnt->can_queue =
-		(setup_can_queue > 0) ? setup_can_queue : CAN_QUEUE;
-	tpnt->cmd_per_lun =
-		(setup_cmd_per_lun > 0) ? setup_cmd_per_lun : CMD_PER_LUN;
-	tpnt->sg_tablesize = 
-		(setup_sg_tablesize >= 0) ? setup_sg_tablesize : SG_TABLESIZE;
+	if (setup_can_queue > 0)
+		tpnt->can_queue = setup_can_queue;
+	if (setup_cmd_per_lun > 0)
+		tpnt->cmd_per_lun = setup_cmd_per_lun;
+	if (setup_sg_tablesize >= 0)
+		tpnt->sg_tablesize = setup_sg_tablesize;
 
 	if (setup_hostid >= 0)
 		tpnt->this_id = setup_hostid;
@@ -257,7 +257,7 @@ static int __init sun3scsi_detect(struct
 #endif
 #ifdef SUPPORT_TAGS
 	if (setup_use_tagged_queuing < 0)
-		setup_use_tagged_queuing = USE_TAGGED_QUEUING;
+		setup_use_tagged_queuing = 1;
 #endif
 
 	instance = scsi_register (tpnt, sizeof(struct NCR5380_hostdata));
@@ -683,10 +683,10 @@ static struct scsi_host_template driver_
 	.queuecommand		= sun3scsi_queue_command,
 	.eh_abort_handler      	= sun3scsi_abort,
 	.eh_bus_reset_handler  	= sun3scsi_bus_reset,
-	.can_queue		= CAN_QUEUE,
+	.can_queue		= 16,
 	.this_id		= 7,
-	.sg_tablesize		= SG_TABLESIZE,
-	.cmd_per_lun		= CMD_PER_LUN,
+	.sg_tablesize		= SG_NONE,
+	.cmd_per_lun		= 2,
 	.use_clustering		= DISABLE_CLUSTERING
 };
 
drivers/scsi/sun3_scsi.h +0 -18
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -31,25 +31,7 @@
 
 #define IOBASE_SUN3_VMESCSI 0xff200000
 
-#ifndef CMD_PER_LUN
-#define CMD_PER_LUN 2
-#endif
-
-#ifndef CAN_QUEUE
-#define CAN_QUEUE 16
-#endif
-
-#ifndef SG_TABLESIZE
-#define SG_TABLESIZE SG_NONE
-#endif
-
-#ifndef MAX_TAGS
 #define MAX_TAGS 32
-#endif
-
-#ifndef USE_TAGGED_QUEUING
-#define	USE_TAGGED_QUEUING 1
-#endif
 
 #include <scsi/scsicam.h>
 
drivers/scsi/atari_scsi.c +1 -1
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -611,7 +611,7 @@ static int __init atari_scsi_detect(stru
 
 #ifdef SUPPORT_TAGS
 	if (setup_use_tagged_queuing < 0)
-		setup_use_tagged_queuing = DEFAULT_USE_TAGGED_QUEUING;
+		setup_use_tagged_queuing = 0;
 #endif
 #ifdef REAL_DMA
 	/* If running on a Falcon and if there's TT-Ram (i.e., more than one
drivers/scsi/atari_scsi.h +0 -3
Index: linux/drivers/scsi/atari_scsi.h
===================================================================
@@ -36,9 +36,6 @@
 #define ATARI_FALCON_CMD_PER_LUN	1
 #define ATARI_FALCON_SG_TABLESIZE	SG_NONE
 
-#define	DEFAULT_USE_TAGGED_QUEUING	0
-
-
 #define	NCR5380_implementation_fields	/* none */
 
 #define NCR5380_read(reg)		  atari_scsi_reg_read( reg )
Reviewed-by on v2 14/36
#26 lore raw

Re: [PATCH v2 14/36] ncr5380: Remove pointless compiler command line override macros

Quoted 29 lines · Finn Thain

Compile-time override of scsi host defaults is pointless for drivers that provide module parameters and __setup options for that. Too many macros make the code hard to read so remove them.

---
 drivers/scsi/atari_scsi.c |    2 +-
 drivers/scsi/atari_scsi.h |    3 ---
 drivers/scsi/mac_scsi.c   |   19 +++++++++----------
 drivers/scsi/mac_scsi.h   |   16 ----------------
 drivers/scsi/sun3_scsi.c  |   20 ++++++++++----------
 drivers/scsi/sun3_scsi.h  |   18 ------------------
 6 files changed, 20 insertions(+), 58 deletions(-)

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +0 -6
@@ -177,13 +177,12 @@ int __init macscsi_detect(struct scsi_ho
     if (macintosh_config->scsi_type != MAC_SCSI_OLD)
 	return( 0 );
 
-    /* setup variables */
-    tpnt->can_queue =
-	(setup_can_queue > 0) ? setup_can_queue : CAN_QUEUE;
-    tpnt->cmd_per_lun =
-	(setup_cmd_per_lun > 0) ? setup_cmd_per_lun : CMD_PER_LUN;
-    tpnt->sg_tablesize = 

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 188

Quoted 10 lines
drivers/scsi/mac_scsi.c +6 -1
-	(setup_sg_tablesize >= 0) ? setup_sg_tablesize : SG_TABLESIZE;
+	if (setup_can_queue > 0)
+		tpnt->can_queue = setup_can_queue;
+	if (setup_cmd_per_lun > 0)
+		tpnt->cmd_per_lun = setup_cmd_per_lun;
+	if (setup_sg_tablesize >= 0)
+		tpnt->sg_tablesize = setup_sg_tablesize;
 
     if (setup_hostid >= 0)
 	tpnt->this_id = setup_hostid;

Sigh. Blasted indentation.
Can I convince you to cleanup mac_scsi.c to conform to current coding style after the cleanup is done?

The remainder is okay.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
#28 lore raw

PATCH v2 15/36 ncr5380: Remove *_RELEASE macros

Quoted 6 lines · Finn Thain

The *_RELEASE macros don't tell me anything. In some cases the version in the macro contradicts the version in the comments. Anyway, the Linux kernel version is sufficient information. Remove these macros to improve readability.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
hare at suse.de			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: J. Hawn, J. Guild, F. Imend?rffer, HRB 16746 (AG N?rnberg)
#30 lore raw

PATCH v2 16/36 ncr5380: Drop legacy scsi.h include

Quoted 6 lines · Finn Thain

Convert Scsi_Cmnd to struct scsi_cmnd and drop the #include "scsi.h". The sun3_NCR5380.c core driver already uses struct scsi_cmnd so converting the other core drivers reduces the diff which makes them easier to unify.

Yippie! I was waiting for that to happen.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
hare at suse.de			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: J. Hawn, J. Guild, F. Imend?rffer, HRB 16746 (AG N?rnberg)
author
#31 lore raw

PATCH v2 17/36 dmx3191d: Use NO_IRQ

In reply to Finn Thain

Testing shows that the Domex 3191D card never asserts its IRQ. Hence it is non-functional with Linux (worse, the EH bugs in the core driver are fatal but that's a problem for another patch). Perhaps the DT-536 chip needs special setup? I can't find documentation for it. The NetBSD driver uses polling apparently because of this issue.

Set host->irq = NO_IRQ so the core driver will prevent targets from disconnecting. Don't request host->irq.

---

Changes since v1:
- Use NO_IRQ instead of IRQ_NONE.

---
 drivers/scsi/dmx3191d.c |   25 ++++++++-----------------
 1 file changed, 8 insertions(+), 17 deletions(-)
drivers/scsi/dmx3191d.c +8 -17
Index: linux/drivers/scsi/dmx3191d.c
===================================================================
@@ -34,6 +34,8 @@
  * Definitions for the generic 5380 driver.
  */
 
+#define DONT_USE_INTR
+
 #define NCR5380_read(reg)		inb(port + reg)
 #define NCR5380_write(reg, value)	outb(value, port + reg)
 
@@ -89,32 +91,23 @@ static int dmx3191d_probe_one(struct pci
 	if (!shost)
 		goto out_release_region;       
 	shost->io_port = io;
-	shost->irq = pdev->irq;
 
-	NCR5380_init(shost, FLAG_NO_PSEUDO_DMA | FLAG_DTC3181E);
+	/* This card does not seem to raise an interrupt on pdev->irq.
+	 * Steam-powered SCSI controllers run without an IRQ anyway.
+	 */
+	shost->irq = NO_IRQ;
 
-	if (request_irq(pdev->irq, NCR5380_intr, IRQF_SHARED,
-				DMX3191D_DRIVER_NAME, shost)) {
-		/*
-		 * Steam powered scsi controllers run without an IRQ anyway
-		 */
-		printk(KERN_WARNING "dmx3191: IRQ %d not available - "
-				    "switching to polled mode.\n", pdev->irq);
-		shost->irq = NO_IRQ;
-	}
+	NCR5380_init(shost, FLAG_NO_PSEUDO_DMA | FLAG_DTC3181E);
 
 	pci_set_drvdata(pdev, shost);
 
 	error = scsi_add_host(shost, &pdev->dev);
 	if (error)
-		goto out_free_irq;
+		goto out_release_region;
 
 	scsi_scan_host(shost);
 	return 0;
 
- out_free_irq:
-	if (shost->irq != NO_IRQ)
-		free_irq(shost->irq, shost);
  out_release_region:
 	release_region(io, DMX3191D_REGION_LEN);
  out_disable_device:
@@ -131,8 +124,6 @@ static void dmx3191d_remove_one(struct p
 
 	NCR5380_exit(shost);
 
-	if (shost->irq != NO_IRQ)
-		free_irq(shost->irq, shost);
 	release_region(shost->io_port, DMX3191D_REGION_LEN);
 	pci_disable_device(pdev);
 
Reviewed-by on v2 17/36
#32 lore raw

Re: [PATCH v2 17/36] dmx3191d: Use NO_IRQ

Quoted 11 lines · Finn Thain

Testing shows that the Domex 3191D card never asserts its IRQ. Hence it is non-functional with Linux (worse, the EH bugs in the core driver are fatal but that's a problem for another patch). Perhaps the DT-536 chip needs special setup? I can't find documentation for it. The NetBSD driver uses polling apparently because of this issue.

Set host->irq = NO_IRQ so the core driver will prevent targets from disconnecting. Don't request host->irq.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#33 lore raw

PATCH v2 18/36 mac_scsi: Remove header

In reply to Finn Thain

The #defines in mac_scsi.h are intended to influence subsequent #includes in mac_scsi.c. IMHO, that's too convoluted.

Remove mac_scsi.h by moving those macro definitions to mac_scsi.c, consistent with other NCR5380 drivers.

---
 drivers/scsi/mac_scsi.c |   21 ++++++++++++++++++++-
 drivers/scsi/mac_scsi.h |   42 ------------------------------------------
 2 files changed, 20 insertions(+), 43 deletions(-)
drivers/scsi/mac_scsi.c +20 -1
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -31,10 +31,29 @@
 #include <asm/mac_via.h>
 
 #include <scsi/scsi_host.h>
-#include "mac_scsi.h"
+
+/* Definitions for the core NCR5380 driver. */
 
 #define PSEUDO_DMA
 
+#define NCR5380_implementation_fields   /* none */
+#define NCR5380_local_declare()         struct Scsi_Host *_instance
+#define NCR5380_setup(instance)         _instance = instance
+
+#define NCR5380_read(reg)               macscsi_read(_instance, reg)
+#define NCR5380_write(reg, value)       macscsi_write(_instance, reg, value)
+
+#define NCR5380_pread                   macscsi_pread
+#define NCR5380_pwrite                  macscsi_pwrite
+
+#define NCR5380_intr                    macscsi_intr
+#define NCR5380_queue_command           macscsi_queue_command
+#define NCR5380_abort                   macscsi_abort
+#define NCR5380_bus_reset               macscsi_bus_reset
+#define NCR5380_info                    macscsi_info
+#define NCR5380_show_info               macscsi_show_info
+#define NCR5380_write_info              macscsi_write_info
+
 #include "NCR5380.h"
 
 #define RESET_BOOT
drivers/scsi/mac_scsi.h deleted +0 -42

42 lines not on this page · raw message

Reviewed-by on v2 18/36
#34 lore raw

Re: [PATCH v2 18/36] mac_scsi: Remove header

Quoted 8 lines · Finn Thain

The #defines in mac_scsi.h are intended to influence subsequent #includes in mac_scsi.c. IMHO, that's too convoluted.

Remove mac_scsi.h by moving those macro definitions to mac_scsi.c, consistent with other NCR5380 drivers.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#35 lore raw

PATCH v2 19/36 mac_scsi: Add module option to Kconfig

In reply to Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)
drivers/scsi/Kconfig +1 -1
Index: linux/drivers/scsi/Kconfig
===================================================================
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help
drivers/scsi/mac_scsi.c +37 -75

155 lines not on this page · raw message

#36 lore raw

Re: [PATCH v2 19/36] mac_scsi: Add module option to Kconfig

Quoted 171 lines · Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)

Index: linux/drivers/scsi/Kconfig
===================================================================

drivers/scsi/Kconfig +1 -1
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +32 -72
@@ -62,15 +62,18 @@
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
 
-static int setup_called = 0;
 static int setup_can_queue = -1;
+module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
+module_param(setup_cmd_per_lun, int, 0);
 static int setup_sg_tablesize = -1;
+module_param(setup_sg_tablesize, int, 0);
 static int setup_use_pdma = -1;
-#ifdef SUPPORT_TAGS
+module_param(setup_use_pdma, int, 0);
 static int setup_use_tagged_queuing = -1;
-#endif
+module_param(setup_use_tagged_queuing, int, 0);
 static int setup_hostid = -1;
+module_param(setup_hostid, int, 0);
 
 /* Time (in jiffies) to wait after a reset; the SCSI standard calls for 250ms,
  * we usually do 0.5s to be on the safe side. But Toshiba CD-ROMs once more
@@ -102,72 +105,34 @@ static __inline__ void macscsi_write(str
   out_8(instance->io_port + (reg<<4), value);
 }
 
-/*
- * Function : mac_scsi_setup(char *str)
- *
- * Purpose : booter command line initialization of the overrides array,
- *
- * Inputs : str - comma delimited list of options
- *
- */
-
-static int __init mac_scsi_setup(char *str) {
+#ifndef MODULE
+static int __init mac_scsi_setup(char *str)
+{
 	int ints[7];
-	
-	(void)get_options( str, ARRAY_SIZE(ints), ints);
-	
-	if (setup_called++ || ints[0] < 1 || ints[0] > 6) {
-	    printk(KERN_WARNING "scsi: <mac5380>"
-		" Usage: mac5380=<can_queue>[,<cmd_per_lun>,<sg_tablesize>,<hostid>,<use_tags>,<use_pdma>]\n");
-	    printk(KERN_ALERT "scsi: <mac5380> Bad Penguin parameters?\n");
-	    return 0;
-	}
-	    
-	if (ints[0] >= 1) {
-		if (ints[1] > 0)
-			/* no limits on this, just > 0 */
-			setup_can_queue = ints[1];
-	}
-	if (ints[0] >= 2) {
-		if (ints[2] > 0)
-			setup_cmd_per_lun = ints[2];
-	}
-	if (ints[0] >= 3) {
-		if (ints[3] >= 0) {
-			setup_sg_tablesize = ints[3];
-			/* Must be <= SG_ALL (255) */
-			if (setup_sg_tablesize > SG_ALL)
-				setup_sg_tablesize = SG_ALL;
-		}
-	}
-	if (ints[0] >= 4) {
-		/* Must be between 0 and 7 */
-		if (ints[4] >= 0 && ints[4] <= 7)
-			setup_hostid = ints[4];
-		else if (ints[4] > 7)
-			printk(KERN_WARNING "mac_scsi_setup: invalid host ID %d !\n", ints[4] );
-	}
-#ifdef SUPPORT_TAGS	
-	if (ints[0] >= 5) {
-		if (ints[5] >= 0)
-			setup_use_tagged_queuing = !!ints[5];
+
+	(void)get_options(str, ARRAY_SIZE(ints), ints);
+
+	if (ints[0] < 1 || ints[0] > 6) {
+		pr_err("Usage: mac5380=<can_queue>[,<cmd_per_lun>[,<sg_tablesize>[,<hostid>[,<use_tags>[,<use_pdma>]]]]]\n");
+		return 0;
 	}
-	
-	if (ints[0] == 6) {
-	    if (ints[6] >= 0)
+	if (ints[0] >= 1)
+		setup_can_queue = ints[1];
+	if (ints[0] >= 2)
+		setup_cmd_per_lun = ints[2];
+	if (ints[0] >= 3)
+		setup_sg_tablesize = ints[3];
+	if (ints[0] >= 4)
+		setup_hostid = ints[4];
+	if (ints[0] >= 5)
+		setup_use_tagged_queuing = ints[5];
+	if (ints[0] >= 6)
 		setup_use_pdma = ints[6];
-	}
-#else
-	if (ints[0] == 5) {
-	    if (ints[5] >= 0)
-		setup_use_pdma = ints[5];
-	}
-#endif /* SUPPORT_TAGS */
-	
 	return 1;
 }
 
 __setup("mac5380=", mac_scsi_setup);
+#endif /* !MODULE */
 
 /*
  * Function : int macscsi_detect(struct scsi_host_template * tpnt)
@@ -199,13 +164,8 @@ int __init macscsi_detect(struct scsi_ho
 		tpnt->cmd_per_lun = setup_cmd_per_lun;
 	if (setup_sg_tablesize >= 0)
 		tpnt->sg_tablesize = setup_sg_tablesize;
-
-    if (setup_hostid >= 0)
-	tpnt->this_id = setup_hostid;
-    else {
-	/* use 7 as default */
-	tpnt->this_id = 7;
-    }
+	if (setup_hostid >= 0)
+		tpnt->this_id = setup_hostid & 7;
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
@@ -219,15 +179,15 @@ int __init macscsi_detect(struct scsi_ho
 	return 0;
 
     if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = via1+0x8000;
-	mac_scsi_drq   = via1+0xE000;
-	mac_scsi_nodrq = via1+0xC000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
 	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
 	flags = FLAG_NO_PSEUDO_DMA;

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 193

Quoted 10 lines
drivers/scsi/mac_scsi.c +3 -3
     } else {
-	mac_scsi_regp  = via1+0x10000;
-	mac_scsi_drq   = via1+0x6000;
-	mac_scsi_nodrq = via1+0x12000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
     }
 
     if (! setup_use_pdma)

Hmm. mac_via.h has this:

/*
* Base addresses for the VIAs. There are two in every machine,
* although on some machines the second is an RBV or an OSS.
* The OSS is different enough that it's handled separately. *
* Do not use these values directly; use the via1 and via2 variables
* instead (and don't forget to check rbv_present when using via2!) */

#define VIA1_BASE (0x50F00000)
#define VIA2_BASE (0x50F02000)
#define RBV_BASE (0x50F26000)

So either that comment is obsolete or you should revert the above bit ...

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#37 lore raw

Re: [PATCH v2 19/36] mac_scsi: Add module option to Kconfig

Quoted 194 lines · Hannes Reinecke
Quoted 172 lines · Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)

Index: linux/drivers/scsi/Kconfig
===================================================================

drivers/scsi/Kconfig +1 -1
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +32 -72
@@ -62,15 +62,18 @@
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
 
-static int setup_called = 0;
 static int setup_can_queue = -1;
+module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
+module_param(setup_cmd_per_lun, int, 0);
 static int setup_sg_tablesize = -1;
+module_param(setup_sg_tablesize, int, 0);
 static int setup_use_pdma = -1;
-#ifdef SUPPORT_TAGS
+module_param(setup_use_pdma, int, 0);
 static int setup_use_tagged_queuing = -1;
-#endif
+module_param(setup_use_tagged_queuing, int, 0);
 static int setup_hostid = -1;
+module_param(setup_hostid, int, 0);
 
 /* Time (in jiffies) to wait after a reset; the SCSI standard calls for 250ms,
  * we usually do 0.5s to be on the safe side. But Toshiba CD-ROMs once more
@@ -102,72 +105,34 @@ static __inline__ void macscsi_write(str
   out_8(instance->io_port + (reg<<4), value);
 }
 
-/*
- * Function : mac_scsi_setup(char *str)
- *
- * Purpose : booter command line initialization of the overrides array,
- *
- * Inputs : str - comma delimited list of options
- *
- */
-
-static int __init mac_scsi_setup(char *str) {
+#ifndef MODULE
+static int __init mac_scsi_setup(char *str)
+{
 	int ints[7];
-	
-	(void)get_options( str, ARRAY_SIZE(ints), ints);
-	
-	if (setup_called++ || ints[0] < 1 || ints[0] > 6) {
-	    printk(KERN_WARNING "scsi: <mac5380>"
-		" Usage: mac5380=<can_queue>[,<cmd_per_lun>,<sg_tablesize>,<hostid>,<use_tags>,<use_pdma>]\n");
-	    printk(KERN_ALERT "scsi: <mac5380> Bad Penguin parameters?\n");
-	    return 0;
-	}
-	    
-	if (ints[0] >= 1) {
-		if (ints[1] > 0)
-			/* no limits on this, just > 0 */
-			setup_can_queue = ints[1];
-	}
-	if (ints[0] >= 2) {
-		if (ints[2] > 0)
-			setup_cmd_per_lun = ints[2];
-	}
-	if (ints[0] >= 3) {
-		if (ints[3] >= 0) {
-			setup_sg_tablesize = ints[3];
-			/* Must be <= SG_ALL (255) */
-			if (setup_sg_tablesize > SG_ALL)
-				setup_sg_tablesize = SG_ALL;
-		}
-	}
-	if (ints[0] >= 4) {
-		/* Must be between 0 and 7 */
-		if (ints[4] >= 0 && ints[4] <= 7)
-			setup_hostid = ints[4];
-		else if (ints[4] > 7)
-			printk(KERN_WARNING "mac_scsi_setup: invalid host ID %d !\n", ints[4] );
-	}
-#ifdef SUPPORT_TAGS	
-	if (ints[0] >= 5) {
-		if (ints[5] >= 0)
-			setup_use_tagged_queuing = !!ints[5];
+
+	(void)get_options(str, ARRAY_SIZE(ints), ints);
+
+	if (ints[0] < 1 || ints[0] > 6) {
+		pr_err("Usage: mac5380=<can_queue>[,<cmd_per_lun>[,<sg_tablesize>[,<hostid>[,<use_tags>[,<use_pdma>]]]]]\n");
+		return 0;
 	}
-	
-	if (ints[0] == 6) {
-	    if (ints[6] >= 0)
+	if (ints[0] >= 1)
+		setup_can_queue = ints[1];
+	if (ints[0] >= 2)
+		setup_cmd_per_lun = ints[2];
+	if (ints[0] >= 3)
+		setup_sg_tablesize = ints[3];
+	if (ints[0] >= 4)
+		setup_hostid = ints[4];
+	if (ints[0] >= 5)
+		setup_use_tagged_queuing = ints[5];
+	if (ints[0] >= 6)
 		setup_use_pdma = ints[6];
-	}
-#else
-	if (ints[0] == 5) {
-	    if (ints[5] >= 0)
-		setup_use_pdma = ints[5];
-	}
-#endif /* SUPPORT_TAGS */
-	
 	return 1;
 }
 
 __setup("mac5380=", mac_scsi_setup);
+#endif /* !MODULE */
 
 /*
  * Function : int macscsi_detect(struct scsi_host_template * tpnt)
@@ -199,13 +164,8 @@ int __init macscsi_detect(struct scsi_ho
 		tpnt->cmd_per_lun = setup_cmd_per_lun;
 	if (setup_sg_tablesize >= 0)
 		tpnt->sg_tablesize = setup_sg_tablesize;
-
-    if (setup_hostid >= 0)
-	tpnt->this_id = setup_hostid;
-    else {
-	/* use 7 as default */
-	tpnt->this_id = 7;
-    }
+	if (setup_hostid >= 0)
+		tpnt->this_id = setup_hostid & 7;
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
@@ -219,15 +179,15 @@ int __init macscsi_detect(struct scsi_ho
 	return 0;
 
     if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = via1+0x8000;
-	mac_scsi_drq   = via1+0xE000;
-	mac_scsi_nodrq = via1+0xC000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
 	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
 	flags = FLAG_NO_PSEUDO_DMA;

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 193

Quoted 10 lines
drivers/scsi/mac_scsi.c +3 -3
     } else {
-	mac_scsi_regp  = via1+0x10000;
-	mac_scsi_drq   = via1+0x6000;
-	mac_scsi_nodrq = via1+0x12000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
     }
 
     if (! setup_use_pdma)

Hmm. mac_via.h has this:

/*
* Base addresses for the VIAs. There are two in every machine,
* although on some machines the second is an RBV or an OSS.
* The OSS is different enough that it's handled separately. *
* Do not use these values directly; use the via1 and via2 variables
* instead (and don't forget to check rbv_present when using via2!) */

Quoted 6 lines

#define VIA1_BASE (0x50F00000)
#define VIA2_BASE (0x50F02000)
#define RBV_BASE (0x50F26000)

So either that comment is obsolete or you should revert the above bit ...

Use of via1 had to be changed because that symbol is not exported.

The comment you quoted is probably not wrong; it relates to programming the VIA chip itself (see ADB drivers for example). But in this driver we aren't interested in the VIA1 chip so I'd say niether via1 or VIA1_BASE is good style. Hence my use of bare addresses in the platform resource initializers in patch 21.

This example of VIA1_BASE + offset disappears in patch 21 (you can find an unrelated example in arch/m68k/mac/config.c but that was not my doing).

This patch is not meant to change the actual addresses used by mac_scsi; it just makes the driver modular. Use of VIA1_BASE seemed like a good way to express the fact that the addresses are not changed yet (some models use new addresses after patch 21).

Basically, I just wanted a modular driver for debugging and bisection and I wanted it early in the patch series. A modular mac_scsi.c aligns better with atari_scsi.c and sun3_scsi.c as they are already modular. That means that the three subsequent patches which convert {atari,mac,sun3}_scsi.c to platform drivers also align nicely (so I could cross check them).

#38 lore raw

Re: [PATCH v2 19/36] mac_scsi: Add module option to Kconfig

Quoted 220 lines · Finn Thain
Quoted 194 lines · Hannes Reinecke
Quoted 172 lines · Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)

Index: linux/drivers/scsi/Kconfig
===================================================================

drivers/scsi/Kconfig +1 -1
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +32 -72
@@ -62,15 +62,18 @@
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
 
-static int setup_called = 0;
 static int setup_can_queue = -1;
+module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
+module_param(setup_cmd_per_lun, int, 0);
 static int setup_sg_tablesize = -1;
+module_param(setup_sg_tablesize, int, 0);
 static int setup_use_pdma = -1;
-#ifdef SUPPORT_TAGS
+module_param(setup_use_pdma, int, 0);
 static int setup_use_tagged_queuing = -1;
-#endif
+module_param(setup_use_tagged_queuing, int, 0);
 static int setup_hostid = -1;
+module_param(setup_hostid, int, 0);
 
 /* Time (in jiffies) to wait after a reset; the SCSI standard calls for 250ms,
  * we usually do 0.5s to be on the safe side. But Toshiba CD-ROMs once more
@@ -102,72 +105,34 @@ static __inline__ void macscsi_write(str
   out_8(instance->io_port + (reg<<4), value);
 }
 
-/*
- * Function : mac_scsi_setup(char *str)
- *
- * Purpose : booter command line initialization of the overrides array,
- *
- * Inputs : str - comma delimited list of options
- *
- */
-
-static int __init mac_scsi_setup(char *str) {
+#ifndef MODULE
+static int __init mac_scsi_setup(char *str)
+{
 	int ints[7];
-	
-	(void)get_options( str, ARRAY_SIZE(ints), ints);
-	
-	if (setup_called++ || ints[0] < 1 || ints[0] > 6) {
-	    printk(KERN_WARNING "scsi: <mac5380>"
-		" Usage: mac5380=<can_queue>[,<cmd_per_lun>,<sg_tablesize>,<hostid>,<use_tags>,<use_pdma>]\n");
-	    printk(KERN_ALERT "scsi: <mac5380> Bad Penguin parameters?\n");
-	    return 0;
-	}
-	    
-	if (ints[0] >= 1) {
-		if (ints[1] > 0)
-			/* no limits on this, just > 0 */
-			setup_can_queue = ints[1];
-	}
-	if (ints[0] >= 2) {
-		if (ints[2] > 0)
-			setup_cmd_per_lun = ints[2];
-	}
-	if (ints[0] >= 3) {
-		if (ints[3] >= 0) {
-			setup_sg_tablesize = ints[3];
-			/* Must be <= SG_ALL (255) */
-			if (setup_sg_tablesize > SG_ALL)
-				setup_sg_tablesize = SG_ALL;
-		}
-	}
-	if (ints[0] >= 4) {
-		/* Must be between 0 and 7 */
-		if (ints[4] >= 0 && ints[4] <= 7)
-			setup_hostid = ints[4];
-		else if (ints[4] > 7)
-			printk(KERN_WARNING "mac_scsi_setup: invalid host ID %d !\n", ints[4] );
-	}
-#ifdef SUPPORT_TAGS	
-	if (ints[0] >= 5) {
-		if (ints[5] >= 0)
-			setup_use_tagged_queuing = !!ints[5];
+
+	(void)get_options(str, ARRAY_SIZE(ints), ints);
+
+	if (ints[0] < 1 || ints[0] > 6) {
+		pr_err("Usage: mac5380=<can_queue>[,<cmd_per_lun>[,<sg_tablesize>[,<hostid>[,<use_tags>[,<use_pdma>]]]]]\n");
+		return 0;
 	}
-	
-	if (ints[0] == 6) {
-	    if (ints[6] >= 0)
+	if (ints[0] >= 1)
+		setup_can_queue = ints[1];
+	if (ints[0] >= 2)
+		setup_cmd_per_lun = ints[2];
+	if (ints[0] >= 3)
+		setup_sg_tablesize = ints[3];
+	if (ints[0] >= 4)
+		setup_hostid = ints[4];
+	if (ints[0] >= 5)
+		setup_use_tagged_queuing = ints[5];
+	if (ints[0] >= 6)
 		setup_use_pdma = ints[6];
-	}
-#else
-	if (ints[0] == 5) {
-	    if (ints[5] >= 0)
-		setup_use_pdma = ints[5];
-	}
-#endif /* SUPPORT_TAGS */
-	
 	return 1;
 }
 
 __setup("mac5380=", mac_scsi_setup);
+#endif /* !MODULE */
 
 /*
  * Function : int macscsi_detect(struct scsi_host_template * tpnt)
@@ -199,13 +164,8 @@ int __init macscsi_detect(struct scsi_ho
 		tpnt->cmd_per_lun = setup_cmd_per_lun;
 	if (setup_sg_tablesize >= 0)
 		tpnt->sg_tablesize = setup_sg_tablesize;
-
-    if (setup_hostid >= 0)
-	tpnt->this_id = setup_hostid;
-    else {
-	/* use 7 as default */
-	tpnt->this_id = 7;
-    }
+	if (setup_hostid >= 0)
+		tpnt->this_id = setup_hostid & 7;
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
@@ -219,15 +179,15 @@ int __init macscsi_detect(struct scsi_ho
 	return 0;
 
     if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = via1+0x8000;
-	mac_scsi_drq   = via1+0xE000;
-	mac_scsi_nodrq = via1+0xC000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
 	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
 	flags = FLAG_NO_PSEUDO_DMA;

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 193

Quoted 10 lines
drivers/scsi/mac_scsi.c +3 -3
     } else {
-	mac_scsi_regp  = via1+0x10000;
-	mac_scsi_drq   = via1+0x6000;
-	mac_scsi_nodrq = via1+0x12000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
     }
 
     if (! setup_use_pdma)

Hmm. mac_via.h has this:

/*
* Base addresses for the VIAs. There are two in every machine,
* although on some machines the second is an RBV or an OSS.
* The OSS is different enough that it's handled separately. *
* Do not use these values directly; use the via1 and via2 variables
* instead (and don't forget to check rbv_present when using via2!) */

Quoted 6 lines

#define VIA1_BASE (0x50F00000)
#define VIA2_BASE (0x50F02000)
#define RBV_BASE (0x50F26000)

So either that comment is obsolete or you should revert the above bit ...

Use of via1 had to be changed because that symbol is not exported.

The comment you quoted is probably not wrong; it relates to programming the VIA chip itself (see ADB drivers for example). But in this driver we aren't interested in the VIA1 chip so I'd say niether via1 or VIA1_BASE is good style. Hence my use of bare addresses in the platform resource initializers in patch 21.

This example of VIA1_BASE + offset disappears in patch 21 (you can find an unrelated example in arch/m68k/mac/config.c but that was not my doing).

This patch is not meant to change the actual addresses used by mac_scsi; it just makes the driver modular. Use of VIA1_BASE seemed like a good way to express the fact that the addresses are not changed yet (some models use new addresses after patch 21).

Quoted 6 lines

Basically, I just wanted a modular driver for debugging and bisection and I wanted it early in the patch series. A modular mac_scsi.c aligns better with atari_scsi.c and sun3_scsi.c as they are already modular. That means that the three subsequent patches which convert {atari,mac,sun3}_scsi.c to platform drivers also align nicely (so I could cross check them).

Fair enough.

Just needed some clarification here. My Mac experience ceased with a IIcx :-)

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#39 lore raw

Re: [PATCH v2 19/36] mac_scsi: Add module option to Kconfig

Quoted 227 lines · Hannes Reinecke
Quoted 220 lines · Finn Thain
Quoted 194 lines · Hannes Reinecke
Quoted 172 lines · Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)

Index: linux/drivers/scsi/Kconfig
===================================================================

drivers/scsi/Kconfig +1 -1
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +32 -72
@@ -62,15 +62,18 @@
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
 
-static int setup_called = 0;
 static int setup_can_queue = -1;
+module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
+module_param(setup_cmd_per_lun, int, 0);
 static int setup_sg_tablesize = -1;
+module_param(setup_sg_tablesize, int, 0);
 static int setup_use_pdma = -1;
-#ifdef SUPPORT_TAGS
+module_param(setup_use_pdma, int, 0);
 static int setup_use_tagged_queuing = -1;
-#endif
+module_param(setup_use_tagged_queuing, int, 0);
 static int setup_hostid = -1;
+module_param(setup_hostid, int, 0);
 
 /* Time (in jiffies) to wait after a reset; the SCSI standard calls for 250ms,
  * we usually do 0.5s to be on the safe side. But Toshiba CD-ROMs once more
@@ -102,72 +105,34 @@ static __inline__ void macscsi_write(str
   out_8(instance->io_port + (reg<<4), value);
 }
 
-/*
- * Function : mac_scsi_setup(char *str)
- *
- * Purpose : booter command line initialization of the overrides array,
- *
- * Inputs : str - comma delimited list of options
- *
- */
-
-static int __init mac_scsi_setup(char *str) {
+#ifndef MODULE
+static int __init mac_scsi_setup(char *str)
+{
 	int ints[7];
-	
-	(void)get_options( str, ARRAY_SIZE(ints), ints);
-	
-	if (setup_called++ || ints[0] < 1 || ints[0] > 6) {
-	    printk(KERN_WARNING "scsi: <mac5380>"
-		" Usage: mac5380=<can_queue>[,<cmd_per_lun>,<sg_tablesize>,<hostid>,<use_tags>,<use_pdma>]\n");
-	    printk(KERN_ALERT "scsi: <mac5380> Bad Penguin parameters?\n");
-	    return 0;
-	}
-	    
-	if (ints[0] >= 1) {
-		if (ints[1] > 0)
-			/* no limits on this, just > 0 */
-			setup_can_queue = ints[1];
-	}
-	if (ints[0] >= 2) {
-		if (ints[2] > 0)
-			setup_cmd_per_lun = ints[2];
-	}
-	if (ints[0] >= 3) {
-		if (ints[3] >= 0) {
-			setup_sg_tablesize = ints[3];
-			/* Must be <= SG_ALL (255) */
-			if (setup_sg_tablesize > SG_ALL)
-				setup_sg_tablesize = SG_ALL;
-		}
-	}
-	if (ints[0] >= 4) {
-		/* Must be between 0 and 7 */
-		if (ints[4] >= 0 && ints[4] <= 7)
-			setup_hostid = ints[4];
-		else if (ints[4] > 7)
-			printk(KERN_WARNING "mac_scsi_setup: invalid host ID %d !\n", ints[4] );
-	}
-#ifdef SUPPORT_TAGS	
-	if (ints[0] >= 5) {
-		if (ints[5] >= 0)
-			setup_use_tagged_queuing = !!ints[5];
+
+	(void)get_options(str, ARRAY_SIZE(ints), ints);
+
+	if (ints[0] < 1 || ints[0] > 6) {
+		pr_err("Usage: mac5380=<can_queue>[,<cmd_per_lun>[,<sg_tablesize>[,<hostid>[,<use_tags>[,<use_pdma>]]]]]\n");
+		return 0;
 	}
-	
-	if (ints[0] == 6) {
-	    if (ints[6] >= 0)
+	if (ints[0] >= 1)
+		setup_can_queue = ints[1];
+	if (ints[0] >= 2)
+		setup_cmd_per_lun = ints[2];
+	if (ints[0] >= 3)
+		setup_sg_tablesize = ints[3];
+	if (ints[0] >= 4)
+		setup_hostid = ints[4];
+	if (ints[0] >= 5)
+		setup_use_tagged_queuing = ints[5];
+	if (ints[0] >= 6)
 		setup_use_pdma = ints[6];
-	}
-#else
-	if (ints[0] == 5) {
-	    if (ints[5] >= 0)
-		setup_use_pdma = ints[5];
-	}
-#endif /* SUPPORT_TAGS */
-	
 	return 1;
 }
 
 __setup("mac5380=", mac_scsi_setup);
+#endif /* !MODULE */
 
 /*
  * Function : int macscsi_detect(struct scsi_host_template * tpnt)
@@ -199,13 +164,8 @@ int __init macscsi_detect(struct scsi_ho
 		tpnt->cmd_per_lun = setup_cmd_per_lun;
 	if (setup_sg_tablesize >= 0)
 		tpnt->sg_tablesize = setup_sg_tablesize;
-
-    if (setup_hostid >= 0)
-	tpnt->this_id = setup_hostid;
-    else {
-	/* use 7 as default */
-	tpnt->this_id = 7;
-    }
+	if (setup_hostid >= 0)
+		tpnt->this_id = setup_hostid & 7;
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
@@ -219,15 +179,15 @@ int __init macscsi_detect(struct scsi_ho
 	return 0;
 
     if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = via1+0x8000;
-	mac_scsi_drq   = via1+0xE000;
-	mac_scsi_nodrq = via1+0xC000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
 	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
 	flags = FLAG_NO_PSEUDO_DMA;

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 193

Quoted 10 lines
drivers/scsi/mac_scsi.c +3 -3
     } else {
-	mac_scsi_regp  = via1+0x10000;
-	mac_scsi_drq   = via1+0x6000;
-	mac_scsi_nodrq = via1+0x12000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
     }
 
     if (! setup_use_pdma)

Hmm. mac_via.h has this:

/*
* Base addresses for the VIAs. There are two in every machine,
* although on some machines the second is an RBV or an OSS.
* The OSS is different enough that it's handled separately. *
* Do not use these values directly; use the via1 and via2 variables
* instead (and don't forget to check rbv_present when using via2!) */

Quoted 6 lines

#define VIA1_BASE (0x50F00000)
#define VIA2_BASE (0x50F02000)
#define RBV_BASE (0x50F26000)

So either that comment is obsolete or you should revert the above bit ...

Use of via1 had to be changed because that symbol is not exported.

The comment you quoted is probably not wrong; it relates to programming the VIA chip itself (see ADB drivers for example). But in this driver we aren't interested in the VIA1 chip so I'd say niether via1 or VIA1_BASE is good style. Hence my use of bare addresses in the platform resource initializers in patch 21.

This example of VIA1_BASE + offset disappears in patch 21 (you can find an unrelated example in arch/m68k/mac/config.c but that was not my doing).

This patch is not meant to change the actual addresses used by mac_scsi; it just makes the driver modular. Use of VIA1_BASE seemed like a good way to express the fact that the addresses are not changed yet (some models use new addresses after patch 21).

Quoted 6 lines

Basically, I just wanted a modular driver for debugging and bisection and I wanted it early in the patch series. A modular mac_scsi.c aligns better with atari_scsi.c and sun3_scsi.c as they are already modular. That means that the three subsequent patches which convert {atari,mac,sun3}_scsi.c to platform drivers also align nicely (so I could cross check them).

Quoted 4 lines

Fair enough.

Just needed some clarification here. My Mac experience ceased with a IIcx :-)

Hannes, can I get a reviewed-by tag for this patch please?

Reviewed-by
#40 lore raw

Re: [PATCH v2 19/36] mac_scsi: Add module option to Kconfig

Quoted 230 lines · Finn Thain
Quoted 227 lines · Hannes Reinecke
Quoted 226 lines · Finn Thain
Quoted 194 lines · Hannes Reinecke
Quoted 172 lines · Finn Thain

Allow mac_scsi to be built as a module. Replace the old validation of __setup options with code that validates both module and __setup options.

---
 drivers/scsi/Kconfig    |    2 
 drivers/scsi/mac_scsi.c |  112 +++++++++++++++---------------------------------
 2 files changed, 38 insertions(+), 76 deletions(-)

Index: linux/drivers/scsi/Kconfig
===================================================================

drivers/scsi/Kconfig +1 -1
@@ -1595,7 +1595,7 @@ config ATARI_SCSI_RESET_BOOT
 	  that leave the devices with SCSI operations partway completed.
 
 config MAC_SCSI
-	bool "Macintosh NCR5380 SCSI"
+	tristate "Macintosh NCR5380 SCSI"
 	depends on MAC && SCSI=y
 	select SCSI_SPI_ATTRS
 	help

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +32 -72
@@ -62,15 +62,18 @@
 static void mac_scsi_reset_boot(struct Scsi_Host *instance);
 #endif
 
-static int setup_called = 0;
 static int setup_can_queue = -1;
+module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
+module_param(setup_cmd_per_lun, int, 0);
 static int setup_sg_tablesize = -1;
+module_param(setup_sg_tablesize, int, 0);
 static int setup_use_pdma = -1;
-#ifdef SUPPORT_TAGS
+module_param(setup_use_pdma, int, 0);
 static int setup_use_tagged_queuing = -1;
-#endif
+module_param(setup_use_tagged_queuing, int, 0);
 static int setup_hostid = -1;
+module_param(setup_hostid, int, 0);
 
 /* Time (in jiffies) to wait after a reset; the SCSI standard calls for 250ms,
  * we usually do 0.5s to be on the safe side. But Toshiba CD-ROMs once more
@@ -102,72 +105,34 @@ static __inline__ void macscsi_write(str
   out_8(instance->io_port + (reg<<4), value);
 }
 
-/*
- * Function : mac_scsi_setup(char *str)
- *
- * Purpose : booter command line initialization of the overrides array,
- *
- * Inputs : str - comma delimited list of options
- *
- */
-
-static int __init mac_scsi_setup(char *str) {
+#ifndef MODULE
+static int __init mac_scsi_setup(char *str)
+{
 	int ints[7];
-	
-	(void)get_options( str, ARRAY_SIZE(ints), ints);
-	
-	if (setup_called++ || ints[0] < 1 || ints[0] > 6) {
-	    printk(KERN_WARNING "scsi: <mac5380>"
-		" Usage: mac5380=<can_queue>[,<cmd_per_lun>,<sg_tablesize>,<hostid>,<use_tags>,<use_pdma>]\n");
-	    printk(KERN_ALERT "scsi: <mac5380> Bad Penguin parameters?\n");
-	    return 0;
-	}
-	    
-	if (ints[0] >= 1) {
-		if (ints[1] > 0)
-			/* no limits on this, just > 0 */
-			setup_can_queue = ints[1];
-	}
-	if (ints[0] >= 2) {
-		if (ints[2] > 0)
-			setup_cmd_per_lun = ints[2];
-	}
-	if (ints[0] >= 3) {
-		if (ints[3] >= 0) {
-			setup_sg_tablesize = ints[3];
-			/* Must be <= SG_ALL (255) */
-			if (setup_sg_tablesize > SG_ALL)
-				setup_sg_tablesize = SG_ALL;
-		}
-	}
-	if (ints[0] >= 4) {
-		/* Must be between 0 and 7 */
-		if (ints[4] >= 0 && ints[4] <= 7)
-			setup_hostid = ints[4];
-		else if (ints[4] > 7)
-			printk(KERN_WARNING "mac_scsi_setup: invalid host ID %d !\n", ints[4] );
-	}
-#ifdef SUPPORT_TAGS	
-	if (ints[0] >= 5) {
-		if (ints[5] >= 0)
-			setup_use_tagged_queuing = !!ints[5];
+
+	(void)get_options(str, ARRAY_SIZE(ints), ints);
+
+	if (ints[0] < 1 || ints[0] > 6) {
+		pr_err("Usage: mac5380=<can_queue>[,<cmd_per_lun>[,<sg_tablesize>[,<hostid>[,<use_tags>[,<use_pdma>]]]]]\n");
+		return 0;
 	}
-	
-	if (ints[0] == 6) {
-	    if (ints[6] >= 0)
+	if (ints[0] >= 1)
+		setup_can_queue = ints[1];
+	if (ints[0] >= 2)
+		setup_cmd_per_lun = ints[2];
+	if (ints[0] >= 3)
+		setup_sg_tablesize = ints[3];
+	if (ints[0] >= 4)
+		setup_hostid = ints[4];
+	if (ints[0] >= 5)
+		setup_use_tagged_queuing = ints[5];
+	if (ints[0] >= 6)
 		setup_use_pdma = ints[6];
-	}
-#else
-	if (ints[0] == 5) {
-	    if (ints[5] >= 0)
-		setup_use_pdma = ints[5];
-	}
-#endif /* SUPPORT_TAGS */
-	
 	return 1;
 }
 
 __setup("mac5380=", mac_scsi_setup);
+#endif /* !MODULE */
 
 /*
  * Function : int macscsi_detect(struct scsi_host_template * tpnt)
@@ -199,13 +164,8 @@ int __init macscsi_detect(struct scsi_ho
 		tpnt->cmd_per_lun = setup_cmd_per_lun;
 	if (setup_sg_tablesize >= 0)
 		tpnt->sg_tablesize = setup_sg_tablesize;
-
-    if (setup_hostid >= 0)
-	tpnt->this_id = setup_hostid;
-    else {
-	/* use 7 as default */
-	tpnt->this_id = 7;
-    }
+	if (setup_hostid >= 0)
+		tpnt->this_id = setup_hostid & 7;
 
 #ifdef SUPPORT_TAGS
     if (setup_use_tagged_queuing < 0)
@@ -219,15 +179,15 @@ int __init macscsi_detect(struct scsi_ho
 	return 0;
 
     if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = via1+0x8000;
-	mac_scsi_drq   = via1+0xE000;
-	mac_scsi_nodrq = via1+0xC000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
 	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
 	flags = FLAG_NO_PSEUDO_DMA;

drivers/scsi/mac_scsi.c int __init macscsi_detect(struct scsi_ho · line 193

Quoted 10 lines
drivers/scsi/mac_scsi.c +3 -3
     } else {
-	mac_scsi_regp  = via1+0x10000;
-	mac_scsi_drq   = via1+0x6000;
-	mac_scsi_nodrq = via1+0x12000;
+	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
+	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
+	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
     }
 
     if (! setup_use_pdma)

Hmm. mac_via.h has this:

/*
* Base addresses for the VIAs. There are two in every machine,
* although on some machines the second is an RBV or an OSS.
* The OSS is different enough that it's handled separately. *
* Do not use these values directly; use the via1 and via2 variables
* instead (and don't forget to check rbv_present when using via2!) */

Quoted 6 lines

#define VIA1_BASE (0x50F00000)
#define VIA2_BASE (0x50F02000)
#define RBV_BASE (0x50F26000)

So either that comment is obsolete or you should revert the above bit ...

Use of via1 had to be changed because that symbol is not exported.

The comment you quoted is probably not wrong; it relates to programming the VIA chip itself (see ADB drivers for example). But in this driver we aren't interested in the VIA1 chip so I'd say niether via1 or VIA1_BASE is good style. Hence my use of bare addresses in the platform resource initializers in patch 21.

This example of VIA1_BASE + offset disappears in patch 21 (you can find an unrelated example in arch/m68k/mac/config.c but that was not my doing).

This patch is not meant to change the actual addresses used by mac_scsi; it just makes the driver modular. Use of VIA1_BASE seemed like a good way to express the fact that the addresses are not changed yet (some models use new addresses after patch 21).

Basically, I just wanted a modular driver for debugging and bisection and I wanted it early in the patch series. A modular mac_scsi.c aligns better with atari_scsi.c and sun3_scsi.c as they are already modular. That means that the three subsequent patches which convert {atari,mac,sun3}_scsi.c to platform drivers also align nicely (so I could cross check them).

Quoted 7 lines
Quoted 4 lines

Fair enough.

Just needed some clarification here. My Mac experience ceased with a IIcx :-)

Hannes, can I get a reviewed-by tag for this patch please?

Sure.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 21284 (AG Nürnberg)
author
#41 lore raw

PATCH v2 20/36 mac_scsi: Cleanup PDMA code

In reply to Finn Thain

Fix whitespace, remove pointless volatile qualifiers and improve code style by use of INPUT_DATA_REG and OUTPUT_DATA_REG macros.

---
 drivers/scsi/mac_scsi.c |  122 ++++++++++++++++++++++++------------------------
 1 file changed, 62 insertions(+), 60 deletions(-)
drivers/scsi/mac_scsi.c +62 -60
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -86,9 +86,9 @@ module_param(setup_hostid, int, 0);
 #define	AFTER_RESET_DELAY	(HZ/2)
 #endif
 
-static volatile unsigned char *mac_scsi_regp = NULL;
-static volatile unsigned char *mac_scsi_drq  = NULL;
-static volatile unsigned char *mac_scsi_nodrq = NULL;
+static unsigned char *mac_scsi_regp;
+static unsigned char *mac_scsi_drq;
+static unsigned char *mac_scsi_nodrq;
 
 
 /*
@@ -262,6 +262,7 @@ static void mac_scsi_reset_boot(struct S
 }
 #endif
 
+#ifdef PSEUDO_DMA
 /* 
    Pseudo-DMA: (Ove Edlund)
    The code attempts to catch bus errors that occur if one for example
@@ -331,38 +332,38 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-
-static int macscsi_pread (struct Scsi_Host *instance,
-			  unsigned char *dst, int len)
+static int macscsi_pread(struct Scsi_Host *instance,
+                         unsigned char *dst, int len)
 {
-   unsigned char *d;
-   volatile unsigned char *s;
+	unsigned char *d;
+	unsigned char *s;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
+
+	s = mac_scsi_drq + (INPUT_DATA_REG << 4);
+	d = dst;
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	/* These conditions are derived from MacOS */
 
-   s = mac_scsi_drq+0x60;
-   d = dst;
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       !(NCR5380_read(STATUS_REG) & SR_REQ))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	    (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
+		pr_err("Error in macscsi_pread\n");
+		return -1;
+	}
 
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && !(NCR5380_read(STATUS_REG) & SR_REQ))
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
-      printk(KERN_ERR "Error in macscsi_pread\n");
-      return -1;
-   }
-
-   CP_IO_TO_MEM(s, d, len);
-   
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pread\n");
-      return -1;
-   }
-   
-   return 0;
+	CP_IO_TO_MEM(s, d, len);
+
+	if (len != 0) {
+		pr_notice("Bus error in macscsi_pread\n");
+		return -1;
+	}
+
+	return 0;
 }
 
 
@@ -424,39 +425,40 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-static int macscsi_pwrite (struct Scsi_Host *instance,
-				  unsigned char *src, int len)
+static int macscsi_pwrite(struct Scsi_Host *instance,
+                          unsigned char *src, int len)
 {
-   unsigned char *s;
-   volatile unsigned char *d;
+	unsigned char *s;
+	unsigned char *d;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	s = src;
+	d = mac_scsi_drq + (OUTPUT_DATA_REG << 4);
 
-   s = src;
-   d = mac_scsi_drq;
-   
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (!(NCR5380_read(STATUS_REG) & SR_REQ) 
-            || (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH))) 
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
-      printk(KERN_ERR "Error in macscsi_pwrite\n");
-      return -1;
-   }
-
-   CP_MEM_TO_IO(s, d, len);   
-
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pwrite\n");
-      return -1;
-   }
-   
-   return 0;
-}
+	/* These conditions are derived from MacOS */
+
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       (!(NCR5380_read(STATUS_REG) & SR_REQ) ||
+	        (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
+		pr_err("Error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	CP_MEM_TO_IO(s, d, len);
 
+	if (len != 0) {
+		pr_notice("Bus error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	return 0;
+}
+#endif
 
 #include "NCR5380.c"
 
#42 lore raw

Re: [PATCH v2 20/36] mac_scsi: Cleanup PDMA code

Quoted 163 lines · Finn Thain

Fix whitespace, remove pointless volatile qualifiers and improve code style by use of INPUT_DATA_REG and OUTPUT_DATA_REG macros.

---
 drivers/scsi/mac_scsi.c |  122 ++++++++++++++++++++++++------------------------
 1 file changed, 62 insertions(+), 60 deletions(-)

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +55 -60
@@ -86,9 +86,9 @@ module_param(setup_hostid, int, 0);
 #define	AFTER_RESET_DELAY	(HZ/2)
 #endif
 
-static volatile unsigned char *mac_scsi_regp = NULL;
-static volatile unsigned char *mac_scsi_drq  = NULL;
-static volatile unsigned char *mac_scsi_nodrq = NULL;
+static unsigned char *mac_scsi_regp;
+static unsigned char *mac_scsi_drq;
+static unsigned char *mac_scsi_nodrq;
 
 
 /*
@@ -262,6 +262,7 @@ static void mac_scsi_reset_boot(struct S
 }
 #endif
 
+#ifdef PSEUDO_DMA
 /* 
    Pseudo-DMA: (Ove Edlund)
    The code attempts to catch bus errors that occur if one for example
@@ -331,38 +332,38 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-
-static int macscsi_pread (struct Scsi_Host *instance,
-			  unsigned char *dst, int len)
+static int macscsi_pread(struct Scsi_Host *instance,
+                         unsigned char *dst, int len)
 {
-   unsigned char *d;
-   volatile unsigned char *s;
+	unsigned char *d;
+	unsigned char *s;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
+
+	s = mac_scsi_drq + (INPUT_DATA_REG << 4);
+	d = dst;
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	/* These conditions are derived from MacOS */
 
-   s = mac_scsi_drq+0x60;
-   d = dst;
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       !(NCR5380_read(STATUS_REG) & SR_REQ))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	    (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
+		pr_err("Error in macscsi_pread\n");
+		return -1;
+	}
 
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && !(NCR5380_read(STATUS_REG) & SR_REQ))
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
-      printk(KERN_ERR "Error in macscsi_pread\n");
-      return -1;
-   }
-
-   CP_IO_TO_MEM(s, d, len);
-   
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pread\n");
-      return -1;
-   }
-   
-   return 0;
+	CP_IO_TO_MEM(s, d, len);
+
+	if (len != 0) {
+		pr_notice("Bus error in macscsi_pread\n");
+		return -1;
+	}
+
+	return 0;
 }
 
 
@@ -424,39 +425,40 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-static int macscsi_pwrite (struct Scsi_Host *instance,
-				  unsigned char *src, int len)
+static int macscsi_pwrite(struct Scsi_Host *instance,
+                          unsigned char *src, int len)
 {
-   unsigned char *s;
-   volatile unsigned char *d;
+	unsigned char *s;
+	unsigned char *d;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	s = src;
+	d = mac_scsi_drq + (OUTPUT_DATA_REG << 4);
 
-   s = src;
-   d = mac_scsi_drq;
-   
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (!(NCR5380_read(STATUS_REG) & SR_REQ) 
-            || (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH))) 
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
-      printk(KERN_ERR "Error in macscsi_pwrite\n");
-      return -1;
-   }
-
-   CP_MEM_TO_IO(s, d, len);   
-
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pwrite\n");
-      return -1;
-   }
-   
-   return 0;
-}
+	/* These conditions are derived from MacOS */
+
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       (!(NCR5380_read(STATUS_REG) & SR_REQ) ||
+	        (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
+		pr_err("Error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	CP_MEM_TO_IO(s, d, len);
 
+	if (len != 0) {

drivers/scsi/mac_scsi.c __asm__ __volatile__ \ · line 464

Quoted 10 lines
drivers/scsi/mac_scsi.c +7 -0
+		pr_notice("Bus error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	return 0;
+}
+#endif
 
 #include "NCR5380.c"
 

Any reason why you didn't re-indent macscsi_indent?

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
#43 lore raw

Re: [PATCH v2 20/36] mac_scsi: Cleanup PDMA code

Quoted 170 lines · Hannes Reinecke
Quoted 169 lines · Finn Thain

Fix whitespace, remove pointless volatile qualifiers and improve code style by use of INPUT_DATA_REG and OUTPUT_DATA_REG macros.

---
 drivers/scsi/mac_scsi.c |  122 ++++++++++++++++++++++++------------------------
 1 file changed, 62 insertions(+), 60 deletions(-)

Index: linux/drivers/scsi/mac_scsi.c
===================================================================

drivers/scsi/mac_scsi.c +62 -60
@@ -86,9 +86,9 @@ module_param(setup_hostid, int, 0);
 #define	AFTER_RESET_DELAY	(HZ/2)
 #endif
 
-static volatile unsigned char *mac_scsi_regp = NULL;
-static volatile unsigned char *mac_scsi_drq  = NULL;
-static volatile unsigned char *mac_scsi_nodrq = NULL;
+static unsigned char *mac_scsi_regp;
+static unsigned char *mac_scsi_drq;
+static unsigned char *mac_scsi_nodrq;
 
 
 /*
@@ -262,6 +262,7 @@ static void mac_scsi_reset_boot(struct S
 }
 #endif
 
+#ifdef PSEUDO_DMA
 /* 
    Pseudo-DMA: (Ove Edlund)
    The code attempts to catch bus errors that occur if one for example
@@ -331,38 +332,38 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-
-static int macscsi_pread (struct Scsi_Host *instance,
-			  unsigned char *dst, int len)
+static int macscsi_pread(struct Scsi_Host *instance,
+                         unsigned char *dst, int len)
 {
-   unsigned char *d;
-   volatile unsigned char *s;
+	unsigned char *d;
+	unsigned char *s;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
+
+	s = mac_scsi_drq + (INPUT_DATA_REG << 4);
+	d = dst;
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	/* These conditions are derived from MacOS */
 
-   s = mac_scsi_drq+0x60;
-   d = dst;
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       !(NCR5380_read(STATUS_REG) & SR_REQ))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	    (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
+		pr_err("Error in macscsi_pread\n");
+		return -1;
+	}
 
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && !(NCR5380_read(STATUS_REG) & SR_REQ))
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)) {
-      printk(KERN_ERR "Error in macscsi_pread\n");
-      return -1;
-   }
-
-   CP_IO_TO_MEM(s, d, len);
-   
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pread\n");
-      return -1;
-   }
-   
-   return 0;
+	CP_IO_TO_MEM(s, d, len);
+
+	if (len != 0) {
+		pr_notice("Bus error in macscsi_pread\n");
+		return -1;
+	}
+
+	return 0;
 }
 
 
@@ -424,39 +425,40 @@ __asm__ __volatile__					\
      : "0"(s), "1"(d), "2"(len)				\
      : "d0")
 
-static int macscsi_pwrite (struct Scsi_Host *instance,
-				  unsigned char *src, int len)
+static int macscsi_pwrite(struct Scsi_Host *instance,
+                          unsigned char *src, int len)
 {
-   unsigned char *s;
-   volatile unsigned char *d;
+	unsigned char *s;
+	unsigned char *d;
+
+	NCR5380_local_declare();
+	NCR5380_setup(instance);
 
-   NCR5380_local_declare();
-   NCR5380_setup(instance);
+	s = src;
+	d = mac_scsi_drq + (OUTPUT_DATA_REG << 4);
 
-   s = src;
-   d = mac_scsi_drq;
-   
-/* These conditions are derived from MacOS */
-
-   while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) 
-         && (!(NCR5380_read(STATUS_REG) & SR_REQ) 
-            || (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH))) 
-      ;
-   if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
-      printk(KERN_ERR "Error in macscsi_pwrite\n");
-      return -1;
-   }
-
-   CP_MEM_TO_IO(s, d, len);   
-
-   if (len != 0) {
-      printk(KERN_NOTICE "Bus error in macscsi_pwrite\n");
-      return -1;
-   }
-   
-   return 0;
-}
+	/* These conditions are derived from MacOS */
+
+	while (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ) &&
+	       (!(NCR5380_read(STATUS_REG) & SR_REQ) ||
+	        (NCR5380_read(BUS_AND_STATUS_REG) & BASR_PHASE_MATCH)))
+		;
+
+	if (!(NCR5380_read(BUS_AND_STATUS_REG) & BASR_DRQ)) {
+		pr_err("Error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	CP_MEM_TO_IO(s, d, len);
 
+	if (len != 0) {
+		pr_notice("Bus error in macscsi_pwrite\n");
+		return -1;
+	}
+
+	return 0;
+}
+#endif
 
Quoted 6 lines

drivers/scsi/mac_scsi.c __asm__ __volatile__ \ · line 464

Quoted 4 lines
drivers/scsi/mac_scsi.c +0 -0
 #include "NCR5380.c"
 

Any reason why you didn't re-indent macscsi_indent?

Ahh, forget it.

Addressed with the next patch.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#44 lore raw

Re: [PATCH v2 20/36] mac_scsi: Cleanup PDMA code

Quoted 6 lines · Hannes Reinecke
Quoted 1 line · Hannes Reinecke

Any reason why you didn't re-indent [...]

Ahh, forget it.

Addressed with the next patch.

So, does it get your reviewed-by tag? (Thanks for reviewing all this, BTW.)

You also questioned mac_scsi.c whitespace in your review of, "[PATCH v2 14/36] ncr5380: Remove pointless compiler command line override macros." By the end of this patch series, I thought that mac_scsi.c was in pretty good shape (?)

#45 lore raw

Re: [PATCH v2 20/36] mac_scsi: Cleanup PDMA code

Quoted 4 lines · Finn Thain
Quoted 1 line · Hannes Reinecke

On 10/30/2014 08:46 AM, Hannes Reinecke wrote:

Quoted 9 lines
Quoted 5 lines
Quoted 1 line

Any reason why you didn't re-indent [...]

Ahh, forget it.

Addressed with the next patch.

So, does it get your reviewed-by tag? (Thanks for reviewing all this, BTW.)

Yes. You can add the reviewed-by tag to this.

Quoted 5 lines

You also questioned mac_scsi.c whitespace in your review of, "[PATCH v2 14/36] ncr5380: Remove pointless compiler command line override macros." By the end of this patch series, I thought that mac_scsi.c was in pretty good shape (?)

I only later figured that you've fixed up mac_scsi.c eventually. So that's all in good shape.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#46 lore raw

PATCH v2 21/36 mac_scsi: Convert to platform device

In reply to Finn Thain

Convert mac_scsi to platform device and eliminate scsi_register().

Platform resources for chip registers now follow the documentation. This should fix issues with the Mac IIci (and possibly other models too).

---

The new hwreg_present() call site is not protected by local_irq_save/restore. This assumes Geert's patch, "Disable/restore interrupts in hwreg_present()/hwreg_write()", which is commit e4dc601bf99ccd1c in 3.18-rc1.

Changes since v1:
- Use NO_IRQ instead of IRQ_NONE.
- Drop unnecessary MACH_IS_MAC() test.
- Remove static platform_device structs and call platform_device_register_simple() instead of platform_device_register().
- Platform resources now const and __initconst.
- Add MAC_SCSI_LATE platform resources to avoid PDMA on certain models.

---
 arch/m68k/include/asm/macintosh.h |    4 
 arch/m68k/mac/config.c            |  146 ++++++++++++++++++++--
 drivers/scsi/mac_scsi.c           |  245 +++++++++++++++++++-------------------
 3 files changed, 262 insertions(+), 133 deletions(-)
drivers/scsi/mac_scsi.c +126 -119
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -12,23 +12,18 @@
  */
 
 #include <linux/types.h>
-#include <linux/stddef.h>
-#include <linux/ctype.h>
 #include <linux/delay.h>
-
 #include <linux/module.h>
-#include <linux/signal.h>
 #include <linux/ioport.h>
 #include <linux/init.h>
 #include <linux/blkdev.h>
 #include <linux/interrupt.h>
+#include <linux/platform_device.h>
 
+#include <asm/hwtest.h>
 #include <asm/io.h>
-#include <asm/irq.h>
-
-#include <asm/macintosh.h>
 #include <asm/macints.h>
-#include <asm/mac_via.h>
+#include <asm/setup.h>
 
 #include <scsi/scsi_host.h>
 
@@ -36,7 +31,7 @@
 
 #define PSEUDO_DMA
 
-#define NCR5380_implementation_fields   /* none */
+#define NCR5380_implementation_fields   unsigned char *pdma_base
 #define NCR5380_local_declare()         struct Scsi_Host *_instance
 #define NCR5380_setup(instance)         _instance = instance
 
@@ -58,10 +53,6 @@
 
 #define RESET_BOOT
 
-#ifdef RESET_BOOT
-static void mac_scsi_reset_boot(struct Scsi_Host *instance);
-#endif
-
 static int setup_can_queue = -1;
 module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
@@ -86,23 +77,18 @@ module_param(setup_hostid, int, 0);
 #define	AFTER_RESET_DELAY	(HZ/2)
 #endif
 
-static unsigned char *mac_scsi_regp;
-static unsigned char *mac_scsi_drq;
-static unsigned char *mac_scsi_nodrq;
-
-
 /*
  * NCR 5380 register access functions
  */
 
-static __inline__ char macscsi_read(struct Scsi_Host *instance, int reg)
+static inline char macscsi_read(struct Scsi_Host *instance, int reg)
 {
-  return in_8(instance->io_port + (reg<<4));
+	return in_8(instance->base + (reg << 4));
 }
 
-static __inline__ void macscsi_write(struct Scsi_Host *instance, int reg, int value)
+static inline void macscsi_write(struct Scsi_Host *instance, int reg, int value)
 {
-  out_8(instance->io_port + (reg<<4), value);
+	out_8(instance->base + (reg << 4), value);
 }
 
 #ifndef MODULE
@@ -134,96 +120,6 @@ static int __init mac_scsi_setup(char *s
 __setup("mac5380=", mac_scsi_setup);
 #endif /* !MODULE */
 
-/*
- * Function : int macscsi_detect(struct scsi_host_template * tpnt)
- *
- * Purpose : initializes mac NCR5380 driver based on the
- *	command line / compile time port and irq definitions.
- *
- * Inputs : tpnt - template for this SCSI adapter.
- *
- * Returns : 1 if a host adapter was found, 0 if not.
- *
- */
- 
-int __init macscsi_detect(struct scsi_host_template * tpnt)
-{
-    static int called = 0;
-    int flags = 0;
-    struct Scsi_Host *instance;
-
-    if (!MACH_IS_MAC || called)
-	return( 0 );
-
-    if (macintosh_config->scsi_type != MAC_SCSI_OLD)
-	return( 0 );
-
-	if (setup_can_queue > 0)
-		tpnt->can_queue = setup_can_queue;
-	if (setup_cmd_per_lun > 0)
-		tpnt->cmd_per_lun = setup_cmd_per_lun;
-	if (setup_sg_tablesize >= 0)
-		tpnt->sg_tablesize = setup_sg_tablesize;
-	if (setup_hostid >= 0)
-		tpnt->this_id = setup_hostid & 7;
-
-#ifdef SUPPORT_TAGS
-    if (setup_use_tagged_queuing < 0)
-	setup_use_tagged_queuing = 0;
-#endif
-
-    /* Once we support multiple 5380s (e.g. DuoDock) we'll do
-       something different here */
-    instance = scsi_register (tpnt, sizeof(struct NCR5380_hostdata));
-    if (instance == NULL)
-	return 0;
-
-    if (macintosh_config->ident == MAC_MODEL_IIFX) {
-	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x8000;
-	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0xE000;
-	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0xC000;
-	/* The IIFX should be able to do true DMA, but pseudo-dma doesn't work */
-	flags = FLAG_NO_PSEUDO_DMA;
-    } else {
-	mac_scsi_regp  = (unsigned char *) VIA1_BASE + 0x10000;
-	mac_scsi_drq   = (unsigned char *) VIA1_BASE + 0x6000;
-	mac_scsi_nodrq = (unsigned char *) VIA1_BASE + 0x12000;
-    }
-
-    if (! setup_use_pdma)
-	flags = FLAG_NO_PSEUDO_DMA;
-	
-    instance->io_port = (unsigned long) mac_scsi_regp;
-    instance->irq = IRQ_MAC_SCSI;
-
-#ifdef RESET_BOOT   
-    mac_scsi_reset_boot(instance);
-#endif
-    
-    NCR5380_init(instance, flags);
-
-    instance->n_io_port = 255;
-
-    if (instance->irq != NO_IRQ)
-	if (request_irq(instance->irq, NCR5380_intr, 0, "ncr5380", instance)) {
-	    printk(KERN_WARNING "scsi%d: IRQ%d not free, interrupts disabled\n",
-		   instance->host_no, instance->irq);
-	    instance->irq = NO_IRQ;
-	}
-
-    called = 1;
-    return 1;
-}
-
-int macscsi_release (struct Scsi_Host *shpnt)
-{
-	if (shpnt->irq != NO_IRQ)
-		free_irq(shpnt->irq, shpnt);
-	NCR5380_exit(shpnt);
-
-	return 0;
-}
-
 #ifdef RESET_BOOT
 /*
  * Our 'bus reset on boot' function
@@ -335,13 +231,14 @@ __asm__ __volatile__					\
 static int macscsi_pread(struct Scsi_Host *instance,
                          unsigned char *dst, int len)
 {
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
 	unsigned char *d;
 	unsigned char *s;
 
 	NCR5380_local_declare();
 	NCR5380_setup(instance);
 
-	s = mac_scsi_drq + (INPUT_DATA_REG << 4);
+	s = hostdata->pdma_base + (INPUT_DATA_REG << 4);
 	d = dst;
 
 	/* These conditions are derived from MacOS */
@@ -428,6 +325,7 @@ __asm__ __volatile__					\
 static int macscsi_pwrite(struct Scsi_Host *instance,
                           unsigned char *src, int len)
 {
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
 	unsigned char *s;
 	unsigned char *d;
 
@@ -435,7 +333,7 @@ static int macscsi_pwrite(struct Scsi_Ho
 	NCR5380_setup(instance);
 
 	s = src;
-	d = mac_scsi_drq + (OUTPUT_DATA_REG << 4);
+	d = hostdata->pdma_base + (OUTPUT_DATA_REG << 4);
 
 	/* These conditions are derived from MacOS */
 
@@ -462,13 +360,15 @@ static int macscsi_pwrite(struct Scsi_Ho
 
 #include "NCR5380.c"
 
-static struct scsi_host_template driver_template = {
-	.proc_name			= "Mac5380",
+#define DRV_MODULE_NAME         "mac_scsi"
+#define PFX                     DRV_MODULE_NAME ": "
+
+static struct scsi_host_template mac_scsi_template = {
+	.module				= THIS_MODULE,
+	.proc_name			= DRV_MODULE_NAME,
 	.show_info			= macscsi_show_info,
 	.write_info			= macscsi_write_info,
 	.name				= "Macintosh NCR5380 SCSI",
-	.detect				= macscsi_detect,
-	.release			= macscsi_release,
 	.info				= macscsi_info,
 	.queuecommand			= macscsi_queue_command,
 	.eh_abort_handler		= macscsi_abort,
@@ -480,7 +380,114 @@ static struct scsi_host_template driver_
 	.use_clustering			= DISABLE_CLUSTERING
 };
 
+static int __init mac_scsi_probe(struct platform_device *pdev)
+{
+	struct Scsi_Host *instance;
+	int error;
+	int host_flags = 0;
+	struct resource *irq, *pio_mem, *pdma_mem = NULL;
+
+	pio_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	if (!pio_mem)
+		return -ENODEV;
+
+#ifdef PSEUDO_DMA
+	pdma_mem = platform_get_resource(pdev, IORESOURCE_MEM, 1);
+#endif
+
+	irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
+
+	if (!hwreg_present((unsigned char *)pio_mem->start +
+	                   (STATUS_REG << 4))) {
+		pr_info(PFX "no device detected at %pap\n", &pio_mem->start);
+		return -ENODEV;
+	}
+
+	if (setup_can_queue > 0)
+		mac_scsi_template.can_queue = setup_can_queue;
+	if (setup_cmd_per_lun > 0)
+		mac_scsi_template.cmd_per_lun = setup_cmd_per_lun;
+	if (setup_sg_tablesize >= 0)
+		mac_scsi_template.sg_tablesize = setup_sg_tablesize;
+	if (setup_hostid >= 0)
+		mac_scsi_template.this_id = setup_hostid & 7;
+#ifdef SUPPORT_TAGS
+	if (setup_use_tagged_queuing < 0)
+		setup_use_tagged_queuing = 0;
+#endif
+	if (setup_use_pdma < 0)
+		setup_use_pdma = 0;
+
+	instance = scsi_host_alloc(&mac_scsi_template,
+	                           sizeof(struct NCR5380_hostdata));
+	if (!instance)
+		return -ENOMEM;
+
+	instance->base = pio_mem->start;
+	if (irq)
+		instance->irq = irq->start;
+	else
+		instance->irq = NO_IRQ;
+
+	if (pdma_mem && setup_use_pdma) {
+		struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+		hostdata->pdma_base = (unsigned char *)pdma_mem->start;
+	} else
+		host_flags |= FLAG_NO_PSEUDO_DMA;
+
+#ifdef RESET_BOOT
+	mac_scsi_reset_boot(instance);
+#endif
+
+	NCR5380_init(instance, host_flags);
+
+	if (instance->irq != NO_IRQ) {
+		error = request_irq(instance->irq, macscsi_intr, IRQF_SHARED,
+		                    "NCR5380", instance);
+		if (error)
+			goto fail_irq;
+	}
+
+	error = scsi_add_host(instance, NULL);
+	if (error)
+		goto fail_host;
+
+	platform_set_drvdata(pdev, instance);
+
+	scsi_scan_host(instance);
+	return 0;
+
+fail_host:
+	if (instance->irq != NO_IRQ)
+		free_irq(instance->irq, instance);
+fail_irq:
+	NCR5380_exit(instance);
+	scsi_host_put(instance);
+	return error;
+}
+
+static int __exit mac_scsi_remove(struct platform_device *pdev)
+{
+	struct Scsi_Host *instance = platform_get_drvdata(pdev);
+
+	scsi_remove_host(instance);
+	if (instance->irq != NO_IRQ)
+		free_irq(instance->irq, instance);
+	NCR5380_exit(instance);
+	scsi_host_put(instance);
+	return 0;
+}
+
+static struct platform_driver mac_scsi_driver = {
+	.remove = __exit_p(mac_scsi_remove),
+	.driver = {
+		.name	= DRV_MODULE_NAME,
+		.owner	= THIS_MODULE,
+	},
+};
 
-#include "scsi_module.c"
+module_platform_driver_probe(mac_scsi_driver, mac_scsi_probe);
 
+MODULE_ALIAS("platform:" DRV_MODULE_NAME);
 MODULE_LICENSE("GPL");
arch/m68k/mac/config.c +132 -14

242 lines not on this page · raw message

arch/m68k/include/asm/macintosh.h +4 -0
Index: linux/arch/m68k/include/asm/macintosh.h
===================================================================
@@ -53,6 +53,10 @@ struct mac_model
 #define MAC_SCSI_QUADRA		2
 #define MAC_SCSI_QUADRA2	3
 #define MAC_SCSI_QUADRA3	4
+#define MAC_SCSI_IIFX		5
+#define MAC_SCSI_DUO		6
+#define MAC_SCSI_CCL		7
+#define MAC_SCSI_LATE		8
 
 #define MAC_IDE_NONE		0
 #define MAC_IDE_QUADRA		1
Reviewed-by on v2 21/36
#47 lore raw

Re: [PATCH v2 21/36] mac_scsi: Convert to platform device

Quoted 7 lines · Finn Thain

Convert mac_scsi to platform device and eliminate scsi_register().

Platform resources for chip registers now follow the documentation. This should fix issues with the Mac IIci (and possibly other models too).

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#48 lore raw

PATCH v2 22/36 atari_scsi: Fix atari_scsi deadlocks on Falcon

In reply to Finn Thain

Don't disable irqs when waiting for the ST DMA "lock"; its release may require an interrupt.

Introduce stdma_try_lock() for use in soft irq context. atari_scsi now tells the SCSI mid-layer to defer queueing a command if the ST DMA lock is not available, as per Michael's patch:
http://marc.info/?l=linux-m68k&m=139095335824863&w=2

The falcon_got_lock variable is race prone: we can't disable IRQs while waiting to acquire the lock, so after acquiring it there must be some interval during which falcon_got_lock remains false. Introduce stdma_is_locked_by() to replace falcon_got_lock.

The falcon_got_lock tests in the EH handlers are incorrect these days. It can happen that an EH handler is called after a command completes normally. Remove these checks along with falcon_got_lock.

Also remove the complicated and racy fairness wait queues. If fairness is an issue (when SCSI competes with IDE for the ST DMA interrupt), the solution is likely to be a lower value for host->can_queue.

---

Changes since v1:
- Use Geert's suggestion for simpler stdma_is_locked_by() implementation.

---
 arch/m68k/atari/stdma.c             |   61 ++++++++++++++++++----------
 arch/m68k/include/asm/atari_stdma.h |    4 -
 drivers/scsi/atari_NCR5380.c        |   35 +++++-----------
 drivers/scsi/atari_scsi.c           |   76 +++++++-----------------------------
 4 files changed, 69 insertions(+), 107 deletions(-)
arch/m68k/atari/stdma.c +40 -21
Index: linux/arch/m68k/atari/stdma.c
===================================================================
@@ -59,6 +59,31 @@ static irqreturn_t stdma_int (int irq, v
 /************************* End of Prototypes **************************/
 
 
+/**
+ * stdma_try_lock - attempt to acquire ST DMA interrupt "lock"
+ * @handler: interrupt handler to use after acquisition
+ *
+ * Returns !0 if lock was acquired; otherwise 0.
+ */
+
+int stdma_try_lock(irq_handler_t handler, void *data)
+{
+	unsigned long flags;
+
+	local_irq_save(flags);
+	if (stdma_locked) {
+		local_irq_restore(flags);
+		return 0;
+	}
+
+	stdma_locked   = 1;
+	stdma_isr      = handler;
+	stdma_isr_data = data;
+	local_irq_restore(flags);
+	return 1;
+}
+EXPORT_SYMBOL(stdma_try_lock);
+
 
 /*
  * Function: void stdma_lock( isrfunc isr, void *data )
@@ -78,19 +103,10 @@ static irqreturn_t stdma_int (int irq, v
 
 void stdma_lock(irq_handler_t handler, void *data)
 {
-	unsigned long flags;
-
-	local_irq_save(flags);		/* protect lock */
-
 	/* Since the DMA is used for file system purposes, we
 	 have to sleep uninterruptible (there may be locked
 	 buffers) */
-	wait_event(stdma_wait, !stdma_locked);
-
-	stdma_locked   = 1;
-	stdma_isr      = handler;
-	stdma_isr_data = data;
-	local_irq_restore(flags);
+	wait_event(stdma_wait, stdma_try_lock(handler, data));
 }
 EXPORT_SYMBOL(stdma_lock);
 
@@ -122,22 +138,25 @@ void stdma_release(void)
 EXPORT_SYMBOL(stdma_release);
 
 
-/*
- * Function: int stdma_others_waiting( void )
- *
- * Purpose: Check if someone waits for the ST-DMA lock.
- *
- * Inputs: none
- *
- * Returns: 0 if no one is waiting, != 0 otherwise
+/**
+ * stdma_is_locked_by - allow lock holder to check whether it needs to release.
+ * @handler: interrupt handler previously used to acquire lock.
  *
+ * Returns !0 if locked for the given handler; 0 otherwise.
  */
 
-int stdma_others_waiting(void)
+int stdma_is_locked_by(irq_handler_t handler)
 {
-	return waitqueue_active(&stdma_wait);
+	unsigned long flags;
+	int result;
+
+	local_irq_save(flags);
+	result = stdma_locked && (stdma_isr == handler);
+	local_irq_restore(flags);
+
+	return result;
 }
-EXPORT_SYMBOL(stdma_others_waiting);
+EXPORT_SYMBOL(stdma_is_locked_by);
 
 
 /*
arch/m68k/include/asm/atari_stdma.h +2 -2
Index: linux/arch/m68k/include/asm/atari_stdma.h
===================================================================
@@ -8,11 +8,11 @@
 
 /***************************** Prototypes *****************************/
 
+int stdma_try_lock(irq_handler_t, void *);
 void stdma_lock(irq_handler_t handler, void *data);
 void stdma_release( void );
-int stdma_others_waiting( void );
 int stdma_islocked( void );
-void *stdma_locked_by( void );
+int stdma_is_locked_by(irq_handler_t);
 void stdma_init( void );
 
 /************************* End of Prototypes **************************/
drivers/scsi/atari_NCR5380.c +12 -23
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -879,10 +879,10 @@ static void NCR5380_exit(struct Scsi_Hos
  *
  */
 
-static int NCR5380_queue_command_lck(struct scsi_cmnd *cmd,
-                                     void (*done)(struct scsi_cmnd *))
+static int NCR5380_queue_command(struct Scsi_Host *instance,
+                                 struct scsi_cmnd *cmd)
 {
-	SETUP_HOSTDATA(cmd->device->host);
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
 	struct scsi_cmnd *tmp;
 	unsigned long flags;
 
@@ -893,7 +893,7 @@ static int NCR5380_queue_command_lck(str
 		printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag set\n",
 		       H_NO(cmd));
 		cmd->result = (DID_ERROR << 16);
-		done(cmd);
+		cmd->scsi_done(cmd);
 		return 0;
 	}
 #endif /* (NDEBUG & NDEBUG_NO_WRITE) */
@@ -904,8 +904,6 @@ static int NCR5380_queue_command_lck(str
 	 */
 
 	SET_NEXT(cmd, NULL);
-	cmd->scsi_done = done;
-
 	cmd->result = 0;
 
 	/*
@@ -915,7 +913,6 @@ static int NCR5380_queue_command_lck(str
 	 * sense data is only guaranteed to be valid while the condition exists.
 	 */
 
-	local_irq_save(flags);
 	/* ++guenther: now that the issue queue is being set up, we can lock ST-DMA.
 	 * Otherwise a running NCR5380_main may steal the lock.
 	 * Lock before actually inserting due to fairness reasons explained in
@@ -928,11 +925,13 @@ static int NCR5380_queue_command_lck(str
 	 * because also a timer int can trigger an abort or reset, which would
 	 * alter queues and touch the lock.
 	 */
-	if (!IS_A_TT()) {
-		/* perhaps stop command timer here */
-		falcon_get_lock();
-		/* perhaps restart command timer here */
-	}
+	/* perhaps stop command timer here */
+	if (!falcon_get_lock())
+		return SCSI_MLQUEUE_HOST_BUSY;
+	/* perhaps restart command timer here */
+
+	local_irq_save(flags);
+
 	if (!(hostdata->issue_queue) || (cmd->cmnd[0] == REQUEST_SENSE)) {
 		LIST(cmd, hostdata->issue_queue);
 		SET_NEXT(cmd, hostdata->issue_queue);
@@ -956,15 +955,13 @@ static int NCR5380_queue_command_lck(str
 	 * If we're not in an interrupt, we can call NCR5380_main()
 	 * unconditionally, because it cannot be already running.
 	 */
-	if (in_interrupt() || ((flags >> 8) & 7) >= 6)
+	if (in_interrupt() || irqs_disabled())
 		queue_main();
 	else
 		NCR5380_main(NULL);
 	return 0;
 }
 
-static DEF_SCSI_QCMD(NCR5380_queue_command)
-
 /*
  * Function : NCR5380_main (void)
  *
@@ -2555,10 +2552,6 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 
 	local_irq_save(flags);
 
-	if (!IS_A_TT() && !falcon_got_lock)
-		printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_abort\n",
-		       HOSTNO);
-
 	dprintk(NDEBUG_ABORT, "scsi%d: abort called basr 0x%02x, sr 0x%02x\n", HOSTNO,
 		    NCR5380_read(BUS_AND_STATUS_REG),
 		    NCR5380_read(STATUS_REG));
@@ -2757,10 +2750,6 @@ static int NCR5380_bus_reset(struct scsi
 	struct scsi_cmnd *connected, *disconnected_queue;
 #endif
 
-	if (!IS_A_TT() && !falcon_got_lock)
-		printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_reset\n",
-		       H_NO(cmd));
-
 	NCR5380_print_status(cmd->device->host);
 
 	/* get in phase */
drivers/scsi/atari_scsi.c +15 -61

110 lines not on this page · raw message

Reviewed-by on v2 22/36
#49 lore raw

Re: [PATCH v2 22/36] atari_scsi: Fix atari_scsi deadlocks on Falcon

Quoted 17 lines · Finn Thain

Don't disable irqs when waiting for the ST DMA "lock"; its release may require an interrupt.

Introduce stdma_try_lock() for use in soft irq context. atari_scsi now tells the SCSI mid-layer to defer queueing a command if the ST DMA lock is not available, as per Michael's patch:
http://marc.info/?l=linux-m68k&m=139095335824863&w=2

The falcon_got_lock variable is race prone: we can't disable IRQs while waiting to acquire the lock, so after acquiring it there must be some interval during which falcon_got_lock remains false. Introduce stdma_is_locked_by() to replace falcon_got_lock.

The falcon_got_lock tests in the EH handlers are incorrect these days. It can happen that an EH handler is called after a command completes normally. Remove these checks along with falcon_got_lock.

Quoted 5 lines

Also remove the complicated and racy fairness wait queues. If fairness is an issue (when SCSI competes with IDE for the ST DMA interrupt), the solution is likely to be a lower value for host->can_queue.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
maintainer Acked-by on v2 22/36
#50 lore raw

Re: [PATCH v2 22/36] atari_scsi: Fix atari_scsi deadlocks on Falcon

In reply to Finn Thain

Hi Finn

Quoted 112 lines

Changes since v1:
- Use Geert's suggestion for simpler stdma_is_locked_by() implementation.

---
  arch/m68k/atari/stdma.c             |   61 ++++++++++++++++++----------
  arch/m68k/include/asm/atari_stdma.h |    4 -
  drivers/scsi/atari_NCR5380.c        |   35 +++++-----------
  drivers/scsi/atari_scsi.c           |   76 +++++++-----------------------------
  4 files changed, 69 insertions(+), 107 deletions(-)

Index: linux/arch/m68k/atari/stdma.c
===================================================================

arch/m68k/atari/stdma.c +40 -21
@@ -59,6 +59,31 @@ static irqreturn_t stdma_int (int irq, v
  /************************* End of Prototypes **************************/
 
 
+/**
+ * stdma_try_lock - attempt to acquire ST DMA interrupt "lock"
+ * @handler: interrupt handler to use after acquisition
+ *
+ * Returns !0 if lock was acquired; otherwise 0.
+ */
+
+int stdma_try_lock(irq_handler_t handler, void *data)
+{
+	unsigned long flags;
+
+	local_irq_save(flags);
+	if (stdma_locked) {
+		local_irq_restore(flags);
+		return 0;
+	}
+
+	stdma_locked   = 1;
+	stdma_isr      = handler;
+	stdma_isr_data = data;
+	local_irq_restore(flags);
+	return 1;
+}
+EXPORT_SYMBOL(stdma_try_lock);
+
 
  /*
   * Function: void stdma_lock( isrfunc isr, void *data )
@@ -78,19 +103,10 @@ static irqreturn_t stdma_int (int irq, v
 
  void stdma_lock(irq_handler_t handler, void *data)
  {
-	unsigned long flags;
-
-	local_irq_save(flags);		/* protect lock */
-
  	/* Since the DMA is used for file system purposes, we
  	 have to sleep uninterruptible (there may be locked
  	 buffers) */
-	wait_event(stdma_wait, !stdma_locked);
-
-	stdma_locked   = 1;
-	stdma_isr      = handler;
-	stdma_isr_data = data;
-	local_irq_restore(flags);
+	wait_event(stdma_wait, stdma_try_lock(handler, data));
  }
  EXPORT_SYMBOL(stdma_lock);
 
@@ -122,22 +138,25 @@ void stdma_release(void)
  EXPORT_SYMBOL(stdma_release);
 
 
-/*
- * Function: int stdma_others_waiting( void )
- *
- * Purpose: Check if someone waits for the ST-DMA lock.
- *
- * Inputs: none
- *
- * Returns: 0 if no one is waiting, != 0 otherwise
+/**
+ * stdma_is_locked_by - allow lock holder to check whether it needs to release.
+ * @handler: interrupt handler previously used to acquire lock.
   *
+ * Returns !0 if locked for the given handler; 0 otherwise.
   */
 
-int stdma_others_waiting(void)
+int stdma_is_locked_by(irq_handler_t handler)
  {
-	return waitqueue_active(&stdma_wait);
+	unsigned long flags;
+	int result;
+
+	local_irq_save(flags);
+	result = stdma_locked && (stdma_isr == handler);
+	local_irq_restore(flags);
+
+	return result;
  }
-EXPORT_SYMBOL(stdma_others_waiting);
+EXPORT_SYMBOL(stdma_is_locked_by);
 
 
  /*

Index: linux/arch/m68k/include/asm/atari_stdma.h
===================================================================

arch/m68k/include/asm/atari_stdma.h +0 -0
@@ -8,11 +8,11 @@
 
  /***************************** Prototypes *****************************/
 

arch/m68k/include/asm/atari_stdma.h line 18

Quoted 10 lines
arch/m68k/include/asm/atari_stdma.h +2 -2
+int stdma_try_lock(irq_handler_t, void *);
  void stdma_lock(irq_handler_t handler, void *data);
  void stdma_release( void );
-int stdma_others_waiting( void );
  int stdma_islocked( void );
-void *stdma_locked_by( void );
+int stdma_is_locked_by(irq_handler_t);
  void stdma_init( void );
 
  /************************* End of Prototypes **************************/
Quoted 7 lines

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +0 -0
@@ -879,10 +879,10 @@ static void NCR5380_exit(struct Scsi_Hos
   *
   */

drivers/scsi/atari_NCR5380.c static void NCR5380_exit(struct Scsi_Hos · line 887

Quoted 10 lines
drivers/scsi/atari_NCR5380.c +3 -3
 
-static int NCR5380_queue_command_lck(struct scsi_cmnd *cmd,
-                                     void (*done)(struct scsi_cmnd *))
+static int NCR5380_queue_command(struct Scsi_Host *instance,
+                                 struct scsi_cmnd *cmd)
  {
-	SETUP_HOSTDATA(cmd->device->host);
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
  	struct scsi_cmnd *tmp;
  	unsigned long flags;

Nitpick - why did this change set go into this particular patch? Because you are converting from NCR5380_queue_command_lck to NCR5380_queue_command?

Quoted 11 lines
drivers/scsi/atari_NCR5380.c +1 -1
@@ -893,7 +893,7 @@ static int NCR5380_queue_command_lck(str
  		printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag set\n",
  		       H_NO(cmd));
  		cmd->result = (DID_ERROR << 16);
-		done(cmd);
+		cmd->scsi_done(cmd);
  		return 0;
  	}
  #endif /* (NDEBUG & NDEBUG_NO_WRITE) */

drivers/scsi/atari_NCR5380.c static int NCR5380_queue_command_lck(str · line 909

Quoted 8 lines
drivers/scsi/atari_NCR5380.c +0 -2
@@ -904,8 +904,6 @@ static int NCR5380_queue_command_lck(str
  	 */
 
  	SET_NEXT(cmd, NULL);
-	cmd->scsi_done = done;
-
  	cmd->result = 0;
 
  	/*

Ditto for these two.

Quoted 12 lines
drivers/scsi/atari_NCR5380.c +0 -1
@@ -915,7 +913,6 @@ static int NCR5380_queue_command_lck(str
  	 * sense data is only guaranteed to be valid while the condition exists.
  	 */
 
-	local_irq_save(flags);
  	/* ++guenther: now that the issue queue is being set up, we can lock ST-DMA.
  	 * Otherwise a running NCR5380_main may steal the lock.
  	 * Lock before actually inserting due to fairness reasons explained in
@@ -928,11 +925,13 @@ static int NCR5380_queue_command_lck(str
  	 * because also a timer int can trigger an abort or reset, which would
  	 * alter queues and touch the lock.
  	 */

drivers/scsi/atari_NCR5380.c static int NCR5380_queue_command_lck(str · line 932

Quoted 10 lines
drivers/scsi/atari_NCR5380.c +5 -5
-	if (!IS_A_TT()) {
-		/* perhaps stop command timer here */
-		falcon_get_lock();
-		/* perhaps restart command timer here */
-	}
+	/* perhaps stop command timer here */
+	if (!falcon_get_lock())
+		return SCSI_MLQUEUE_HOST_BUSY;
+	/* perhaps restart command timer here */
+

The comments about stopping and restarting the command timer can be removed. In 2.4 kernels, the driver would tweak the timers and wait on the lock unconditionally, Can't ne done anymore, for so many reasons.

Quoted 164 lines
drivers/scsi/atari_NCR5380.c +3 -11
+	local_irq_save(flags);
+
  	if (!(hostdata->issue_queue) || (cmd->cmnd[0] == REQUEST_SENSE)) {
  		LIST(cmd, hostdata->issue_queue);
  		SET_NEXT(cmd, hostdata->issue_queue);
@@ -956,15 +955,13 @@ static int NCR5380_queue_command_lck(str
  	 * If we're not in an interrupt, we can call NCR5380_main()
  	 * unconditionally, because it cannot be already running.
  	 */
-	if (in_interrupt() || ((flags >> 8) & 7) >= 6)
+	if (in_interrupt() || irqs_disabled())
  		queue_main();
  	else
  		NCR5380_main(NULL);
  	return 0;
  }
 
-static DEF_SCSI_QCMD(NCR5380_queue_command)
-
  /*
   * Function : NCR5380_main (void)
   *
@@ -2555,10 +2552,6 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 
  	local_irq_save(flags);
 
-	if (!IS_A_TT() && !falcon_got_lock)
-		printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_abort\n",
-		       HOSTNO);
-
  	dprintk(NDEBUG_ABORT, "scsi%d: abort called basr 0x%02x, sr 0x%02x\n", HOSTNO,
  		    NCR5380_read(BUS_AND_STATUS_REG),
  		    NCR5380_read(STATUS_REG));
@@ -2757,10 +2750,6 @@ static int NCR5380_bus_reset(struct scsi
  	struct scsi_cmnd *connected, *disconnected_queue;
  #endif
 
-	if (!IS_A_TT() && !falcon_got_lock)
-		printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_reset\n",
-		       H_NO(cmd));
-
  	NCR5380_print_status(cmd->device->host);
 
  	/* get in phase */

Index: linux/drivers/scsi/atari_scsi.c
===================================================================

drivers/scsi/atari_scsi.c +15 -61
@@ -184,7 +184,7 @@ static void atari_scsi_fetch_restbytes(v
  static irqreturn_t scsi_tt_intr(int irq, void *dummy);
  static irqreturn_t scsi_falcon_intr(int irq, void *dummy);
  static void falcon_release_lock_if_possible(struct NCR5380_hostdata *hostdata);
-static void falcon_get_lock(void);
+static int falcon_get_lock(void);
  #ifdef CONFIG_ATARI_SCSI_RESET_BOOT
  static void atari_scsi_reset_boot(void);
  #endif
@@ -473,17 +473,10 @@ static void atari_scsi_fetch_restbytes(v
  #endif /* REAL_DMA */
 
 
-static int falcon_got_lock = 0;
-static DECLARE_WAIT_QUEUE_HEAD(falcon_fairness_wait);
-static int falcon_trying_lock = 0;
-static DECLARE_WAIT_QUEUE_HEAD(falcon_try_wait);
  static int falcon_dont_release = 0;
 
  /* This function releases the lock on the DMA chip if there is no
- * connected command and the disconnected queue is empty. On
- * releasing, instances of falcon_get_lock are awoken, that put
- * themselves to sleep for fairness. They can now try to get the lock
- * again (but others waiting longer more probably will win).
+ * connected command and the disconnected queue is empty.
   */
 
  static void falcon_release_lock_if_possible(struct NCR5380_hostdata *hostdata)
@@ -495,20 +488,12 @@ static void falcon_release_lock_if_possi
 
  	local_irq_save(flags);
 
-	if (falcon_got_lock && !hostdata->disconnected_queue &&
-	    !hostdata->issue_queue && !hostdata->connected) {
-
-		if (falcon_dont_release) {
-#if 0
-			printk("WARNING: Lock release not allowed. Ignored\n");
-#endif
-			local_irq_restore(flags);
-			return;
-		}
-		falcon_got_lock = 0;
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !falcon_dont_release &&
+	    stdma_is_locked_by(scsi_falcon_intr))
  		stdma_release();
-		wake_up(&falcon_fairness_wait);
-	}
 
  	local_irq_restore(flags);
  }
@@ -517,51 +502,20 @@ static void falcon_release_lock_if_possi
   * If the DMA isn't locked already for SCSI, it tries to lock it by
   * calling stdma_lock(). But if the DMA is locked by the SCSI code and
   * there are other drivers waiting for the chip, we do not issue the
- * command immediately but wait on 'falcon_fairness_queue'. We will be
- * waked up when the DMA is unlocked by some SCSI interrupt. After that
- * we try to get the lock again.
- * But we must be prepared that more than one instance of
- * falcon_get_lock() is waiting on the fairness queue. They should not
- * try all at once to call stdma_lock(), one is enough! For that, the
- * first one sets 'falcon_trying_lock', others that see that variable
- * set wait on the queue 'falcon_try_wait'.
- * Complicated, complicated.... Sigh...
+ * command immediately but tell the SCSI mid-layer to defer.
   */
 
-static void falcon_get_lock(void)
+static int falcon_get_lock(void)
  {
-	unsigned long flags;
-
  	if (IS_A_TT())
-		return;
+		return 1;
 
-	local_irq_save(flags);
-
-	wait_event_cmd(falcon_fairness_wait,
-		in_interrupt() || !falcon_got_lock || !stdma_others_waiting(),
-		local_irq_restore(flags),
-		local_irq_save(flags));
-
-	while (!falcon_got_lock) {
-		if (in_irq())
-			panic("Falcon SCSI hasn't ST-DMA lock in interrupt");
-		if (!falcon_trying_lock) {
-			falcon_trying_lock = 1;
-			stdma_lock(scsi_falcon_intr, NULL);
-			falcon_got_lock = 1;
-			falcon_trying_lock = 0;
-			wake_up(&falcon_try_wait);
-		} else {
-			wait_event_cmd(falcon_try_wait,
-				falcon_got_lock && !falcon_trying_lock,
-				local_irq_restore(flags),
-				local_irq_save(flags));
-		}
+	if (in_interrupt()) {
+		return stdma_try_lock(scsi_falcon_intr, NULL);
+	} else {
+		stdma_lock(scsi_falcon_intr, NULL);
+		return 1;
  	}
-
-	local_irq_restore(flags);
-	if (!falcon_got_lock)
-		panic("Falcon SCSI: someone stole the lock :-(\n");
  }
 
 
author
#51 lore raw

Re: [PATCH v2 22/36] atari_scsi: Fix atari_scsi deadlocks on Falcon

Quoted 13 lines · Michael Schmitz
Quoted 13 lines

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
--- linux.orig/drivers/scsi/atari_NCR5380.c 2014-10-27 16:25:36.000000000
+1100
+++ linux/drivers/scsi/atari_NCR5380.c 2014-10-27 16:25:45.000000000
+1100

drivers/scsi/atari_NCR5380.c +2 -1
@@ -879,10 +879,10 @@ static void NCR5380_exit(struct Scsi_Hos
   *
   */
  -static int NCR5380_queue_command_lck(struct scsi_cmnd *cmd,
-                                     void (*done)(struct scsi_cmnd *))
+static int NCR5380_queue_command(struct Scsi_Host *instance,
+                                 struct scsi_cmnd *cmd)
Quoted 8 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_exit(struct Scsi_Hos · line 887

Quoted 5 lines
drivers/scsi/atari_NCR5380.c +1 -1
  {
-	SETUP_HOSTDATA(cmd->device->host);
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
   struct scsi_cmnd *tmp;
   unsigned long flags;

Nitpick - why did this change set go into this particular patch? Because you are converting from NCR5380_queue_command_lck to NCR5380_queue_command?

That's right.

The SETUP_HOSTDATA macro does not appear in NCR5380.c, it is peculiar to atari_NCR5380.c. Like so much pre-processor abuse in these drivers, this example is undesirable as it harms readability, whereas the shost_priv() convention is common and readily understood.

So the uniform adoption of,

	struct NCR5380_hostdata *hostdata = shost_priv(instance);

is the purpose of a different patch (unsent). I have more unsent patches to fix up other weird macros in atari_NCR5380.c like HOSTDATA, H_NO, etc.

It's instructive to compare this change with the use of the NCR5380_local_declare() macro in NCR5380.c, which was long ago dropped from atari_NCR5380.c (and quite rightly so).

Quoted 14 lines
Quoted 14 lines
drivers/scsi/atari_NCR5380.c +1 -1
  @@ -893,7 +893,7 @@ static int NCR5380_queue_command_lck(str
    printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag
    set\n",
           H_NO(cmd));
  		cmd->result = (DID_ERROR << 16);
-		done(cmd);
+		cmd->scsi_done(cmd);
   	return 0;
  	}
  #endif /* (NDEBUG & NDEBUG_NO_WRITE) */
@@ -904,8 +904,6 @@ static int NCR5380_queue_command_lck(str
    */
 
Quoted 8 lines

drivers/scsi/atari_NCR5380.c static int NCR5380_queue_command_lck(str · line 909

Quoted 6 lines
drivers/scsi/atari_NCR5380.c +0 -2
  	SET_NEXT(cmd, NULL);
-	cmd->scsi_done = done;
-
   cmd->result = 0;
 
   /*

Ditto for these two.

Again, it follows from the differences in the formal parameters between NCR5380_queue_command_lck() and NCR5380_queue_command().

Quoted 19 lines
Quoted 19 lines
drivers/scsi/atari_NCR5380.c +1 -5
@@ -915,7 +913,6 @@ static int NCR5380_queue_command_lck(str
    * sense data is only guaranteed to be valid while the condition exists.
    */
  -	local_irq_save(flags);
   /* ++guenther: now that the issue queue is being set up, we can lock
   ST-DMA.
    * Otherwise a running NCR5380_main may steal the lock.
    * Lock before actually inserting due to fairness reasons explained in
@@ -928,11 +925,13 @@ static int NCR5380_queue_command_lck(str
    * because also a timer int can trigger an abort or reset, which would
    * alter queues and touch the lock.
    */
-	if (!IS_A_TT()) {
-		/* perhaps stop command timer here */
-		falcon_get_lock();
-		/* perhaps restart command timer here */
-	}
+	/* perhaps stop command timer here */
Quoted 8 lines

drivers/scsi/atari_NCR5380.c static int NCR5380_queue_command_lck(str · line 932

Quoted 4 lines
drivers/scsi/atari_NCR5380.c +4 -0
+	if (!falcon_get_lock())
+		return SCSI_MLQUEUE_HOST_BUSY;
+	/* perhaps restart command timer here */
+

The comments about stopping and restarting the command timer can be removed. In 2.4 kernels, the driver would tweak the timers and wait on the lock unconditionally, Can't ne done anymore, for so many reasons.

Well, you sent an acked-by for this patch, so I'm a bit confused. Do you want me to re-spin it?

maintainer
#52 lore raw

Re: [PATCH v2 22/36] atari_scsi: Fix atari_scsi deadlocks on Falcon

Finn,

Quoted 24 lines
Quoted 14 lines
Quoted 14 lines

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
--- linux.orig/drivers/scsi/atari_NCR5380.c 2014-10-27 16:25:36.000000000
+1100
+++ linux/drivers/scsi/atari_NCR5380.c 2014-10-27 16:25:45.000000000
+1100

drivers/scsi/atari_NCR5380.c +2 -1
@@ -879,10 +879,10 @@ static void NCR5380_exit(struct Scsi_Hos
   *
   */
  -static int NCR5380_queue_command_lck(struct scsi_cmnd *cmd,
-                                     void (*done)(struct scsi_cmnd *))
+static int NCR5380_queue_command(struct Scsi_Host *instance,
+                                 struct scsi_cmnd *cmd)
Quoted 9 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_exit(struct Scsi_Hos · line 888

Quoted 6 lines
drivers/scsi/atari_NCR5380.c +1 -1
  {
-	SETUP_HOSTDATA(cmd->device->host);
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
   struct scsi_cmnd *tmp;
   unsigned long flags;
 

Nitpick - why did this change set go into this particular patch? Because you are converting from NCR5380_queue_command_lck to NCR5380_queue_command?

Quoted 2 lines

That's right.

OK, I just wanted to understand why it's being combined with the stram.c patch (and the directly resulting changes in the SCSI driver).

The change to NCR5380_queue_command() can only now be done, as a result of the deadlock fixes in this patch, so it follows logically. Makes perfectly good sense to me now, thanks.

Quoted 18 lines
Quoted 18 lines
Quoted 18 lines
drivers/scsi/atari_NCR5380.c +1 -3
  @@ -893,7 +893,7 @@ static int NCR5380_queue_command_lck(str
    printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag
    set\n",
           H_NO(cmd));
  		cmd->result = (DID_ERROR << 16);
-		done(cmd);
+		cmd->scsi_done(cmd);
   	return 0;
  	}
  #endif /* (NDEBUG & NDEBUG_NO_WRITE) */
@@ -904,8 +904,6 @@ static int NCR5380_queue_command_lck(str
    */
 
  	SET_NEXT(cmd, NULL);
-	cmd->scsi_done = done;
-
   cmd->result = 0;
 
Quoted 7 lines
Quoted 4 lines

Review static int NCR5380_queue_command_lck(str · line 909

Quoted 2 lines
(quoted diff) +0 -0
   /*

Ditto for these two.

Again, it follows from the differences in the formal parameters between NCR5380_queue_command_lck() and NCR5380_queue_command().

Yep, I got that bit. Thanks for the explanation, and apologies for the noise.

Quoted 27 lines
Quoted 17 lines
Quoted 17 lines
drivers/scsi/atari_NCR5380.c +0 -4
@@ -915,7 +913,6 @@ static int NCR5380_queue_command_lck(str
    * sense data is only guaranteed to be valid while the condition exists.
    */
  -	local_irq_save(flags);
   /* ++guenther: now that the issue queue is being set up, we can lock
   ST-DMA.
    * Otherwise a running NCR5380_main may steal the lock.
    * Lock before actually inserting due to fairness reasons explained in
@@ -928,11 +925,13 @@ static int NCR5380_queue_command_lck(str
    * because also a timer int can trigger an abort or reset, which would
    * alter queues and touch the lock.
    */
-	if (!IS_A_TT()) {
-		/* perhaps stop command timer here */
-		falcon_get_lock();
-		/* perhaps restart command timer here */
Quoted 9 lines

drivers/scsi/atari_NCR5380.c static int NCR5380_queue_command_lck(str

Quoted 7 lines
drivers/scsi/atari_NCR5380.c +5 -1
-	}
+	/* perhaps stop command timer here */
+	if (!falcon_get_lock())
+		return SCSI_MLQUEUE_HOST_BUSY;
+	/* perhaps restart command timer here */
+
 

The comments about stopping and restarting the command timer can be removed. In 2.4 kernels, the driver would tweak the timers and wait on the lock unconditionally, Can't ne done anymore, for so many reasons.

Quoted 2 lines

Well, you sent an acked-by for this patch, so I'm a bit confused. Do you want me to re-spin it?

Not at all - this was just something I wanted to raise for future patches, before it slips my mind, again. Sorry I did not make that clear at all.

I expect we will have an opportunity to address this when we embark on a wider cleanup of comments throughout the driver - most of these comments were for the 0.9 kernel series and might still be somewhat germane up to 2.4. Might be totally misleading now.

Not a priority at all - I know you have bigger fish to fry. I should not have brought it up in this context.

No problems at all with this patch (or indeed with the rest of the series).

Cheers,

Michael

author
#53 lore raw

PATCH v2 23/36 atari_scsi: Convert to platform device

In reply to Finn Thain

Convert atari_scsi to platform device and eliminate scsi_register().

Validate __setup options later on so that module options are checked as well.

Remove the comment about the scsi mid-layer disabling the host irq as it is no longer true (AFAICT). Also remove the obsolete slow interrupt stuff (IRQ_TYPE_SLOW == 0 anyway).

---

Changes since v1:
- Remove unnecessary return -ENODEV branch.
- Move IRQ constants to platform resources.
- Always assign instance->irq so that the atari_NCR5380.c core driver can adopt the NCR5380.c interpretation of instance->irq.

---
 arch/m68k/atari/config.c  |   27 ++
 drivers/scsi/atari_scsi.c |  424 ++++++++++++++++++++++------------------------
 drivers/scsi/atari_scsi.h |   17 -
 3 files changed, 237 insertions(+), 231 deletions(-)
arch/m68k/atari/config.c +27 -0
Index: linux/arch/m68k/atari/config.c
===================================================================
@@ -858,6 +858,24 @@ static struct platform_device *atari_net
 };
 #endif /* CONFIG_ATARI_ETHERNEC */
 
+#ifdef CONFIG_ATARI_SCSI
+static const struct resource atari_scsi_st_rsrc[] __initconst = {
+	{
+		.flags = IORESOURCE_IRQ,
+		.start = IRQ_MFP_FSCSI,
+		.end   = IRQ_MFP_FSCSI,
+	},
+};
+
+static const struct resource atari_scsi_tt_rsrc[] __initconst = {
+	{
+		.flags = IORESOURCE_IRQ,
+		.start = IRQ_TT_MFP_SCSI,
+		.end   = IRQ_TT_MFP_SCSI,
+	},
+};
+#endif
+
 int __init atari_platform_init(void)
 {
 	int rv = 0;
@@ -892,6 +910,15 @@ int __init atari_platform_init(void)
 	}
 #endif
 
+#ifdef CONFIG_ATARI_SCSI
+	if (ATARIHW_PRESENT(ST_SCSI))
+		platform_device_register_simple("atari_scsi", -1,
+			atari_scsi_st_rsrc, ARRAY_SIZE(atari_scsi_st_rsrc));
+	else if (ATARIHW_PRESENT(TT_SCSI))
+		platform_device_register_simple("atari_scsi", -1,
+			atari_scsi_tt_rsrc, ARRAY_SIZE(atari_scsi_tt_rsrc));
+#endif
+
 	return rv;
 }
 
drivers/scsi/atari_scsi.c +210 -214

487 lines not on this page · raw message

drivers/scsi/atari_scsi.h +0 -17
Index: linux/drivers/scsi/atari_scsi.h
===================================================================
@@ -18,23 +18,6 @@
 /* (I_HAVE_OVERRUNS stuff removed) */
 
 #ifndef ASM
-/* The values for CMD_PER_LUN and CAN_QUEUE are somehow arbitrary. Higher
- * values should work, too; try it! (but cmd_per_lun costs memory!) */
-
-/* But there seems to be a bug somewhere that requires CAN_QUEUE to be
- * 2*CMD_PER_LUN. At least on a TT, no spurious timeouts seen since
- * changed CMD_PER_LUN... */
-
-/* Note: The Falcon currently uses 8/1 setting due to unsolved problems with
- * cmd_per_lun != 1 */
-
-#define ATARI_TT_CAN_QUEUE		16
-#define ATARI_TT_CMD_PER_LUN		8
-#define ATARI_TT_SG_TABLESIZE		SG_ALL
-
-#define ATARI_FALCON_CAN_QUEUE		8
-#define ATARI_FALCON_CMD_PER_LUN	1
-#define ATARI_FALCON_SG_TABLESIZE	SG_NONE
 
 #define	NCR5380_implementation_fields	/* none */
 
Reviewed-by on v2 23/36
#54 lore raw

Re: [PATCH v2 23/36] atari_scsi: Convert to platform device

Quoted 10 lines · Finn Thain

Convert atari_scsi to platform device and eliminate scsi_register().

Validate __setup options later on so that module options are checked as well.

Remove the comment about the scsi mid-layer disabling the host irq as it is no longer true (AFAICT). Also remove the obsolete slow interrupt stuff (IRQ_TYPE_SLOW == 0 anyway).

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#55 lore raw

PATCH v2 24/36 atari_scsi: Remove header

In reply to Finn Thain

The #defines in atari_scsi.h are intended to influence subsequent #includes in atari_scsi.c. IMHO, that's too convoluted.

Remove atari_scsi.h by moving those macro definitions to atari_scsi.c, consistent with other NCR5380 drivers.

---
 drivers/scsi/atari_scsi.c |   35 ++++++++++++++++++++++++++---------
 drivers/scsi/atari_scsi.h |   40 ----------------------------------------
 2 files changed, 26 insertions(+), 49 deletions(-)
drivers/scsi/atari_scsi.c +26 -9
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -64,15 +64,7 @@
 /**************************************************************************/
 
 
-
 #include <linux/module.h>
-
-/* For the Atari version, use only polled IO or REAL_DMA */
-#define	REAL_DMA
-/* Support tagged queuing? (on devices that are able to... :-) */
-#define	SUPPORT_TAGS
-#define	MAX_TAGS 32
-
 #include <linux/types.h>
 #include <linux/delay.h>
 #include <linux/blkdev.h>
@@ -92,9 +84,34 @@
 
 #include <scsi/scsi_host.h>
 
-#include "atari_scsi.h"
+/* Definitions for the core NCR5380 driver. */
+
+#define REAL_DMA
+#define SUPPORT_TAGS
+#define MAX_TAGS                        32
+
+#define NCR5380_implementation_fields   /* none */
+
+#define NCR5380_read(reg)               atari_scsi_reg_read(reg)
+#define NCR5380_write(reg, value)       atari_scsi_reg_write(reg, value)
+
+#define NCR5380_queue_command           atari_scsi_queue_command
+#define NCR5380_abort                   atari_scsi_abort
+#define NCR5380_show_info               atari_scsi_show_info
+#define NCR5380_info                    atari_scsi_info
+
+#define NCR5380_dma_read_setup(instance, data, count) \
+        atari_scsi_dma_setup(instance, data, count, 0)
+#define NCR5380_dma_write_setup(instance, data, count) \
+        atari_scsi_dma_setup(instance, data, count, 1)
+#define NCR5380_dma_residual(instance) \
+        atari_scsi_dma_residual(instance)
+#define NCR5380_dma_xfer_len(instance, cmd, phase) \
+        atari_dma_xfer_len(cmd->SCp.this_residual, cmd, !((phase) & SR_IO))
+
 #include "NCR5380.h"
 
+
 #define	IS_A_TT()	ATARIHW_PRESENT(TT_SCSI)
 
 #define	SCSI_DMA_WRITE_P(elt,val)				\
drivers/scsi/atari_scsi.h deleted +0 -40
Index: linux/drivers/scsi/atari_scsi.h
===================================================================
@@ -1,40 +0,0 @@
-/*
- * atari_scsi.h -- Header file for the Atari native SCSI driver
- *
- * Copyright 1994 Roman Hodek <[email protected]>
- *
- * (Loosely based on the work of Robert De Vries' team)
- *
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file COPYING in the main directory of this archive
- * for more details.
- *
- */
-
-
-#ifndef ATARI_SCSI_H
-#define ATARI_SCSI_H
-
-/* (I_HAVE_OVERRUNS stuff removed) */
-
-#ifndef ASM
-
-#define	NCR5380_implementation_fields	/* none */
-
-#define NCR5380_read(reg)		  atari_scsi_reg_read( reg )
-#define NCR5380_write(reg, value) atari_scsi_reg_write( reg, value )
-
-#define NCR5380_queue_command atari_scsi_queue_command
-#define NCR5380_abort atari_scsi_abort
-#define NCR5380_show_info atari_scsi_show_info
-#define NCR5380_info atari_scsi_info
-#define NCR5380_dma_read_setup(inst,d,c) atari_scsi_dma_setup (inst, d, c, 0)
-#define NCR5380_dma_write_setup(inst,d,c) atari_scsi_dma_setup (inst, d, c, 1)
-#define NCR5380_dma_residual(inst) atari_scsi_dma_residual( inst )
-#define	NCR5380_dma_xfer_len(i,cmd,phase) \
-	atari_dma_xfer_len(cmd->SCp.this_residual,cmd,((phase) & SR_IO) ? 0 : 1)
-
-#endif /* ndef ASM */
-#endif /* ATARI_SCSI_H */
-
-
Reviewed-by on v2 24/36
#56 lore raw

Re: [PATCH v2 24/36] atari_scsi: Remove header

Quoted 7 lines · Finn Thain

The #defines in atari_scsi.h are intended to influence subsequent #includes in atari_scsi.c. IMHO, that's too convoluted.

Remove atari_scsi.h by moving those macro definitions to atari_scsi.c, consistent with other NCR5380 drivers.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#57 lore raw

PATCH v2 25/36 sun3_scsi: Convert to platform device

In reply to Finn Thain

Convert sun3_scsi to platform device and eliminate scsi_register().

---

Changes since v1:
- Use NO_IRQ instead of IRQ_NONE.
- Move device IRQ and address constants to platform resources.
- Test idprom->id_machtype before registering platform device instead of during platform driver probe.
- Omit pointless instance->n_io_port assignment.

---
 arch/m68k/sun3/config.c  |   60 +++++++
 drivers/scsi/sun3_scsi.c |  390 ++++++++++++++++++++++-------------------------
 drivers/scsi/sun3_scsi.h |   17 --
 3 files changed, 245 insertions(+), 222 deletions(-)
arch/m68k/sun3/config.c +60 -0
Index: linux/arch/m68k/sun3/config.c
===================================================================
@@ -16,6 +16,7 @@
 #include <linux/console.h>
 #include <linux/init.h>
 #include <linux/bootmem.h>
+#include <linux/platform_device.h>
 
 #include <asm/oplib.h>
 #include <asm/setup.h>
@@ -27,6 +28,7 @@
 #include <asm/sun3mmu.h>
 #include <asm/rtc.h>
 #include <asm/machdep.h>
+#include <asm/machines.h>
 #include <asm/idprom.h>
 #include <asm/intersil.h>
 #include <asm/irq.h>
@@ -169,3 +171,61 @@ static void __init sun3_sched_init(irq_h
         intersil_clear();
 }
 
+#ifdef CONFIG_SUN3_SCSI
+
+static const struct resource sun3_scsi_vme_rsrc[] __initconst = {
+	{
+		.flags = IORESOURCE_IRQ,
+		.start = SUN3_VEC_VMESCSI0,
+		.end   = SUN3_VEC_VMESCSI0,
+	}, {
+		.flags = IORESOURCE_MEM,
+		.start = 0xff200000,
+		.end   = 0xff200000 + PAGE_SIZE - 1,
+	}, {
+		.flags = IORESOURCE_IRQ,
+		.start = SUN3_VEC_VMESCSI1,
+		.end   = SUN3_VEC_VMESCSI1,
+	}, {
+		.flags = IORESOURCE_MEM,
+		.start = 0xff204000,
+		.end   = 0xff204000 + PAGE_SIZE - 1,
+	},
+};
+
+/*
+ * Int: level 2 autovector
+ * IO: type 1, base 0x00140000, 5 bits phys space: A<4..0>
+ */
+static const struct resource sun3_scsi_rsrc[] __initconst = {
+	{
+		.flags = IORESOURCE_IRQ,
+		.start = 2,
+		.end   = 2,
+	}, {
+		.flags = IORESOURCE_MEM,
+		.start = 0x00140000,
+		.end   = 0x00140000 + PAGE_SIZE - 1,
+	},
+};
+
+int __init sun3_platform_init(void)
+{
+	switch (idprom->id_machtype) {
+	case SM_SUN3 | SM_3_160:
+	case SM_SUN3 | SM_3_260:
+		platform_device_register_simple("sun3_scsi_vme", -1,
+			sun3_scsi_vme_rsrc, ARRAY_SIZE(sun3_scsi_vme_rsrc));
+		break;
+	case SM_SUN3 | SM_3_50:
+	case SM_SUN3 | SM_3_60:
+		platform_device_register_simple("sun3_scsi", -1,
+			sun3_scsi_rsrc, ARRAY_SIZE(sun3_scsi_rsrc));
+		break;
+	}
+	return 0;
+}
+
+arch_initcall(sun3_platform_init);
+
+#endif
drivers/scsi/sun3_scsi.c +185 -205

452 lines not on this page · raw message

drivers/scsi/sun3_scsi.h +0 -17
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -18,25 +18,8 @@
 #ifndef SUN3_SCSI_H
 #define SUN3_SCSI_H
 
-/*
- * Int: level 2 autovector
- * IO: type 1, base 0x00140000, 5 bits phys space: A<4..0>
- */
-#define IRQ_SUN3_SCSI 2
-#define IOBASE_SUN3_SCSI 0x00140000
-
-#define IOBASE_SUN3_VMESCSI 0xff200000
-
 #define MAX_TAGS 32
 
-#include <scsi/scsicam.h>
-
-#ifdef SUN3_SCSI_VME
-#define SUN3_SCSI_NAME "Sun3 NCR5380 VME SCSI"
-#else
-#define SUN3_SCSI_NAME "Sun3 NCR5380 SCSI"
-#endif
-
 #define NCR5380_implementation_fields /* none */
 
 #define NCR5380_local_declare() \
Reviewed-by on v2 25/36
#58 lore raw

Re: [PATCH v2 25/36] sun3_scsi: Convert to platform device

Quoted 3 lines · Finn Thain

Convert sun3_scsi to platform device and eliminate scsi_register().

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
#59 lore raw

Re: [PATCH v2 25/36] sun3_scsi: Convert to platform device

In reply to Finn Thain
Quoted 8 lines · Finn Thain
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +1 -0
@@ -169,3 +171,61 @@ static void __init sun3_sched_init(irq_h
         intersil_clear();
 }
 
+#ifdef CONFIG_SUN3_SCSI

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 184

Quoted 10 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +10 -0
+
+static const struct resource sun3_scsi_vme_rsrc[] __initconst = {
+       {
+               .flags = IORESOURCE_IRQ,
+               .start = SUN3_VEC_VMESCSI0,
+               .end   = SUN3_VEC_VMESCSI0,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0xff200000,
+               .end   = 0xff200000 + PAGE_SIZE - 1,

PAGE_SIZE is a software kernel configuration option, not a hardware property. It makes sense to use it in an ioremap() call, but not in a platform device's resource, which describes the hardware.

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 192

Quoted 8 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +8 -0
+       }, {
+               .flags = IORESOURCE_IRQ,
+               .start = SUN3_VEC_VMESCSI1,
+               .end   = SUN3_VEC_VMESCSI1,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0xff204000,
+               .end   = 0xff204000 + PAGE_SIZE - 1,

Likewise

Quoted 6 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +6 -0
+       },
+};
+
+/*
+ * Int: level 2 autovector
+ * IO: type 1, base 0x00140000, 5 bits phys space: A<4..0>

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 208

Quoted 10 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +10 -0
+ */
+static const struct resource sun3_scsi_rsrc[] __initconst = {
+       {
+               .flags = IORESOURCE_IRQ,
+               .start = 2,
+               .end   = 2,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0x00140000,
+               .end   = 0x00140000 + PAGE_SIZE - 1,

Likewise

According to the Sun-3 Architecture Manual v2.0 (May 1985), end should be 0x0014001f.

I guess the resource length is 0x20 for VME SCSI, too?

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 209

Quoted 1 line
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +1 -0
+       },

Gr{oetje,eeting}s,

Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- [email protected]

In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds

author
#60 lore raw

Re: [PATCH v2 25/36] sun3_scsi: Convert to platform device

Quoted 54 lines · Geert Uytterhoeven
Quoted 8 lines · Finn Thain
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +1 -0
@@ -169,3 +171,61 @@ static void __init sun3_sched_init(irq_h
         intersil_clear();
 }
 
+#ifdef CONFIG_SUN3_SCSI

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 184

Quoted 10 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +10 -0
+
+static const struct resource sun3_scsi_vme_rsrc[] __initconst = {
+       {
+               .flags = IORESOURCE_IRQ,
+               .start = SUN3_VEC_VMESCSI0,
+               .end   = SUN3_VEC_VMESCSI0,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0xff200000,
+               .end   = 0xff200000 + PAGE_SIZE - 1,

PAGE_SIZE is a software kernel configuration option, not a hardware property. It makes sense to use it in an ioremap() call, but not in a platform device's resource, which describes the hardware.

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 192

Quoted 8 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +8 -0
+       }, {
+               .flags = IORESOURCE_IRQ,
+               .start = SUN3_VEC_VMESCSI1,
+               .end   = SUN3_VEC_VMESCSI1,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0xff204000,
+               .end   = 0xff204000 + PAGE_SIZE - 1,

Likewise

Quoted 6 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +6 -0
+       },
+};
+
+/*
+ * Int: level 2 autovector
+ * IO: type 1, base 0x00140000, 5 bits phys space: A<4..0>

arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 static void __init sun3_sched_init(irq_h · line 208

Quoted 10 lines
arch/m68k/sun3/config.c 2014-10-27 16:25:50.000000000 +1100 renamed from arch/m68k/sun3/config.c 2014-10-27 16:17:59.000000000 +1100 +10 -0
+ */
+static const struct resource sun3_scsi_rsrc[] __initconst = {
+       {
+               .flags = IORESOURCE_IRQ,
+               .start = 2,
+               .end   = 2,
+       }, {
+               .flags = IORESOURCE_MEM,
+               .start = 0x00140000,
+               .end   = 0x00140000 + PAGE_SIZE - 1,

Likewise

Quoted 2 lines

According to the Sun-3 Architecture Manual v2.0 (May 1985), end should be 0x0014001f.

OK. Where did you find that, BTW?

Quoted 2 lines

I guess the resource length is 0x20 for VME SCSI, too?

For VME SCSI it would need to be 8 + sizeof(struct sun3_dma_regs) which I think equals 0x22:

struct sun3_dma_regs {
unsigned short dma_addr_hi; /* vme only */
unsigned short dma_addr_lo; /* vme only */
unsigned short dma_count_hi; /* vme only */
unsigned short dma_count_lo; /* vme only */
unsigned short udc_data; /* udc dma data reg (obio only) */ unsigned short udc_addr; /* uda dma addr reg (obio only) */ unsigned short fifo_data; /* fifo data reg, holds extra byte on
odd dma reads */
unsigned short fifo_count;
unsigned short csr; /* control/status reg */ unsigned short bpack_hi; /* vme only */
unsigned short bpack_lo; /* vme only */
unsigned short ivect; /* vme only */
unsigned short fifo_count_hi; /* vme only */
};

I'll make these changes and re-spin the patch series once Hannes' questions have been resolved. Thanks for reviewing.

#61 lore raw

Re: [PATCH v2 25/36] sun3_scsi: Convert to platform device

Quoted 4 lines · Finn Thain
Quoted 2 lines

According to the Sun-3 Architecture Manual v2.0 (May 1985), end should be 0x0014001f.

OK. Where did you find that, BTW?

In my local collection of hardware docs I downloaded eons ago ;-) Fortunately it hasn't disappeared from the Internet, unlike many others docs I've collected over the years:

https://www.google.be/search?q=Sun-3_Architecture_Manual_Ver_2.0_May85.pdf

Quoted 4 lines
Quoted 1 line

I guess the resource length is 0x20 for VME SCSI, too?

For VME SCSI it would need to be 8 + sizeof(struct sun3_dma_regs) which I think equals 0x22:

IC.

Gr{oetje,eeting}s,

Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- [email protected]

In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds

author
#62 lore raw

PATCH v2 26/36 sun3_scsi: Move macro definitions

In reply to Finn Thain

The #defines in sun3_scsi.h are intended to influence subsequent #includes in sun3_scsi.c. IMHO, that's too convoluted.

Move sun3_scsi.h macro definitions to sun3_scsi.c, consistent with other NCR5380 drivers.

Omit the unused NCR5380_local_declare() and NCR5380_setup() macros.

---
 drivers/scsi/sun3_scsi.c |   45 ++++++++++++++++++++++++++++++++-------------
 drivers/scsi/sun3_scsi.h |   25 -------------------------
 2 files changed, 32 insertions(+), 38 deletions(-)
drivers/scsi/sun3_scsi.c +32 -13
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -33,18 +33,42 @@
 #include <asm/io.h>
 #include <asm/dvma.h>
 
-/* dma on! */
-#define REAL_DMA
-
 #include <scsi/scsi_host.h>
 #include "sun3_scsi.h"
-#include "NCR5380.h"
 
-extern int sun3_map_test(unsigned long, char *);
+/* Definitions for the core NCR5380 driver. */
 
-/*#define RESET_BOOT */
+#define REAL_DMA
+#define RESET_RUN_DONE
 /* #define SUPPORT_TAGS */
 
+/* #define MAX_TAGS                     32 */
+
+#define NCR5380_implementation_fields   /* none */
+
+#define NCR5380_read(reg)               sun3scsi_read(reg)
+#define NCR5380_write(reg, value)       sun3scsi_write(reg, value)
+
+#define NCR5380_queue_command           sun3scsi_queue_command
+#define NCR5380_bus_reset               sun3scsi_bus_reset
+#define NCR5380_abort                   sun3scsi_abort
+#define NCR5380_show_info               sun3scsi_show_info
+#define NCR5380_info                    sun3scsi_info
+
+#define NCR5380_dma_read_setup(instance, data, count) \
+        sun3scsi_dma_setup(data, count, 0)
+#define NCR5380_dma_write_setup(instance, data, count) \
+        sun3scsi_dma_setup(data, count, 1)
+#define NCR5380_dma_residual(instance) \
+        sun3scsi_dma_residual(instance)
+#define NCR5380_dma_xfer_len(instance, cmd, phase) \
+        sun3scsi_dma_xfer_len(cmd->SCp.this_residual, cmd, !((phase) & SR_IO))
+
+#include "NCR5380.h"
+
+
+extern int sun3_map_test(unsigned long, char *);
+
 #ifdef SUN3_SCSI_VME
 #define ENABLE_IRQ()
 #else
@@ -65,9 +89,7 @@ module_param(setup_use_tagged_queuing, i
 static int setup_hostid = -1;
 module_param(setup_hostid, int, 0);
 
-static struct scsi_cmnd *sun3_dma_setup_done = NULL;
-
-#define	RESET_RUN_DONE
+/* #define RESET_BOOT */
 
 #define	AFTER_RESET_DELAY	(HZ/2)
 
@@ -80,6 +102,7 @@ static struct scsi_cmnd *sun3_dma_setup_
 /* minimum number of bytes to do dma on */
 #define SUN3_DMA_MINSIZE 128
 
+static struct scsi_cmnd *sun3_dma_setup_done;
 static unsigned char *sun3_scsi_regp;
 static volatile struct sun3_dma_regs *dregs;
 static struct sun3_udc_regs *udc_regs;
@@ -131,9 +154,6 @@ static inline void sun3_udc_write(unsign
 static void sun3_scsi_reset_boot(struct Scsi_Host *instance)
 {
 	unsigned long end;
-
-	NCR5380_local_declare();
-	NCR5380_setup(instance);
 	
 	/*
 	 * Do a SCSI reset to clean up the bus during initialization. No
@@ -210,7 +230,6 @@ static irqreturn_t scsi_sun3_intr(int ir
 void sun3_sun3_debug (void)
 {
 	unsigned long flags;
-	NCR5380_local_declare();
 
 	if (default_instance) {
 			local_irq_save(flags);
drivers/scsi/sun3_scsi.h +0 -25
Index: linux/drivers/scsi/sun3_scsi.h
===================================================================
@@ -18,31 +18,6 @@
 #ifndef SUN3_SCSI_H
 #define SUN3_SCSI_H
 
-#define MAX_TAGS 32
-
-#define NCR5380_implementation_fields /* none */
-
-#define NCR5380_local_declare() \
-        struct Scsi_Host *_instance
-
-#define NCR5380_setup(instance) \
-        _instance = instance
-
-#define NCR5380_read(reg) sun3scsi_read(reg)
-#define NCR5380_write(reg, value) sun3scsi_write(reg, value)
-
-#define NCR5380_queue_command sun3scsi_queue_command
-#define NCR5380_bus_reset sun3scsi_bus_reset
-#define NCR5380_abort sun3scsi_abort
-#define NCR5380_show_info sun3scsi_show_info
-#define NCR5380_info sun3scsi_info
-#define NCR5380_dma_xfer_len(i, cmd, phase) \
-        sun3scsi_dma_xfer_len(cmd->SCp.this_residual,cmd,((phase) & SR_IO) ? 0 : 1)
-
-#define NCR5380_dma_write_setup(instance, data, count) sun3scsi_dma_setup(data, count, 1)
-#define NCR5380_dma_read_setup(instance, data, count) sun3scsi_dma_setup(data, count, 0)
-#define NCR5380_dma_residual sun3scsi_dma_residual
-
 /* additional registers - mainly DMA control regs */
 /* these start at regbase + 8 -- directly after the NCR regs */
 struct sun3_dma_regs {
Reviewed-by on v2 26/36
#63 lore raw

Re: [PATCH v2 26/36] sun3_scsi: Move macro definitions

Quoted 9 lines · Finn Thain

The #defines in sun3_scsi.h are intended to influence subsequent #includes in sun3_scsi.c. IMHO, that's too convoluted.

Move sun3_scsi.h macro definitions to sun3_scsi.c, consistent with other NCR5380 drivers.

Omit the unused NCR5380_local_declare() and NCR5380_setup() macros.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#64 lore raw

PATCH v2 27/36 ncr5380: Remove ENABLE_IRQ/DISABLE_IRQ macros

In reply to Finn Thain

atari_NCR5380.c enables its IRQ when it is already enabled. Sun3 doesn't use the ENABLE_IRQ/DISABLE_IRQ cruft. Remove it.

---
 drivers/scsi/atari_NCR5380.c |    2 --
 drivers/scsi/atari_scsi.c    |   21 ---------------------
 drivers/scsi/sun3_NCR5380.c  |    2 --
 drivers/scsi/sun3_scsi.c     |    7 -------
 4 files changed, 32 deletions(-)
drivers/scsi/atari_NCR5380.c +0 -2
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -1229,7 +1229,6 @@ static irqreturn_t NCR5380_intr(int irq,
 		NCR5380_dprint(NDEBUG_INTR, instance);
 		if ((NCR5380_read(STATUS_REG) & (SR_SEL|SR_IO)) == (SR_SEL|SR_IO)) {
 			done = 0;
-			ENABLE_IRQ();
 			dprintk(NDEBUG_INTR, "scsi%d: SEL interrupt\n", HOSTNO);
 			NCR5380_reselect(instance);
 			(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
@@ -1259,7 +1258,6 @@ static irqreturn_t NCR5380_intr(int irq,
 				dprintk(NDEBUG_INTR, "scsi%d: PHASE MISM or EOP interrupt\n", HOSTNO);
 				NCR5380_dma_complete( instance );
 				done = 0;
-				ENABLE_IRQ();
 			} else
 #endif /* REAL_DMA */
 			{
drivers/scsi/atari_scsi.c +0 -21
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -157,23 +157,6 @@ static inline unsigned long SCSI_DMA_GET
 	return adr;
 }
 
-static inline void ENABLE_IRQ(void)
-{
-	if (IS_A_TT())
-		atari_enable_irq(IRQ_TT_MFP_SCSI);
-	else
-		atari_enable_irq(IRQ_MFP_FSCSI);
-}
-
-static inline void DISABLE_IRQ(void)
-{
-	if (IS_A_TT())
-		atari_disable_irq(IRQ_TT_MFP_SCSI);
-	else
-		atari_disable_irq(IRQ_MFP_FSCSI);
-}
-
-
 #define HOSTDATA_DMALEN		(((struct NCR5380_hostdata *) \
 				(atari_scsi_host->hostdata))->dma_len)
 
@@ -373,10 +356,6 @@ static irqreturn_t scsi_tt_intr(int irq,
 
 	NCR5380_intr(irq, dummy);
 
-#if 0
-	/* To be sure the int is not masked */
-	atari_enable_irq(IRQ_TT_MFP_SCSI);
-#endif
 	return IRQ_HANDLED;
 }
 
drivers/scsi/sun3_NCR5380.c +0 -2
Index: linux/drivers/scsi/sun3_NCR5380.c
===================================================================
@@ -1155,7 +1155,6 @@ static irqreturn_t NCR5380_intr (int irq
 	NCR5380_dprint(NDEBUG_INTR, instance);
 	if ((NCR5380_read(STATUS_REG) & (SR_SEL|SR_IO)) == (SR_SEL|SR_IO)) {
 	    done = 0;
-//	    ENABLE_IRQ();
 	    dprintk(NDEBUG_INTR, "scsi%d: SEL interrupt\n", HOSTNO);
 	    NCR5380_reselect(instance);
 	    (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
@@ -1188,7 +1187,6 @@ static irqreturn_t NCR5380_intr (int irq
 		dprintk(NDEBUG_INTR, "scsi%d: PHASE MISM or EOP interrupt\n", HOSTNO);
 		NCR5380_dma_complete( instance );
 		done = 0;
-//		ENABLE_IRQ();
 	    } else
 #endif /* REAL_DMA */
 	    {
drivers/scsi/sun3_scsi.c +0 -7
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -69,13 +69,6 @@
 
 extern int sun3_map_test(unsigned long, char *);
 
-#ifdef SUN3_SCSI_VME
-#define ENABLE_IRQ()
-#else
-#define	ENABLE_IRQ()	enable_irq( IRQ_SUN3_SCSI ); 
-#endif
-
-
 static int setup_can_queue = -1;
 module_param(setup_can_queue, int, 0);
 static int setup_cmd_per_lun = -1;
Reviewed-by on v2 27/36
#65 lore raw

Re: [PATCH v2 27/36] ncr5380: Remove ENABLE_IRQ/DISABLE_IRQ macros

Quoted 5 lines · Finn Thain

atari_NCR5380.c enables its IRQ when it is already enabled. Sun3 doesn't use the ENABLE_IRQ/DISABLE_IRQ cruft. Remove it.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#66 lore raw

PATCH v2 28/36 atari_NCR5380: Refactor Falcon special cases

In reply to Finn Thain

Make the atari_NCR5380.c core driver usable by sun3_scsi, mac_scsi and others by moving some of the Falcon-specific code out of the core driver:
!IS_A_TT, atari_read_overruns and falcon_dont_release. Replace these with hostdata variables and flags. FLAG_CHECK_LAST_BYTE_SENT is unused in atari_NCR5380.c so don't set it.

---
 drivers/scsi/NCR5380.h       |    4 ++++
 drivers/scsi/atari_NCR5380.c |   30 +++++++++++++++---------------
 drivers/scsi/atari_scsi.c    |   21 ++++++++++++---------
 3 files changed, 31 insertions(+), 24 deletions(-)
drivers/scsi/atari_scsi.c +12 -9
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -196,8 +196,6 @@ static char		*atari_dma_orig_addr;
 /* mask for address bits that can't be used with the ST-DMA */
 static unsigned long	atari_dma_stram_mask;
 #define STRAM_ADDR(a)	(((a) & atari_dma_stram_mask) == 0)
-/* number of bytes to cut from a transfer to handle NCR overruns */
-static int atari_read_overruns;
 #endif
 
 static int setup_can_queue = -1;
@@ -446,8 +444,6 @@ static void atari_scsi_fetch_restbytes(v
 #endif /* REAL_DMA */
 
 
-static int falcon_dont_release = 0;
-
 /* This function releases the lock on the DMA chip if there is no
  * connected command and the disconnected queue is empty.
  */
@@ -464,7 +460,7 @@ static void falcon_release_lock_if_possi
 	if (!hostdata->disconnected_queue &&
 	    !hostdata->issue_queue &&
 	    !hostdata->connected &&
-	    !falcon_dont_release &&
+	    !hostdata->retain_dma_intr &&
 	    stdma_is_locked_by(scsi_falcon_intr))
 		stdma_release();
 
@@ -847,6 +843,7 @@ static int __init atari_scsi_probe(struc
 	struct Scsi_Host *instance;
 	int error;
 	struct resource *irq;
+	int host_flags = 0;
 
 	irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
 	if (!irq)
@@ -943,7 +940,9 @@ static int __init atari_scsi_probe(struc
 
 	instance->irq = irq->start;
 
-	NCR5380_init(instance, 0);
+	host_flags |= IS_A_TT() ? 0 : FLAG_LATE_DMA_SETUP;
+
+	NCR5380_init(instance, host_flags);
 
 	if (IS_A_TT()) {
 		error = request_irq(instance->irq, scsi_tt_intr, 0,
@@ -966,12 +965,16 @@ static int __init atari_scsi_probe(struc
 		 *
 		 * In principle it should be sufficient to do max. 1 byte with
 		 * PIO, but there is another problem on the Medusa with the DMA
-		 * rest data register. So 'atari_read_overruns' is currently set
+		 * rest data register. So read_overruns is currently set
 		 * to 4 to avoid having transfers that aren't a multiple of 4.
 		 * If the rest data bug is fixed, this can be lowered to 1.
 		 */
-		if (MACH_IS_MEDUSA)
-			atari_read_overruns = 4;
+		if (MACH_IS_MEDUSA) {
+			struct NCR5380_hostdata *hostdata =
+				shost_priv(instance);
+
+			hostdata->read_overruns = 4;
+		}
 #endif
 	} else {
 		/* Nothing to do for the interrupt: the ST-DMA is initialized
drivers/scsi/NCR5380.h +4 -0
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -241,6 +241,7 @@
 #define FLAG_NCR53C400			4	/* NCR53c400 */
 #define FLAG_NO_PSEUDO_DMA		8	/* Inhibit DMA */
 #define FLAG_DTC3181E			16	/* DTC3181E */
+#define FLAG_LATE_DMA_SETUP		32	/* Setup NCR before DMA H/W */
 
 #ifndef ASM
 struct NCR5380_hostdata {
@@ -269,6 +270,9 @@ struct NCR5380_hostdata {
 	struct delayed_work coroutine;		/* our co-routine */
 	struct scsi_eh_save ses;
 	char info[256];
+	int read_overruns;                /* number of bytes to cut from a
+	                                   * transfer to handle chip overruns */
+	int retain_dma_intr;
 #ifdef PSEUDO_DMA
 	unsigned spin_max_r;
 	unsigned spin_max_w;
drivers/scsi/atari_NCR5380.c +15 -15
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -839,7 +839,7 @@ static int __init NCR5380_init(struct Sc
 	hostdata->connected = NULL;
 	hostdata->issue_queue = NULL;
 	hostdata->disconnected_queue = NULL;
-	hostdata->flags = FLAG_CHECK_LAST_BYTE_SENT;
+	hostdata->flags = flags;
 
 	if (!the_template) {
 		the_template = instance->hostt;
@@ -1056,7 +1056,7 @@ static void NCR5380_main(struct work_str
 						hostdata->issue_queue = NEXT(tmp);
 					}
 					SET_NEXT(tmp, NULL);
-					falcon_dont_release++;
+					hostdata->retain_dma_intr++;
 
 					/* reenable interrupts after finding one */
 					local_irq_restore(flags);
@@ -1084,7 +1084,7 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
-						falcon_dont_release--;
+						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
 						falcon_release_lock_if_possible(hostdata);
 						break;
@@ -1096,7 +1096,7 @@ static void NCR5380_main(struct work_str
 #ifdef SUPPORT_TAGS
 						cmd_free_tag(tmp);
 #endif
-						falcon_dont_release--;
+						hostdata->retain_dma_intr--;
 						local_irq_restore(flags);
 						dprintk(NDEBUG_MAIN, "scsi%d: main(): select() failed, "
 							    "returned to issue_queue\n", HOSTNO);
@@ -1153,7 +1153,7 @@ static void NCR5380_dma_complete(struct
 		return;
 	}
 
-	if (atari_read_overruns) {
+	if (hostdata->read_overruns) {
 		p = hostdata->connected->SCp.phase;
 		if (p & SR_IO) {
 			udelay(10);
@@ -1183,9 +1183,9 @@ static void NCR5380_dma_complete(struct
 	*data += transfered;
 	*count -= transfered;
 
-	if (atari_read_overruns) {
+	if (hostdata->read_overruns) {
 		if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
-			cnt = toPIO = atari_read_overruns;
+			cnt = toPIO = hostdata->read_overruns;
 			if (overrun) {
 				dprintk(NDEBUG_DMA, "Got an input overrun, using saved byte\n");
 				*(*data)++ = saved_data;
@@ -1840,8 +1840,8 @@ static int NCR5380_transfer_dma(struct S
 		return -1;
 	}
 
-	if (atari_read_overruns && (p & SR_IO))
-		c -= atari_read_overruns;
+	if (hostdata->read_overruns && (p & SR_IO))
+		c -= hostdata->read_overruns;
 
 	dprintk(NDEBUG_DMA, "scsi%d: initializing DMA for %s, %d bytes %s %p\n",
 		   HOSTNO, (p & SR_IO) ? "reading" : "writing",
@@ -1853,7 +1853,7 @@ static int NCR5380_transfer_dma(struct S
 	NCR5380_write(MODE_REG, MR_BASE | MR_DMA_MODE | MR_ENABLE_EOP_INTR | MR_MONITOR_BSY);
 #endif /* def REAL_DMA  */
 
-	if (IS_A_TT()) {
+	if (!(hostdata->flags & FLAG_LATE_DMA_SETUP)) {
 		/* On the Medusa, it is a must to initialize the DMA before
 		 * starting the NCR. This is also the cleaner way for the TT.
 		 */
@@ -1871,7 +1871,7 @@ static int NCR5380_transfer_dma(struct S
 		NCR5380_write(START_DMA_SEND_REG, 0);
 	}
 
-	if (!IS_A_TT()) {
+	if (hostdata->flags & FLAG_LATE_DMA_SETUP) {
 		/* On the Falcon, the DMA setup must be done after the last */
 		/* NCR access, else the DMA setup gets trashed!
 		 */
@@ -2086,7 +2086,7 @@ static void NCR5380_information_transfer
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 					/* ++guenther: possible race with Falcon locking */
-					falcon_dont_release++;
+					hostdata->retain_dma_intr++;
 					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
@@ -2169,7 +2169,7 @@ static void NCR5380_information_transfer
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
 
-					falcon_dont_release--;
+					hostdata->retain_dma_intr--;
 					/* ++roman: For Falcon SCSI, release the lock on the
 					 * ST-DMA here if no other commands are waiting on the
 					 * disconnected queue.
@@ -2476,7 +2476,7 @@ static void NCR5380_reselect(struct Scsi
 #endif
 		    ) {
 			/* ++guenther: prevent race with falcon_release_lock */
-			falcon_dont_release++;
+			hostdata->retain_dma_intr++;
 			if (prev) {
 				REMOVE(prev, NEXT(prev), tmp, NEXT(tmp));
 				SET_NEXT(prev, NEXT(tmp));
@@ -2514,7 +2514,7 @@ static void NCR5380_reselect(struct Scsi
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);
-	falcon_dont_release--;
+	hostdata->retain_dma_intr--;
 }
 
 
Reviewed-by on v2 28/36
#67 lore raw

Re: [PATCH v2 28/36] atari_NCR5380: Refactor Falcon special cases

Quoted 7 lines · Finn Thain

Make the atari_NCR5380.c core driver usable by sun3_scsi, mac_scsi and others by moving some of the Falcon-specific code out of the core driver:
!IS_A_TT, atari_read_overruns and falcon_dont_release. Replace these with hostdata variables and flags. FLAG_CHECK_LAST_BYTE_SENT is unused in atari_NCR5380.c so don't set it.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#68 lore raw

PATCH v2 29/36 atari_NCR5380: Refactor Falcon locking

In reply to Finn Thain

Simplify falcon_release_lock_if_possible() by making callers responsible for disabling local IRQ's, which they must do anyway to correctly synchronize the ST DMA "lock" with core driver data structures. Move this synchronization logic to the core driver with which it is tightly coupled.

Other LLD's like sun3_scsi and mac_scsi that can make use of this core driver can just stub out the NCR5380_acquire_dma_irq() and NCR5380_release_dma_irq() calls so the compiler will eliminate the ST DMA code.

Remove a redundant local_irq_save/restore pair (irq's are disabled for interrupt handlers these days). Revise the locking for atari_scsi_bus_reset(): use local_irq_save/restore() instead of atari_turnoff/turnon_irq(). There is no guarantee that atari_scsi still holds the ST DMA lock during EH, so atari_turnoff/turnon_irq() could end up dropping an IDE or floppy interrupt.

---
 drivers/scsi/atari_NCR5380.c |   72 ++++++++++++++++++++++++++-----------------
 drivers/scsi/atari_scsi.c    |   47 ++++++++++------------------
 2 files changed, 62 insertions(+), 57 deletions(-)
drivers/scsi/atari_NCR5380.c +45 -27
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -926,7 +926,7 @@ static int NCR5380_queue_command(struct
 	 * alter queues and touch the lock.
 	 */
 	/* perhaps stop command timer here */
-	if (!falcon_get_lock())
+	if (!NCR5380_acquire_dma_irq(instance))
 		return SCSI_MLQUEUE_HOST_BUSY;
 	/* perhaps restart command timer here */
 
@@ -962,6 +962,18 @@ static int NCR5380_queue_command(struct
 	return 0;
 }
 
+static inline void maybe_release_dma_irq(struct Scsi_Host *instance)
+{
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+	/* Caller does the locking needed to set & test these data atomically */
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !hostdata->retain_dma_intr)
+		NCR5380_release_dma_irq(instance);
+}
+
 /*
  * Function : NCR5380_main (void)
  *
@@ -1084,9 +1096,11 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
+						local_irq_disable();
 						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
-						falcon_release_lock_if_possible(hostdata);
+						maybe_release_dma_irq(instance);
+						local_irq_restore(flags);
 						break;
 					} else {
 						local_irq_disable();
@@ -2085,11 +2099,12 @@ static void NCR5380_information_transfer
 				case COMMAND_COMPLETE:
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-					/* ++guenther: possible race with Falcon locking */
-					hostdata->retain_dma_intr++;
-					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
+
+					local_irq_save(flags);
+					hostdata->retain_dma_intr++;
+					hostdata->connected = NULL;
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 					if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
@@ -2148,17 +2163,17 @@ static void NCR5380_information_transfer
 
 						dprintk(NDEBUG_AUTOSENSE, "scsi%d: performing request sense\n", HOSTNO);
 
-						local_irq_save(flags);
 						LIST(cmd,hostdata->issue_queue);
 						SET_NEXT(cmd, hostdata->issue_queue);
 						hostdata->issue_queue = (struct scsi_cmnd *) cmd;
-						local_irq_restore(flags);
 						dprintk(NDEBUG_QUEUES, "scsi%d: REQUEST SENSE added to head of "
 							  "issue queue\n", H_NO(cmd));
 					} else {
 						cmd->scsi_done(cmd);
 					}
 
+					local_irq_restore(flags);
+
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					/*
 					 * Restore phase bits to 0 so an interrupted selection,
@@ -2169,12 +2184,14 @@ static void NCR5380_information_transfer
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
 
+					local_irq_save(flags);
 					hostdata->retain_dma_intr--;
 					/* ++roman: For Falcon SCSI, release the lock on the
 					 * ST-DMA here if no other commands are waiting on the
 					 * disconnected queue.
 					 */
-					falcon_release_lock_if_possible(hostdata);
+					maybe_release_dma_irq(instance);
+					local_irq_restore(flags);
 					return;
 				case MESSAGE_REJECT:
 					/* Accept message by clearing ACK */
@@ -2333,6 +2350,7 @@ static void NCR5380_information_transfer
 				hostdata->last_message = msgout;
 				NCR5380_transfer_pio(instance, &phase, &len, &data);
 				if (msgout == ABORT) {
+					local_irq_save(flags);
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 #else
@@ -2340,9 +2358,10 @@ static void NCR5380_information_transfer
 #endif
 					hostdata->connected = NULL;
 					cmd->result = DID_ERROR << 16;
-					cmd->scsi_done(cmd);
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
-					falcon_release_lock_if_possible(hostdata);
+					maybe_release_dma_irq(instance);
+					local_irq_restore(flags);
+					cmd->scsi_done(cmd);
 					return;
 				}
 				msgout = NOP;
@@ -2395,7 +2414,6 @@ static void NCR5380_reselect(struct Scsi
 	unsigned char msg[3];
 	unsigned char *data;
 	struct scsi_cmnd *tmp = NULL, *prev;
-/*	unsigned long flags; */
 
 	/*
 	 * Disable arbitration, etc. since the host adapter obviously
@@ -2475,8 +2493,6 @@ static void NCR5380_reselect(struct Scsi
 		    && (tag == tmp->tag)
 #endif
 		    ) {
-			/* ++guenther: prevent race with falcon_release_lock */
-			hostdata->retain_dma_intr++;
 			if (prev) {
 				REMOVE(prev, NEXT(prev), tmp, NEXT(tmp));
 				SET_NEXT(prev, NEXT(tmp));
@@ -2514,7 +2530,6 @@ static void NCR5380_reselect(struct Scsi
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);
-	hostdata->retain_dma_intr--;
 }
 
 
@@ -2590,12 +2605,12 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 #else
 			hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
 #endif
+			maybe_release_dma_irq(instance);
 			local_irq_restore(flags);
 			cmd->scsi_done(cmd);
-			falcon_release_lock_if_possible(hostdata);
 			return SUCCESS;
 		} else {
-/*			local_irq_restore(flags); */
+			local_irq_restore(flags);
 			printk("scsi%d: abort of connected command failed!\n", HOSTNO);
 			return FAILED;
 		}
@@ -2614,13 +2629,13 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 			(*prev) = NEXT(tmp);
 			SET_NEXT(tmp, NULL);
 			tmp->result = DID_ABORT << 16;
+			maybe_release_dma_irq(instance);
 			local_irq_restore(flags);
 			dprintk(NDEBUG_ABORT, "scsi%d: abort removed command from issue queue.\n",
 				    HOSTNO);
 			/* Tagged queuing note: no tag to free here, hasn't been assigned
 			 * yet... */
 			tmp->scsi_done(tmp);
-			falcon_release_lock_if_possible(hostdata);
 			return SUCCESS;
 		}
 	}
@@ -2698,15 +2713,22 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 #else
 					hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
 #endif
+					maybe_release_dma_irq(instance);
 					local_irq_restore(flags);
 					tmp->scsi_done(tmp);
-					falcon_release_lock_if_possible(hostdata);
 					return SUCCESS;
 				}
 			}
 		}
 	}
 
+	/* Maybe it is sufficient just to release the ST-DMA lock... (if
+	 * possible at all) At least, we should check if the lock could be
+	 * released after the abort, in case it is kept due to some bug.
+	 */
+	maybe_release_dma_irq(instance);
+	local_irq_restore(flags);
+
 	/*
 	 * Case 5 : If we reached this point, the command was not found in any of
 	 *	    the queues.
@@ -2717,15 +2739,8 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 	 * broke.
 	 */
 
-	local_irq_restore(flags);
 	printk(KERN_INFO "scsi%d: warning : SCSI command probably completed successfully before abortion\n", HOSTNO);
 
-	/* Maybe it is sufficient just to release the ST-DMA lock... (if
-	 * possible at all) At least, we should check if the lock could be
-	 * released after the abort, in case it is kept due to some bug.
-	 */
-	falcon_release_lock_if_possible(hostdata);
-
 	return FAILED;
 }
 
@@ -2741,14 +2756,15 @@ int NCR5380_abort(struct scsi_cmnd *cmd)
 
 static int NCR5380_bus_reset(struct scsi_cmnd *cmd)
 {
-	SETUP_HOSTDATA(cmd->device->host);
+	struct Scsi_Host *instance = cmd->device->host;
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
 	int i;
 	unsigned long flags;
 #if defined(RESET_RUN_DONE)
 	struct scsi_cmnd *connected, *disconnected_queue;
 #endif
 
-	NCR5380_print_status(cmd->device->host);
+	NCR5380_print_status(instance);
 
 	/* get in phase */
 	NCR5380_write(TARGET_COMMAND_REG,
@@ -2873,6 +2889,8 @@ static int NCR5380_bus_reset(struct scsi
 #ifdef REAL_DMA
 	hostdata->dma_len = 0;
 #endif
+
+	maybe_release_dma_irq(instance);
 	local_irq_restore(flags);
 
 	/* we did no complete reset of all commands, so a wakeup is required */
drivers/scsi/atari_scsi.c +17 -30

82 lines not on this page · raw message

#69 lore raw

Re: [PATCH v2 29/36] atari_NCR5380: Refactor Falcon locking

Quoted 95 lines · Finn Thain

Simplify falcon_release_lock_if_possible() by making callers responsible for disabling local IRQ's, which they must do anyway to correctly synchronize the ST DMA "lock" with core driver data structures. Move this synchronization logic to the core driver with which it is tightly coupled.

Other LLD's like sun3_scsi and mac_scsi that can make use of this core driver can just stub out the NCR5380_acquire_dma_irq() and NCR5380_release_dma_irq() calls so the compiler will eliminate the ST DMA code.

Remove a redundant local_irq_save/restore pair (irq's are disabled for interrupt handlers these days). Revise the locking for atari_scsi_bus_reset(): use local_irq_save/restore() instead of atari_turnoff/turnon_irq(). There is no guarantee that atari_scsi still holds the ST DMA lock during EH, so atari_turnoff/turnon_irq() could end up dropping an IDE or floppy interrupt.

---
 drivers/scsi/atari_NCR5380.c |   72 ++++++++++++++++++++++++++-----------------
 drivers/scsi/atari_scsi.c    |   47 ++++++++++------------------
 2 files changed, 62 insertions(+), 57 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +20 -7
@@ -926,7 +926,7 @@ static int NCR5380_queue_command(struct
 	 * alter queues and touch the lock.
 	 */
 	/* perhaps stop command timer here */
-	if (!falcon_get_lock())
+	if (!NCR5380_acquire_dma_irq(instance))
 		return SCSI_MLQUEUE_HOST_BUSY;
 	/* perhaps restart command timer here */
 
@@ -962,6 +962,18 @@ static int NCR5380_queue_command(struct
 	return 0;
 }
 
+static inline void maybe_release_dma_irq(struct Scsi_Host *instance)
+{
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+	/* Caller does the locking needed to set & test these data atomically */
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !hostdata->retain_dma_intr)
+		NCR5380_release_dma_irq(instance);
+}
+
 /*
  * Function : NCR5380_main (void)
  *
@@ -1084,9 +1096,11 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
+						local_irq_disable();
 						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
-						falcon_release_lock_if_possible(hostdata);
+						maybe_release_dma_irq(instance);
+						local_irq_restore(flags);
 						break;
 					} else {
 						local_irq_disable();
@@ -2085,11 +2099,12 @@ static void NCR5380_information_transfer
 				case COMMAND_COMPLETE:
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-					/* ++guenther: possible race with Falcon locking */
-					hostdata->retain_dma_intr++;
-					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
+
+					local_irq_save(flags);
+					hostdata->retain_dma_intr++;
+					hostdata->connected = NULL;
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 					if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
@@ -2148,17 +2163,17 @@ static void NCR5380_information_transfer
 
 						dprintk(NDEBUG_AUTOSENSE, "scsi%d: performing request sense\n", HOSTNO);
 
-						local_irq_save(flags);
 						LIST(cmd,hostdata->issue_queue);
 						SET_NEXT(cmd, hostdata->issue_queue);
 						hostdata->issue_queue = (struct scsi_cmnd *) cmd;
-						local_irq_restore(flags);
 						dprintk(NDEBUG_QUEUES, "scsi%d: REQUEST SENSE added to head of "

drivers/scsi/atari_NCR5380.c static void NCR5380_information_transfer · line 2179

Quoted 10 lines
drivers/scsi/atari_NCR5380.c +2 -0
 							  "issue queue\n", H_NO(cmd));
 					} else {
 						cmd->scsi_done(cmd);
 					}
 
+					local_irq_restore(flags);
+
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					/*
 					 * Restore phase bits to 0 so an interrupted selection,

Probably a stupid question, but you're disabling local interrupts. scsi_done() OTOH is triggering a soft irq. Does this work? Shouldn't we enable interrupts before calling scsi_done() ?

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#70 lore raw

Re: [PATCH v2 29/36] atari_NCR5380: Refactor Falcon locking

Quoted 102 lines · Hannes Reinecke
Quoted 101 lines · Finn Thain

Simplify falcon_release_lock_if_possible() by making callers responsible for disabling local IRQ's, which they must do anyway to correctly synchronize the ST DMA "lock" with core driver data structures. Move this synchronization logic to the core driver with which it is tightly coupled.

Other LLD's like sun3_scsi and mac_scsi that can make use of this core driver can just stub out the NCR5380_acquire_dma_irq() and NCR5380_release_dma_irq() calls so the compiler will eliminate the ST DMA code.

Remove a redundant local_irq_save/restore pair (irq's are disabled for interrupt handlers these days). Revise the locking for atari_scsi_bus_reset(): use local_irq_save/restore() instead of atari_turnoff/turnon_irq(). There is no guarantee that atari_scsi still holds the ST DMA lock during EH, so atari_turnoff/turnon_irq() could end up dropping an IDE or floppy interrupt.

---
 drivers/scsi/atari_NCR5380.c |   72 ++++++++++++++++++++++++++-----------------
 drivers/scsi/atari_scsi.c    |   47 ++++++++++------------------
 2 files changed, 62 insertions(+), 57 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +20 -7
@@ -926,7 +926,7 @@ static int NCR5380_queue_command(struct
 	 * alter queues and touch the lock.
 	 */
 	/* perhaps stop command timer here */
-	if (!falcon_get_lock())
+	if (!NCR5380_acquire_dma_irq(instance))
 		return SCSI_MLQUEUE_HOST_BUSY;
 	/* perhaps restart command timer here */
 
@@ -962,6 +962,18 @@ static int NCR5380_queue_command(struct
 	return 0;
 }
 
+static inline void maybe_release_dma_irq(struct Scsi_Host *instance)
+{
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+	/* Caller does the locking needed to set & test these data atomically */
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !hostdata->retain_dma_intr)
+		NCR5380_release_dma_irq(instance);
+}
+
 /*
  * Function : NCR5380_main (void)
  *
@@ -1084,9 +1096,11 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
+						local_irq_disable();
 						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
-						falcon_release_lock_if_possible(hostdata);
+						maybe_release_dma_irq(instance);
+						local_irq_restore(flags);
 						break;
 					} else {
 						local_irq_disable();
@@ -2085,11 +2099,12 @@ static void NCR5380_information_transfer
 				case COMMAND_COMPLETE:
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-					/* ++guenther: possible race with Falcon locking */
-					hostdata->retain_dma_intr++;
-					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
+
+					local_irq_save(flags);
+					hostdata->retain_dma_intr++;
+					hostdata->connected = NULL;
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 					if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
@@ -2148,17 +2163,17 @@ static void NCR5380_information_transfer
 
 						dprintk(NDEBUG_AUTOSENSE, "scsi%d: performing request sense\n", HOSTNO);
 
-						local_irq_save(flags);
 						LIST(cmd,hostdata->issue_queue);
 						SET_NEXT(cmd, hostdata->issue_queue);
 						hostdata->issue_queue = (struct scsi_cmnd *) cmd;
-						local_irq_restore(flags);
 						dprintk(NDEBUG_QUEUES, "scsi%d: REQUEST SENSE added to head of "
 							  "issue queue\n", H_NO(cmd));
 					} else {
 						cmd->scsi_done(cmd);
 					}
 
Quoted 7 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_information_transfer · line 2179

Quoted 5 lines
drivers/scsi/atari_NCR5380.c +2 -0
+					local_irq_restore(flags);
+
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					/*
 					 * Restore phase bits to 0 so an interrupted selection,

Probably a stupid question, but you're disabling local interrupts. scsi_done() OTOH is triggering a soft irq.

Isn't that how all bottom halves work?

Quoted 1 line

Does this work?

Yes, I've tested that particular code. I'm pretty sure Michael has too.

A quick search turned up another example of this in zfcp_fsf_fcp_cmnd_handler().

Quoted 1 line

Shouldn't we enable interrupts before calling scsi_done() ?

I don't see anything in the scsi_done() implementation in scsi_lib.c that would be problematic. The description says "This function is interrupt context safe". The same would have to apply to scsi_eh_done().

author
#71 lore raw

Re: [PATCH v2 29/36] atari_NCR5380: Refactor Falcon locking

Ping...

Quoted 129 lines · Finn Thain
Quoted 102 lines · Hannes Reinecke
Quoted 101 lines · Finn Thain

Simplify falcon_release_lock_if_possible() by making callers responsible for disabling local IRQ's, which they must do anyway to correctly synchronize the ST DMA "lock" with core driver data structures. Move this synchronization logic to the core driver with which it is tightly coupled.

Other LLD's like sun3_scsi and mac_scsi that can make use of this core driver can just stub out the NCR5380_acquire_dma_irq() and NCR5380_release_dma_irq() calls so the compiler will eliminate the ST DMA code.

Remove a redundant local_irq_save/restore pair (irq's are disabled for interrupt handlers these days). Revise the locking for atari_scsi_bus_reset(): use local_irq_save/restore() instead of atari_turnoff/turnon_irq(). There is no guarantee that atari_scsi still holds the ST DMA lock during EH, so atari_turnoff/turnon_irq() could end up dropping an IDE or floppy interrupt.

---
 drivers/scsi/atari_NCR5380.c |   72 ++++++++++++++++++++++++++-----------------
 drivers/scsi/atari_scsi.c    |   47 ++++++++++------------------
 2 files changed, 62 insertions(+), 57 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +20 -7
@@ -926,7 +926,7 @@ static int NCR5380_queue_command(struct
 	 * alter queues and touch the lock.
 	 */
 	/* perhaps stop command timer here */
-	if (!falcon_get_lock())
+	if (!NCR5380_acquire_dma_irq(instance))
 		return SCSI_MLQUEUE_HOST_BUSY;
 	/* perhaps restart command timer here */
 
@@ -962,6 +962,18 @@ static int NCR5380_queue_command(struct
 	return 0;
 }
 
+static inline void maybe_release_dma_irq(struct Scsi_Host *instance)
+{
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+	/* Caller does the locking needed to set & test these data atomically */
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !hostdata->retain_dma_intr)
+		NCR5380_release_dma_irq(instance);
+}
+
 /*
  * Function : NCR5380_main (void)
  *
@@ -1084,9 +1096,11 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
+						local_irq_disable();
 						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
-						falcon_release_lock_if_possible(hostdata);
+						maybe_release_dma_irq(instance);
+						local_irq_restore(flags);
 						break;
 					} else {
 						local_irq_disable();
@@ -2085,11 +2099,12 @@ static void NCR5380_information_transfer
 				case COMMAND_COMPLETE:
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-					/* ++guenther: possible race with Falcon locking */
-					hostdata->retain_dma_intr++;
-					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
+
+					local_irq_save(flags);
+					hostdata->retain_dma_intr++;
+					hostdata->connected = NULL;
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 					if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
@@ -2148,17 +2163,17 @@ static void NCR5380_information_transfer
 
 						dprintk(NDEBUG_AUTOSENSE, "scsi%d: performing request sense\n", HOSTNO);
 
-						local_irq_save(flags);
 						LIST(cmd,hostdata->issue_queue);
 						SET_NEXT(cmd, hostdata->issue_queue);
 						hostdata->issue_queue = (struct scsi_cmnd *) cmd;
-						local_irq_restore(flags);
 						dprintk(NDEBUG_QUEUES, "scsi%d: REQUEST SENSE added to head of "
 							  "issue queue\n", H_NO(cmd));
 					} else {
 						cmd->scsi_done(cmd);
 					}
 
Quoted 7 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_information_transfer · line 2179

Quoted 5 lines
drivers/scsi/atari_NCR5380.c +2 -0
+					local_irq_restore(flags);
+
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					/*
 					 * Restore phase bits to 0 so an interrupted selection,

Probably a stupid question, but you're disabling local interrupts. scsi_done() OTOH is triggering a soft irq.

Isn't that how all bottom halves work?

Quoted 1 line

Does this work?

Yes, I've tested that particular code. I'm pretty sure Michael has too.

A quick search turned up another example of this in zfcp_fsf_fcp_cmnd_handler().

Quoted 1 line

Shouldn't we enable interrupts before calling scsi_done() ?

I don't see anything in the scsi_done() implementation in scsi_lib.c that would be problematic. The description says "This function is interrupt context safe". The same would have to apply to scsi_eh_done().

Reviewed-by
#72 lore raw

Re: [PATCH v2 29/36] atari_NCR5380: Refactor Falcon locking

Quoted 134 lines · Finn Thain

Ping...

Quoted 129 lines · Finn Thain
Quoted 102 lines · Hannes Reinecke
Quoted 101 lines · Finn Thain

Simplify falcon_release_lock_if_possible() by making callers responsible for disabling local IRQ's, which they must do anyway to correctly synchronize the ST DMA "lock" with core driver data structures. Move this synchronization logic to the core driver with which it is tightly coupled.

Other LLD's like sun3_scsi and mac_scsi that can make use of this core driver can just stub out the NCR5380_acquire_dma_irq() and NCR5380_release_dma_irq() calls so the compiler will eliminate the ST DMA code.

Remove a redundant local_irq_save/restore pair (irq's are disabled for interrupt handlers these days). Revise the locking for atari_scsi_bus_reset(): use local_irq_save/restore() instead of atari_turnoff/turnon_irq(). There is no guarantee that atari_scsi still holds the ST DMA lock during EH, so atari_turnoff/turnon_irq() could end up dropping an IDE or floppy interrupt.

---
 drivers/scsi/atari_NCR5380.c |   72 ++++++++++++++++++++++++++-----------------
 drivers/scsi/atari_scsi.c    |   47 ++++++++++------------------
 2 files changed, 62 insertions(+), 57 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +20 -7
@@ -926,7 +926,7 @@ static int NCR5380_queue_command(struct
 	 * alter queues and touch the lock.
 	 */
 	/* perhaps stop command timer here */
-	if (!falcon_get_lock())
+	if (!NCR5380_acquire_dma_irq(instance))
 		return SCSI_MLQUEUE_HOST_BUSY;
 	/* perhaps restart command timer here */
 
@@ -962,6 +962,18 @@ static int NCR5380_queue_command(struct
 	return 0;
 }
 
+static inline void maybe_release_dma_irq(struct Scsi_Host *instance)
+{
+	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+
+	/* Caller does the locking needed to set & test these data atomically */
+	if (!hostdata->disconnected_queue &&
+	    !hostdata->issue_queue &&
+	    !hostdata->connected &&
+	    !hostdata->retain_dma_intr)
+		NCR5380_release_dma_irq(instance);
+}
+
 /*
  * Function : NCR5380_main (void)
  *
@@ -1084,9 +1096,11 @@ static void NCR5380_main(struct work_str
 					cmd_get_tag(tmp, tmp->cmnd[0] != REQUEST_SENSE);
 #endif
 					if (!NCR5380_select(instance, tmp)) {
+						local_irq_disable();
 						hostdata->retain_dma_intr--;
 						/* release if target did not response! */
-						falcon_release_lock_if_possible(hostdata);
+						maybe_release_dma_irq(instance);
+						local_irq_restore(flags);
 						break;
 					} else {
 						local_irq_disable();
@@ -2085,11 +2099,12 @@ static void NCR5380_information_transfer
 				case COMMAND_COMPLETE:
 					/* Accept message by clearing ACK */
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-					/* ++guenther: possible race with Falcon locking */
-					hostdata->retain_dma_intr++;
-					hostdata->connected = NULL;
 					dprintk(NDEBUG_QUEUES, "scsi%d: command for target %d, lun %llu "
 						  "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
+
+					local_irq_save(flags);
+					hostdata->retain_dma_intr++;
+					hostdata->connected = NULL;
 #ifdef SUPPORT_TAGS
 					cmd_free_tag(cmd);
 					if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
@@ -2148,17 +2163,17 @@ static void NCR5380_information_transfer
 
 						dprintk(NDEBUG_AUTOSENSE, "scsi%d: performing request sense\n", HOSTNO);
 
-						local_irq_save(flags);
 						LIST(cmd,hostdata->issue_queue);
 						SET_NEXT(cmd, hostdata->issue_queue);
 						hostdata->issue_queue = (struct scsi_cmnd *) cmd;
-						local_irq_restore(flags);
 						dprintk(NDEBUG_QUEUES, "scsi%d: REQUEST SENSE added to head of "
 							  "issue queue\n", H_NO(cmd));
 					} else {
 						cmd->scsi_done(cmd);
 					}
 
Quoted 7 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_information_transfer · line 2179

Quoted 5 lines
drivers/scsi/atari_NCR5380.c +2 -0
+					local_irq_restore(flags);
+
 					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					/*
 					 * Restore phase bits to 0 so an interrupted selection,

Probably a stupid question, but you're disabling local interrupts. scsi_done() OTOH is triggering a soft irq.

Isn't that how all bottom halves work?

Quoted 1 line

Does this work?

Yes, I've tested that particular code. I'm pretty sure Michael has too.

A quick search turned up another example of this in zfcp_fsf_fcp_cmnd_handler().

Quoted 1 line

Shouldn't we enable interrupts before calling scsi_done() ?

I don't see anything in the scsi_done() implementation in scsi_lib.c that would be problematic. The description says "This function is interrupt context safe". The same would have to apply to scsi_eh_done().

Ah. I thought I've had it answered, but apparently I ran into one of our network hickups.

Cheers,
Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 21284 (AG Nürnberg)
author
#73 lore raw

PATCH v2 30/36 atari_NCR5380: Merge from sun3_NCR5380.c

In reply to Finn Thain

There is very little difference between the sun3_NCR5380.c core driver and atari_NCR5380.c. The former is a fork of the latter.

Merge the sun3_NCR5380.c core driver into atari_NCR5380.c so that sun3_scsi.c can adopt the latter and the former can be deleted.

---

This patch brings some undesirable #ifdef's to atari_NCR5380. It's a small price to pay for the elimination of so much duplication. Eventually, with some testing, it should be possible to remove many of these.

Elimination of the SUN3_SCSI_VME macro is necessary to reach the goal of a single platform driver to replace the {atari,mac,sun3,sun3_vme}_scsi modules.

Elimination of the #ifdef CONFIG_SUN3 tests is not necessary. But some of these would go away if the sun3 driver followed the atari logic more closely, such as use of PIO vs DMA for certain phases and transfer sizes.

After applying this patch it is easy to compare the new atari_NCR5380.c with sun3_NCR5380.c, to check that they are equivalent. E.g.

$ cp drivers/scsi/{sun3,atari}_NCR5380.c /tmp
$ sed -i -e 's/  *$//'      /tmp/{sun3,atari}_NCR5380.c
$ scripts/Lindent -l96 -hnl /tmp/{sun3,atari}_NCR5380.c
$ meld                      /tmp/{sun3,atari}_NCR5380.c

One can see that the two implementations of tagged command queueing have diverged since the fork. The atari version has been updated and the sun3 implementation is unused as sun3_scsi.c does not define SUPPORT_TAGS.

The remaining differences are merge_contiguous_buffers() and the falcon locking code. The falcon code disappears when suitable macro definitions are provided in sun3_scsi.c. merge_contiguous_buffers() could be a problem for sun3 (due to a DMA setup in an odd place) so it is #ifdef'd for sun3 until the DMA setup discrepancies can be reconciled or moved out of the core driver.

---
 drivers/scsi/atari_NCR5380.c |  210 +++++++++++++++++++++++++++++++++++++++----
 drivers/scsi/atari_scsi.c    |    1 
 2 files changed, 195 insertions(+), 16 deletions(-)
drivers/scsi/atari_NCR5380.c +194 -16
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -71,6 +71,9 @@
  * 1.  Test linked command handling code after Eric is ready with
  *     the high level code.
  */
+
+/* Adapted for the sun3 by Sam Creasey. */
+
 #include <scsi/scsi_dbg.h>
 #include <scsi/scsi_transport_spi.h>
 
@@ -458,6 +461,7 @@ static void free_all_tags(void)
 
 static void merge_contiguous_buffers(struct scsi_cmnd *cmd)
 {
+#if !defined(CONFIG_SUN3)
 	unsigned long endaddr;
 #if (NDEBUG & NDEBUG_MERGING)
 	unsigned long oldlen = cmd->SCp.this_residual;
@@ -482,6 +486,7 @@ static void merge_contiguous_buffers(str
 		dprintk(NDEBUG_MERGING, "merged %d buffers from %p, new length %08x\n",
 			   cnt, cmd->SCp.ptr, cmd->SCp.this_residual);
 #endif
+#endif /* !defined(CONFIG_SUN3) */
 }
 
 /*
@@ -1043,12 +1048,10 @@ static void NCR5380_main(struct work_str
 			     prev = NULL; tmp; prev = tmp, tmp = NEXT(tmp)) {
 				u8 lun = tmp->device->lun;
 
-#if (NDEBUG & NDEBUG_LISTS)
-				if (prev != tmp)
-					printk("MAIN tmp=%p   target=%d   busy=%d lun=%llu\n",
-					       tmp, tmp->device->id, hostdata->busy[tmp->device->id],
-					       lun);
-#endif
+				dprintk(NDEBUG_LISTS,
+				        "MAIN tmp=%p target=%d busy=%d lun=%d\n",
+				        tmp, scmd_id(tmp), hostdata->busy[scmd_id(tmp)],
+				        lun);
 				/*  When we find one, remove it from the issue queue. */
 				/* ++guenther: possible race with Falcon locking */
 				if (
@@ -1157,9 +1160,11 @@ static void NCR5380_main(struct work_str
 static void NCR5380_dma_complete(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
-	int transfered, saved_data = 0, overrun = 0, cnt, toPIO;
-	unsigned char **data, p;
+	int transfered;
+	unsigned char **data;
 	volatile int *count;
+	int saved_data = 0, overrun = 0;
+	unsigned char p;
 
 	if (!hostdata->connected) {
 		printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "
@@ -1185,6 +1190,26 @@ static void NCR5380_dma_complete(struct
 		   HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
 		   NCR5380_read(STATUS_REG));
 
+#if defined(CONFIG_SUN3)
+	if ((sun3scsi_dma_finish(rq_data_dir(hostdata->connected->request)))) {
+		pr_err("scsi%d: overrun in UDC counter -- not prepared to deal with this!\n",
+		       instance->host_no);
+		pr_err("please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+
+	/* make sure we're not stuck in a data phase */
+	if ((NCR5380_read(BUS_AND_STATUS_REG) & (BASR_PHASE_MATCH | BASR_ACK)) ==
+	    (BASR_PHASE_MATCH | BASR_ACK)) {
+		pr_err("scsi%d: BASR %02x\n", instance->host_no,
+		       NCR5380_read(BUS_AND_STATUS_REG));
+		pr_err("scsi%d: bus stuck in data phase -- probably a single byte overrun!\n",
+		       instance->host_no);
+		pr_err("not prepared for this error! please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+#endif
+
 	(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
 	NCR5380_write(MODE_REG, MR_BASE);
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
@@ -1198,6 +1223,8 @@ static void NCR5380_dma_complete(struct
 	*count -= transfered;
 
 	if (hostdata->read_overruns) {
+		int cnt, toPIO;
+
 		if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
 			cnt = toPIO = hostdata->read_overruns;
 			if (overrun) {
@@ -1277,11 +1304,14 @@ static irqreturn_t NCR5380_intr(int irq,
 			{
 /* MS: Ignore unknown phase mismatch interrupts (caused by EOP interrupt) */
 				if (basr & BASR_PHASE_MATCH)
-					printk(KERN_NOTICE "scsi%d: unknown interrupt, "
+					dprintk(NDEBUG_INTR, "scsi%d: unknown interrupt, "
 					       "BASR 0x%x, MR 0x%x, SR 0x%x\n",
 					       HOSTNO, basr, NCR5380_read(MODE_REG),
 					       NCR5380_read(STATUS_REG));
 				(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_DMA_ENABLE;
+#endif
 			}
 		} /* if !(SELECTION || PARITY) */
 		handled = 1;
@@ -1290,6 +1320,9 @@ static irqreturn_t NCR5380_intr(int irq,
 		       "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
 		       NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
 		(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+		dregs->csr |= CSR_DMA_ENABLE;
+#endif
 	}
 
 	if (!done) {
@@ -1622,6 +1655,9 @@ static int NCR5380_select(struct Scsi_Ho
 #ifndef SUPPORT_TAGS
 	hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
 #endif
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
 
 	initialize_SCp(cmd);
 
@@ -1845,9 +1881,54 @@ static int NCR5380_transfer_dma(struct S
 	SETUP_HOSTDATA(instance);
 	register int c = *count;
 	register unsigned char p = *phase;
+	unsigned long flags;
+
+#if defined(CONFIG_SUN3)
+	/* sanity check */
+	if (!sun3_dma_setup_done) {
+		pr_err("scsi%d: transfer_dma without setup!\n",
+		       instance->host_no);
+		BUG();
+	}
+	hostdata->dma_len = c;
+
+	dprintk(NDEBUG_DMA, "scsi%d: initializing DMA for %s, %d bytes %s %p\n",
+		instance->host_no, (p & SR_IO) ? "reading" : "writing",
+		c, (p & SR_IO) ? "to" : "from", *data);
+
+	/* netbsd turns off ints here, why not be safe and do it too */
+	local_irq_save(flags);
+
+	/* send start chain */
+	sun3scsi_dma_start(c, *data);
+
+	if (p & SR_IO) {
+		NCR5380_write(TARGET_COMMAND_REG, 1);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, 0);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_INITIATOR_RECEIVE_REG, 0);
+	} else {
+		NCR5380_write(TARGET_COMMAND_REG, 0);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_DATA);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_SEND_REG, 0);
+	}
+
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_DMA_ENABLE;
+#endif
+
+	local_irq_restore(flags);
+
+	sun3_dma_active = 1;
+
+#else /* !defined(CONFIG_SUN3) */
 	register unsigned char *d = *data;
 	unsigned char tmp;
-	unsigned long flags;
 
 	if ((tmp = (NCR5380_read(STATUS_REG) & PHASE_MASK)) != p) {
 		*phase = tmp;
@@ -1895,6 +1976,8 @@ static int NCR5380_transfer_dma(struct S
 			NCR5380_dma_write_setup(instance, d, c);
 		local_irq_restore(flags);
 	}
+#endif /* !defined(CONFIG_SUN3) */
+
 	return 0;
 }
 #endif /* defined(REAL_DMA) */
@@ -1930,6 +2013,10 @@ static void NCR5380_information_transfer
 	unsigned char phase, tmp, extended_msg[10], old_phase = 0xff;
 	struct scsi_cmnd *cmd = (struct scsi_cmnd *) hostdata->connected;
 
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
+
 	while (1) {
 		tmp = NCR5380_read(STATUS_REG);
 		/* We only have a valid SCSI phase when REQ is asserted */
@@ -1939,6 +2026,33 @@ static void NCR5380_information_transfer
 				old_phase = phase;
 				NCR5380_dprint_phase(NDEBUG_INFORMATION, instance);
 			}
+#if defined(CONFIG_SUN3)
+			if (phase == PHASE_CMDOUT) {
+#if defined(REAL_DMA)
+				void *d;
+				unsigned long count;
+
+				if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
+					count = cmd->SCp.buffer->length;
+					d = sg_virt(cmd->SCp.buffer);
+				} else {
+					count = cmd->SCp.this_residual;
+					d = cmd->SCp.ptr;
+				}
+				/* this command setup for dma yet? */
+				if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != cmd)) {
+					if (cmd->request->cmd_type == REQ_TYPE_FS) {
+						sun3scsi_dma_setup(d, count,
+						                   rq_data_dir(cmd->request));
+						sun3_dma_setup_done = cmd;
+					}
+				}
+#endif
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_INTR;
+#endif
+			}
+#endif /* CONFIG_SUN3 */
 
 			if (sink && (phase != PHASE_MSGOUT)) {
 				NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
@@ -2000,8 +2114,11 @@ static void NCR5380_information_transfer
 				 */
 
 #if defined(REAL_DMA)
-				if (!cmd->device->borken &&
-				    (transfersize = NCR5380_dma_xfer_len(instance,cmd,phase)) > 31) {
+				if (
+#if !defined(CONFIG_SUN3)
+				    !cmd->device->borken &&
+#endif
+				    (transfersize = NCR5380_dma_xfer_len(instance, cmd, phase)) >= DMA_MIN_SIZE) {
 					len = transfersize;
 					cmd->SCp.phase = phase;
 					if (NCR5380_transfer_dma(instance, &phase,
@@ -2038,6 +2155,11 @@ static void NCR5380_information_transfer
 					NCR5380_transfer_pio(instance, &phase,
 							     (int *)&cmd->SCp.this_residual,
 							     (unsigned char **)&cmd->SCp.ptr);
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+				/* if we had intended to dma that command clear it */
+				if (sun3_dma_setup_done == cmd)
+					sun3_dma_setup_done = NULL;
+#endif
 				break;
 			case PHASE_MSGIN:
 				len = 1;
@@ -2243,6 +2365,9 @@ static void NCR5380_information_transfer
 					/* Wait for bus free to avoid nasty timeouts */
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
+#ifdef SUN3_SCSI_VME
+					dregs->csr |= CSR_DMA_ENABLE;
+#endif
 					return;
 					/*
 					 * The SCSI data pointer is *IMPLICITLY* saved on a disconnect
@@ -2402,17 +2527,20 @@ static void NCR5380_information_transfer
  */
 
 
+/* it might eventually prove necessary to do a dma setup on
+   reselection, but it doesn't seem to be needed now -- sam */
+
 static void NCR5380_reselect(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
 	unsigned char target_mask;
-	unsigned char lun, phase;
-	int len;
+	unsigned char lun;
 #ifdef SUPPORT_TAGS
 	unsigned char tag;
 #endif
 	unsigned char msg[3];
-	unsigned char *data;
+	int __maybe_unused len;
+	unsigned char __maybe_unused *data, __maybe_unused phase;
 	struct scsi_cmnd *tmp = NULL, *prev;
 
 	/*
@@ -2449,10 +2577,18 @@ static void NCR5380_reselect(struct Scsi
 	while (!(NCR5380_read(STATUS_REG) & SR_REQ))
 		;
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* acknowledge toggle to MSGIN */
+	NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(PHASE_MSGIN));
+
+	/* peek at the byte without really hitting the bus */
+	msg[0] = NCR5380_read(CURRENT_SCSI_DATA_REG);
+#else
 	len = 1;
 	data = msg;
 	phase = PHASE_MSGIN;
 	NCR5380_transfer_pio(instance, &phase, &len, &data);
+#endif
 
 	if (!(msg[0] & 0x80)) {
 		printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
@@ -2462,7 +2598,7 @@ static void NCR5380_reselect(struct Scsi
 	}
 	lun = (msg[0] & 0x07);
 
-#ifdef SUPPORT_TAGS
+#if defined(SUPPORT_TAGS) && !defined(CONFIG_SUN3)
 	/* If the phase is still MSGIN, the target wants to send some more
 	 * messages. In case it supports tagged queuing, this is probably a
 	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
@@ -2524,9 +2660,51 @@ static void NCR5380_reselect(struct Scsi
 		return;
 	}
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* engage dma setup for the command we just saw */
+	{
+		void *d;
+		unsigned long count;
+
+		if (!tmp->SCp.this_residual && tmp->SCp.buffers_residual) {
+			count = tmp->SCp.buffer->length;
+			d = sg_virt(tmp->SCp.buffer);
+		} else {
+			count = tmp->SCp.this_residual;
+			d = tmp->SCp.ptr;
+		}
+		/* setup this command for dma if not already */
+		if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != tmp)) {
+			sun3scsi_dma_setup(d, count, rq_data_dir(tmp->request));
+			sun3_dma_setup_done = tmp;
+		}
+	}
+
+	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
+#endif
+
 	/* Accept message by clearing ACK */
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 
+#if defined(SUPPORT_TAGS) && defined(CONFIG_SUN3)
+	/* If the phase is still MSGIN, the target wants to send some more
+	 * messages. In case it supports tagged queuing, this is probably a
+	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
+	 */
+	tag = TAG_NONE;
+	if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
+		/* Accept previous IDENTIFY message by clearing ACK */
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
+		len = 2;
+		data = msg + 1;
+		if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
+		    msg[1] == SIMPLE_QUEUE_TAG)
+			tag = msg[2];
+		dprintk(NDEBUG_TAGS, "scsi%d: target mask %02x, lun %d sent tag %d at reselection\n"
+			HOSTNO, target_mask, lun, tag);
+	}
+#endif
+
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);
drivers/scsi/atari_scsi.c +1 -0
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -89,6 +89,7 @@
 #define REAL_DMA
 #define SUPPORT_TAGS
 #define MAX_TAGS                        32
+#define DMA_MIN_SIZE                    32
 
 #define NCR5380_implementation_fields   /* none */
 
#74 lore raw

Re: [PATCH v2 30/36] atari_NCR5380: Merge from sun3_NCR5380.c

Quoted 96 lines · Finn Thain

There is very little difference between the sun3_NCR5380.c core driver and atari_NCR5380.c. The former is a fork of the latter.

Merge the sun3_NCR5380.c core driver into atari_NCR5380.c so that sun3_scsi.c can adopt the latter and the former can be deleted.

---

This patch brings some undesirable #ifdef's to atari_NCR5380. It's a small price to pay for the elimination of so much duplication. Eventually, with some testing, it should be possible to remove many of these.

Elimination of the SUN3_SCSI_VME macro is necessary to reach the goal of a single platform driver to replace the {atari,mac,sun3,sun3_vme}_scsi modules.

Elimination of the #ifdef CONFIG_SUN3 tests is not necessary. But some of these would go away if the sun3 driver followed the atari logic more closely, such as use of PIO vs DMA for certain phases and transfer sizes.

After applying this patch it is easy to compare the new atari_NCR5380.c with sun3_NCR5380.c, to check that they are equivalent. E.g.

$ cp drivers/scsi/{sun3,atari}_NCR5380.c /tmp
$ sed -i -e 's/  *$//'      /tmp/{sun3,atari}_NCR5380.c
$ scripts/Lindent -l96 -hnl /tmp/{sun3,atari}_NCR5380.c
$ meld                      /tmp/{sun3,atari}_NCR5380.c

One can see that the two implementations of tagged command queueing have diverged since the fork. The atari version has been updated and the sun3 implementation is unused as sun3_scsi.c does not define SUPPORT_TAGS.

The remaining differences are merge_contiguous_buffers() and the falcon locking code. The falcon code disappears when suitable macro definitions are provided in sun3_scsi.c. merge_contiguous_buffers() could be a problem for sun3 (due to a DMA setup in an odd place) so it is #ifdef'd for sun3 until the DMA setup discrepancies can be reconciled or moved out of the core driver.

---
 drivers/scsi/atari_NCR5380.c |  210 +++++++++++++++++++++++++++++++++++++++----
 drivers/scsi/atari_scsi.c    |    1 
 2 files changed, 195 insertions(+), 16 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +9 -6
@@ -71,6 +71,9 @@
  * 1.  Test linked command handling code after Eric is ready with
  *     the high level code.
  */
+
+/* Adapted for the sun3 by Sam Creasey. */
+
 #include <scsi/scsi_dbg.h>
 #include <scsi/scsi_transport_spi.h>
 
@@ -458,6 +461,7 @@ static void free_all_tags(void)
 
 static void merge_contiguous_buffers(struct scsi_cmnd *cmd)
 {
+#if !defined(CONFIG_SUN3)
 	unsigned long endaddr;
 #if (NDEBUG & NDEBUG_MERGING)
 	unsigned long oldlen = cmd->SCp.this_residual;
@@ -482,6 +486,7 @@ static void merge_contiguous_buffers(str
 		dprintk(NDEBUG_MERGING, "merged %d buffers from %p, new length %08x\n",
 			   cnt, cmd->SCp.ptr, cmd->SCp.this_residual);
 #endif
+#endif /* !defined(CONFIG_SUN3) */
 }
 
 /*
@@ -1043,12 +1048,10 @@ static void NCR5380_main(struct work_str
 			     prev = NULL; tmp; prev = tmp, tmp = NEXT(tmp)) {
 				u8 lun = tmp->device->lun;
 
-#if (NDEBUG & NDEBUG_LISTS)
-				if (prev != tmp)
-					printk("MAIN tmp=%p   target=%d   busy=%d lun=%llu\n",
-					       tmp, tmp->device->id, hostdata->busy[tmp->device->id],
-					       lun);
-#endif
+				dprintk(NDEBUG_LISTS,
+				        "MAIN tmp=%p target=%d busy=%d lun=%d\n",
+				        tmp, scmd_id(tmp), hostdata->busy[scmd_id(tmp)],
+				        lun);
 				/*  When we find one, remove it from the issue queue. */
 				/* ++guenther: possible race with Falcon locking */
 				if (
@@ -1157,9 +1160,11 @@ static void NCR5380_main(struct work_str
 static void NCR5380_dma_complete(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);

drivers/scsi/atari_NCR5380.c static void NCR5380_main(struct work_str · line 1170

Quoted 10 lines
drivers/scsi/atari_NCR5380.c +4 -2
-	int transfered, saved_data = 0, overrun = 0, cnt, toPIO;
-	unsigned char **data, p;
+	int transfered;
+	unsigned char **data;
 	volatile int *count;
+	int saved_data = 0, overrun = 0;
+	unsigned char p;
 
 	if (!hostdata->connected) {
 		printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "

nitpick: shouldn't that be 'transferred' ?

Quoted 329 lines
drivers/scsi/atari_NCR5380.c +181 -8
@@ -1185,6 +1190,26 @@ static void NCR5380_dma_complete(struct
 		   HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
 		   NCR5380_read(STATUS_REG));
 
+#if defined(CONFIG_SUN3)
+	if ((sun3scsi_dma_finish(rq_data_dir(hostdata->connected->request)))) {
+		pr_err("scsi%d: overrun in UDC counter -- not prepared to deal with this!\n",
+		       instance->host_no);
+		pr_err("please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+
+	/* make sure we're not stuck in a data phase */
+	if ((NCR5380_read(BUS_AND_STATUS_REG) & (BASR_PHASE_MATCH | BASR_ACK)) ==
+	    (BASR_PHASE_MATCH | BASR_ACK)) {
+		pr_err("scsi%d: BASR %02x\n", instance->host_no,
+		       NCR5380_read(BUS_AND_STATUS_REG));
+		pr_err("scsi%d: bus stuck in data phase -- probably a single byte overrun!\n",
+		       instance->host_no);
+		pr_err("not prepared for this error! please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+#endif
+
 	(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
 	NCR5380_write(MODE_REG, MR_BASE);
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
@@ -1198,6 +1223,8 @@ static void NCR5380_dma_complete(struct
 	*count -= transfered;
 
 	if (hostdata->read_overruns) {
+		int cnt, toPIO;
+
 		if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
 			cnt = toPIO = hostdata->read_overruns;
 			if (overrun) {
@@ -1277,11 +1304,14 @@ static irqreturn_t NCR5380_intr(int irq,
 			{
 /* MS: Ignore unknown phase mismatch interrupts (caused by EOP interrupt) */
 				if (basr & BASR_PHASE_MATCH)
-					printk(KERN_NOTICE "scsi%d: unknown interrupt, "
+					dprintk(NDEBUG_INTR, "scsi%d: unknown interrupt, "
 					       "BASR 0x%x, MR 0x%x, SR 0x%x\n",
 					       HOSTNO, basr, NCR5380_read(MODE_REG),
 					       NCR5380_read(STATUS_REG));
 				(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_DMA_ENABLE;
+#endif
 			}
 		} /* if !(SELECTION || PARITY) */
 		handled = 1;
@@ -1290,6 +1320,9 @@ static irqreturn_t NCR5380_intr(int irq,
 		       "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
 		       NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
 		(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+		dregs->csr |= CSR_DMA_ENABLE;
+#endif
 	}
 
 	if (!done) {
@@ -1622,6 +1655,9 @@ static int NCR5380_select(struct Scsi_Ho
 #ifndef SUPPORT_TAGS
 	hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
 #endif
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
 
 	initialize_SCp(cmd);
 
@@ -1845,9 +1881,54 @@ static int NCR5380_transfer_dma(struct S
 	SETUP_HOSTDATA(instance);
 	register int c = *count;
 	register unsigned char p = *phase;
+	unsigned long flags;
+
+#if defined(CONFIG_SUN3)
+	/* sanity check */
+	if (!sun3_dma_setup_done) {
+		pr_err("scsi%d: transfer_dma without setup!\n",
+		       instance->host_no);
+		BUG();
+	}
+	hostdata->dma_len = c;
+
+	dprintk(NDEBUG_DMA, "scsi%d: initializing DMA for %s, %d bytes %s %p\n",
+		instance->host_no, (p & SR_IO) ? "reading" : "writing",
+		c, (p & SR_IO) ? "to" : "from", *data);
+
+	/* netbsd turns off ints here, why not be safe and do it too */
+	local_irq_save(flags);
+
+	/* send start chain */
+	sun3scsi_dma_start(c, *data);
+
+	if (p & SR_IO) {
+		NCR5380_write(TARGET_COMMAND_REG, 1);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, 0);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_INITIATOR_RECEIVE_REG, 0);
+	} else {
+		NCR5380_write(TARGET_COMMAND_REG, 0);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_DATA);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_SEND_REG, 0);
+	}
+
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_DMA_ENABLE;
+#endif
+
+	local_irq_restore(flags);
+
+	sun3_dma_active = 1;
+
+#else /* !defined(CONFIG_SUN3) */
 	register unsigned char *d = *data;
 	unsigned char tmp;
-	unsigned long flags;
 
 	if ((tmp = (NCR5380_read(STATUS_REG) & PHASE_MASK)) != p) {
 		*phase = tmp;
@@ -1895,6 +1976,8 @@ static int NCR5380_transfer_dma(struct S
 			NCR5380_dma_write_setup(instance, d, c);
 		local_irq_restore(flags);
 	}
+#endif /* !defined(CONFIG_SUN3) */
+
 	return 0;
 }
 #endif /* defined(REAL_DMA) */
@@ -1930,6 +2013,10 @@ static void NCR5380_information_transfer
 	unsigned char phase, tmp, extended_msg[10], old_phase = 0xff;
 	struct scsi_cmnd *cmd = (struct scsi_cmnd *) hostdata->connected;
 
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
+
 	while (1) {
 		tmp = NCR5380_read(STATUS_REG);
 		/* We only have a valid SCSI phase when REQ is asserted */
@@ -1939,6 +2026,33 @@ static void NCR5380_information_transfer
 				old_phase = phase;
 				NCR5380_dprint_phase(NDEBUG_INFORMATION, instance);
 			}
+#if defined(CONFIG_SUN3)
+			if (phase == PHASE_CMDOUT) {
+#if defined(REAL_DMA)
+				void *d;
+				unsigned long count;
+
+				if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
+					count = cmd->SCp.buffer->length;
+					d = sg_virt(cmd->SCp.buffer);
+				} else {
+					count = cmd->SCp.this_residual;
+					d = cmd->SCp.ptr;
+				}
+				/* this command setup for dma yet? */
+				if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != cmd)) {
+					if (cmd->request->cmd_type == REQ_TYPE_FS) {
+						sun3scsi_dma_setup(d, count,
+						                   rq_data_dir(cmd->request));
+						sun3_dma_setup_done = cmd;
+					}
+				}
+#endif
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_INTR;
+#endif
+			}
+#endif /* CONFIG_SUN3 */
 
 			if (sink && (phase != PHASE_MSGOUT)) {
 				NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
@@ -2000,8 +2114,11 @@ static void NCR5380_information_transfer
 				 */
 
 #if defined(REAL_DMA)
-				if (!cmd->device->borken &&
-				    (transfersize = NCR5380_dma_xfer_len(instance,cmd,phase)) > 31) {
+				if (
+#if !defined(CONFIG_SUN3)
+				    !cmd->device->borken &&
+#endif
+				    (transfersize = NCR5380_dma_xfer_len(instance, cmd, phase)) >= DMA_MIN_SIZE) {
 					len = transfersize;
 					cmd->SCp.phase = phase;
 					if (NCR5380_transfer_dma(instance, &phase,
@@ -2038,6 +2155,11 @@ static void NCR5380_information_transfer
 					NCR5380_transfer_pio(instance, &phase,
 							     (int *)&cmd->SCp.this_residual,
 							     (unsigned char **)&cmd->SCp.ptr);
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+				/* if we had intended to dma that command clear it */
+				if (sun3_dma_setup_done == cmd)
+					sun3_dma_setup_done = NULL;
+#endif
 				break;
 			case PHASE_MSGIN:
 				len = 1;
@@ -2243,6 +2365,9 @@ static void NCR5380_information_transfer
 					/* Wait for bus free to avoid nasty timeouts */
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
+#ifdef SUN3_SCSI_VME
+					dregs->csr |= CSR_DMA_ENABLE;
+#endif
 					return;
 					/*
 					 * The SCSI data pointer is *IMPLICITLY* saved on a disconnect
@@ -2402,17 +2527,20 @@ static void NCR5380_information_transfer
  */
 
 
+/* it might eventually prove necessary to do a dma setup on
+   reselection, but it doesn't seem to be needed now -- sam */
+
 static void NCR5380_reselect(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
 	unsigned char target_mask;
-	unsigned char lun, phase;
-	int len;
+	unsigned char lun;
 #ifdef SUPPORT_TAGS
 	unsigned char tag;
 #endif
 	unsigned char msg[3];
-	unsigned char *data;
+	int __maybe_unused len;
+	unsigned char __maybe_unused *data, __maybe_unused phase;
 	struct scsi_cmnd *tmp = NULL, *prev;
 
 	/*
@@ -2449,10 +2577,18 @@ static void NCR5380_reselect(struct Scsi
 	while (!(NCR5380_read(STATUS_REG) & SR_REQ))
 		;
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* acknowledge toggle to MSGIN */
+	NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(PHASE_MSGIN));
+
+	/* peek at the byte without really hitting the bus */
+	msg[0] = NCR5380_read(CURRENT_SCSI_DATA_REG);
+#else
 	len = 1;
 	data = msg;
 	phase = PHASE_MSGIN;
 	NCR5380_transfer_pio(instance, &phase, &len, &data);
+#endif
 
 	if (!(msg[0] & 0x80)) {
 		printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
@@ -2462,7 +2598,7 @@ static void NCR5380_reselect(struct Scsi
 	}
 	lun = (msg[0] & 0x07);
 
-#ifdef SUPPORT_TAGS
+#if defined(SUPPORT_TAGS) && !defined(CONFIG_SUN3)
 	/* If the phase is still MSGIN, the target wants to send some more
 	 * messages. In case it supports tagged queuing, this is probably a
 	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
@@ -2524,9 +2660,51 @@ static void NCR5380_reselect(struct Scsi
 		return;
 	}
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* engage dma setup for the command we just saw */
+	{
+		void *d;
+		unsigned long count;
+
+		if (!tmp->SCp.this_residual && tmp->SCp.buffers_residual) {
+			count = tmp->SCp.buffer->length;
+			d = sg_virt(tmp->SCp.buffer);
+		} else {
+			count = tmp->SCp.this_residual;
+			d = tmp->SCp.ptr;
+		}
+		/* setup this command for dma if not already */
+		if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != tmp)) {
+			sun3scsi_dma_setup(d, count, rq_data_dir(tmp->request));
+			sun3_dma_setup_done = tmp;
+		}
+	}
+
+	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
+#endif
+
 	/* Accept message by clearing ACK */
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 
+#if defined(SUPPORT_TAGS) && defined(CONFIG_SUN3)
+	/* If the phase is still MSGIN, the target wants to send some more
+	 * messages. In case it supports tagged queuing, this is probably a
+	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
+	 */
+	tag = TAG_NONE;
+	if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
+		/* Accept previous IDENTIFY message by clearing ACK */
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
+		len = 2;
+		data = msg + 1;
+		if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
+		    msg[1] == SIMPLE_QUEUE_TAG)
+			tag = msg[2];
+		dprintk(NDEBUG_TAGS, "scsi%d: target mask %02x, lun %d sent tag %d at reselection\n"
+			HOSTNO, target_mask, lun, tag);
+	}
+#endif
+
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);

Index: linux/drivers/scsi/atari_scsi.c
===================================================================

drivers/scsi/atari_scsi.c line 95

Quoted 7 lines
drivers/scsi/atari_scsi.c +1 -0
@@ -89,6 +89,7 @@
 #define REAL_DMA
 #define SUPPORT_TAGS
 #define MAX_TAGS                        32
+#define DMA_MIN_SIZE                    32
 
 #define NCR5380_implementation_fields   /* none */
 

You reference a certain Sam Creasey in the code (and there is even his email in it). Has he contributed to this patch?
If so, shouldn't he be added somewhere in the patch description, either with 'From;' (if the patch was originally by him) or with a 'Signed-off-by' tag?

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#75 lore raw

Re: [PATCH v2 30/36] atari_NCR5380: Merge from sun3_NCR5380.c

Quoted 110 lines · Hannes Reinecke
Quoted 109 lines · Finn Thain

There is very little difference between the sun3_NCR5380.c core driver and atari_NCR5380.c. The former is a fork of the latter.

Merge the sun3_NCR5380.c core driver into atari_NCR5380.c so that sun3_scsi.c can adopt the latter and the former can be deleted.

---

This patch brings some undesirable #ifdef's to atari_NCR5380. It's a small price to pay for the elimination of so much duplication. Eventually, with some testing, it should be possible to remove many of these.

Elimination of the SUN3_SCSI_VME macro is necessary to reach the goal of a single platform driver to replace the {atari,mac,sun3,sun3_vme}_scsi modules.

Elimination of the #ifdef CONFIG_SUN3 tests is not necessary. But some of these would go away if the sun3 driver followed the atari logic more closely, such as use of PIO vs DMA for certain phases and transfer sizes.

After applying this patch it is easy to compare the new atari_NCR5380.c with sun3_NCR5380.c, to check that they are equivalent. E.g.

$ cp drivers/scsi/{sun3,atari}_NCR5380.c /tmp
$ sed -i -e 's/  *$//'      /tmp/{sun3,atari}_NCR5380.c
$ scripts/Lindent -l96 -hnl /tmp/{sun3,atari}_NCR5380.c
$ meld                      /tmp/{sun3,atari}_NCR5380.c

One can see that the two implementations of tagged command queueing have diverged since the fork. The atari version has been updated and the sun3 implementation is unused as sun3_scsi.c does not define SUPPORT_TAGS.

The remaining differences are merge_contiguous_buffers() and the falcon locking code. The falcon code disappears when suitable macro definitions are provided in sun3_scsi.c. merge_contiguous_buffers() could be a problem for sun3 (due to a DMA setup in an odd place) so it is #ifdef'd for sun3 until the DMA setup discrepancies can be reconciled or moved out of the core driver.

---
 drivers/scsi/atari_NCR5380.c |  210 +++++++++++++++++++++++++++++++++++++++----
 drivers/scsi/atari_scsi.c    |    1 
 2 files changed, 195 insertions(+), 16 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +13 -8
@@ -71,6 +71,9 @@
  * 1.  Test linked command handling code after Eric is ready with
  *     the high level code.
  */
+
+/* Adapted for the sun3 by Sam Creasey. */
+
 #include <scsi/scsi_dbg.h>
 #include <scsi/scsi_transport_spi.h>
 
@@ -458,6 +461,7 @@ static void free_all_tags(void)
 
 static void merge_contiguous_buffers(struct scsi_cmnd *cmd)
 {
+#if !defined(CONFIG_SUN3)
 	unsigned long endaddr;
 #if (NDEBUG & NDEBUG_MERGING)
 	unsigned long oldlen = cmd->SCp.this_residual;
@@ -482,6 +486,7 @@ static void merge_contiguous_buffers(str
 		dprintk(NDEBUG_MERGING, "merged %d buffers from %p, new length %08x\n",
 			   cnt, cmd->SCp.ptr, cmd->SCp.this_residual);
 #endif
+#endif /* !defined(CONFIG_SUN3) */
 }
 
 /*
@@ -1043,12 +1048,10 @@ static void NCR5380_main(struct work_str
 			     prev = NULL; tmp; prev = tmp, tmp = NEXT(tmp)) {
 				u8 lun = tmp->device->lun;
 
-#if (NDEBUG & NDEBUG_LISTS)
-				if (prev != tmp)
-					printk("MAIN tmp=%p   target=%d   busy=%d lun=%llu\n",
-					       tmp, tmp->device->id, hostdata->busy[tmp->device->id],
-					       lun);
-#endif
+				dprintk(NDEBUG_LISTS,
+				        "MAIN tmp=%p target=%d busy=%d lun=%d\n",
+				        tmp, scmd_id(tmp), hostdata->busy[scmd_id(tmp)],
+				        lun);
 				/*  When we find one, remove it from the issue queue. */
 				/* ++guenther: possible race with Falcon locking */
 				if (
@@ -1157,9 +1160,11 @@ static void NCR5380_main(struct work_str
 static void NCR5380_dma_complete(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
-	int transfered, saved_data = 0, overrun = 0, cnt, toPIO;
-	unsigned char **data, p;
+	int transfered;
+	unsigned char **data;
 	volatile int *count;
+	int saved_data = 0, overrun = 0;
+	unsigned char p;
 
Quoted 4 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_main(struct work_str · line 1170

Quoted 2 lines
drivers/scsi/atari_NCR5380.c +0 -0
 	if (!hostdata->connected) {
 		printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "

nitpick: shouldn't that be 'transferred' ?

The intention of this patch was to merge two files into one file, in such a way that the result could be easily compared with the originals.

With that in mind, fixing this typo could be done pre-merger by patching both files, or post-merger by patching just one.

If this patch series ends up iterating again as v3, I'll add a new patch to the end to fix this (long standing) typo.

If there's no need for a re-spin, I'll send a separate patch with Cc to [email protected].

Quoted 333 lines
Quoted 333 lines
drivers/scsi/atari_NCR5380.c +181 -8
@@ -1185,6 +1190,26 @@ static void NCR5380_dma_complete(struct
 		   HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
 		   NCR5380_read(STATUS_REG));
 
+#if defined(CONFIG_SUN3)
+	if ((sun3scsi_dma_finish(rq_data_dir(hostdata->connected->request)))) {
+		pr_err("scsi%d: overrun in UDC counter -- not prepared to deal with this!\n",
+		       instance->host_no);
+		pr_err("please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+
+	/* make sure we're not stuck in a data phase */
+	if ((NCR5380_read(BUS_AND_STATUS_REG) & (BASR_PHASE_MATCH | BASR_ACK)) ==
+	    (BASR_PHASE_MATCH | BASR_ACK)) {
+		pr_err("scsi%d: BASR %02x\n", instance->host_no,
+		       NCR5380_read(BUS_AND_STATUS_REG));
+		pr_err("scsi%d: bus stuck in data phase -- probably a single byte overrun!\n",
+		       instance->host_no);
+		pr_err("not prepared for this error! please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+#endif
+
 	(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
 	NCR5380_write(MODE_REG, MR_BASE);
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
@@ -1198,6 +1223,8 @@ static void NCR5380_dma_complete(struct
 	*count -= transfered;
 
 	if (hostdata->read_overruns) {
+		int cnt, toPIO;
+
 		if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
 			cnt = toPIO = hostdata->read_overruns;
 			if (overrun) {
@@ -1277,11 +1304,14 @@ static irqreturn_t NCR5380_intr(int irq,
 			{
 /* MS: Ignore unknown phase mismatch interrupts (caused by EOP interrupt) */
 				if (basr & BASR_PHASE_MATCH)
-					printk(KERN_NOTICE "scsi%d: unknown interrupt, "
+					dprintk(NDEBUG_INTR, "scsi%d: unknown interrupt, "
 					       "BASR 0x%x, MR 0x%x, SR 0x%x\n",
 					       HOSTNO, basr, NCR5380_read(MODE_REG),
 					       NCR5380_read(STATUS_REG));
 				(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_DMA_ENABLE;
+#endif
 			}
 		} /* if !(SELECTION || PARITY) */
 		handled = 1;
@@ -1290,6 +1320,9 @@ static irqreturn_t NCR5380_intr(int irq,
 		       "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
 		       NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
 		(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+		dregs->csr |= CSR_DMA_ENABLE;
+#endif
 	}
 
 	if (!done) {
@@ -1622,6 +1655,9 @@ static int NCR5380_select(struct Scsi_Ho
 #ifndef SUPPORT_TAGS
 	hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
 #endif
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
 
 	initialize_SCp(cmd);
 
@@ -1845,9 +1881,54 @@ static int NCR5380_transfer_dma(struct S
 	SETUP_HOSTDATA(instance);
 	register int c = *count;
 	register unsigned char p = *phase;
+	unsigned long flags;
+
+#if defined(CONFIG_SUN3)
+	/* sanity check */
+	if (!sun3_dma_setup_done) {
+		pr_err("scsi%d: transfer_dma without setup!\n",
+		       instance->host_no);
+		BUG();
+	}
+	hostdata->dma_len = c;
+
+	dprintk(NDEBUG_DMA, "scsi%d: initializing DMA for %s, %d bytes %s %p\n",
+		instance->host_no, (p & SR_IO) ? "reading" : "writing",
+		c, (p & SR_IO) ? "to" : "from", *data);
+
+	/* netbsd turns off ints here, why not be safe and do it too */
+	local_irq_save(flags);
+
+	/* send start chain */
+	sun3scsi_dma_start(c, *data);
+
+	if (p & SR_IO) {
+		NCR5380_write(TARGET_COMMAND_REG, 1);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, 0);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_INITIATOR_RECEIVE_REG, 0);
+	} else {
+		NCR5380_write(TARGET_COMMAND_REG, 0);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_DATA);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_SEND_REG, 0);
+	}
+
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_DMA_ENABLE;
+#endif
+
+	local_irq_restore(flags);
+
+	sun3_dma_active = 1;
+
+#else /* !defined(CONFIG_SUN3) */
 	register unsigned char *d = *data;
 	unsigned char tmp;
-	unsigned long flags;
 
 	if ((tmp = (NCR5380_read(STATUS_REG) & PHASE_MASK)) != p) {
 		*phase = tmp;
@@ -1895,6 +1976,8 @@ static int NCR5380_transfer_dma(struct S
 			NCR5380_dma_write_setup(instance, d, c);
 		local_irq_restore(flags);
 	}
+#endif /* !defined(CONFIG_SUN3) */
+
 	return 0;
 }
 #endif /* defined(REAL_DMA) */
@@ -1930,6 +2013,10 @@ static void NCR5380_information_transfer
 	unsigned char phase, tmp, extended_msg[10], old_phase = 0xff;
 	struct scsi_cmnd *cmd = (struct scsi_cmnd *) hostdata->connected;
 
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
+
 	while (1) {
 		tmp = NCR5380_read(STATUS_REG);
 		/* We only have a valid SCSI phase when REQ is asserted */
@@ -1939,6 +2026,33 @@ static void NCR5380_information_transfer
 				old_phase = phase;
 				NCR5380_dprint_phase(NDEBUG_INFORMATION, instance);
 			}
+#if defined(CONFIG_SUN3)
+			if (phase == PHASE_CMDOUT) {
+#if defined(REAL_DMA)
+				void *d;
+				unsigned long count;
+
+				if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
+					count = cmd->SCp.buffer->length;
+					d = sg_virt(cmd->SCp.buffer);
+				} else {
+					count = cmd->SCp.this_residual;
+					d = cmd->SCp.ptr;
+				}
+				/* this command setup for dma yet? */
+				if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != cmd)) {
+					if (cmd->request->cmd_type == REQ_TYPE_FS) {
+						sun3scsi_dma_setup(d, count,
+						                   rq_data_dir(cmd->request));
+						sun3_dma_setup_done = cmd;
+					}
+				}
+#endif
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_INTR;
+#endif
+			}
+#endif /* CONFIG_SUN3 */
 
 			if (sink && (phase != PHASE_MSGOUT)) {
 				NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
@@ -2000,8 +2114,11 @@ static void NCR5380_information_transfer
 				 */
 
 #if defined(REAL_DMA)
-				if (!cmd->device->borken &&
-				    (transfersize = NCR5380_dma_xfer_len(instance,cmd,phase)) > 31) {
+				if (
+#if !defined(CONFIG_SUN3)
+				    !cmd->device->borken &&
+#endif
+				    (transfersize = NCR5380_dma_xfer_len(instance, cmd, phase)) >= DMA_MIN_SIZE) {
 					len = transfersize;
 					cmd->SCp.phase = phase;
 					if (NCR5380_transfer_dma(instance, &phase,
@@ -2038,6 +2155,11 @@ static void NCR5380_information_transfer
 					NCR5380_transfer_pio(instance, &phase,
 							     (int *)&cmd->SCp.this_residual,
 							     (unsigned char **)&cmd->SCp.ptr);
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+				/* if we had intended to dma that command clear it */
+				if (sun3_dma_setup_done == cmd)
+					sun3_dma_setup_done = NULL;
+#endif
 				break;
 			case PHASE_MSGIN:
 				len = 1;
@@ -2243,6 +2365,9 @@ static void NCR5380_information_transfer
 					/* Wait for bus free to avoid nasty timeouts */
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
+#ifdef SUN3_SCSI_VME
+					dregs->csr |= CSR_DMA_ENABLE;
+#endif
 					return;
 					/*
 					 * The SCSI data pointer is *IMPLICITLY* saved on a disconnect
@@ -2402,17 +2527,20 @@ static void NCR5380_information_transfer
  */
 
 
+/* it might eventually prove necessary to do a dma setup on
+   reselection, but it doesn't seem to be needed now -- sam */
+
 static void NCR5380_reselect(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
 	unsigned char target_mask;
-	unsigned char lun, phase;
-	int len;
+	unsigned char lun;
 #ifdef SUPPORT_TAGS
 	unsigned char tag;
 #endif
 	unsigned char msg[3];
-	unsigned char *data;
+	int __maybe_unused len;
+	unsigned char __maybe_unused *data, __maybe_unused phase;
 	struct scsi_cmnd *tmp = NULL, *prev;
 
 	/*
@@ -2449,10 +2577,18 @@ static void NCR5380_reselect(struct Scsi
 	while (!(NCR5380_read(STATUS_REG) & SR_REQ))
 		;
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* acknowledge toggle to MSGIN */
+	NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(PHASE_MSGIN));
+
+	/* peek at the byte without really hitting the bus */
+	msg[0] = NCR5380_read(CURRENT_SCSI_DATA_REG);
+#else
 	len = 1;
 	data = msg;
 	phase = PHASE_MSGIN;
 	NCR5380_transfer_pio(instance, &phase, &len, &data);
+#endif
 
 	if (!(msg[0] & 0x80)) {
 		printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
@@ -2462,7 +2598,7 @@ static void NCR5380_reselect(struct Scsi
 	}
 	lun = (msg[0] & 0x07);
 
-#ifdef SUPPORT_TAGS
+#if defined(SUPPORT_TAGS) && !defined(CONFIG_SUN3)
 	/* If the phase is still MSGIN, the target wants to send some more
 	 * messages. In case it supports tagged queuing, this is probably a
 	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
@@ -2524,9 +2660,51 @@ static void NCR5380_reselect(struct Scsi
 		return;
 	}
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* engage dma setup for the command we just saw */
+	{
+		void *d;
+		unsigned long count;
+
+		if (!tmp->SCp.this_residual && tmp->SCp.buffers_residual) {
+			count = tmp->SCp.buffer->length;
+			d = sg_virt(tmp->SCp.buffer);
+		} else {
+			count = tmp->SCp.this_residual;
+			d = tmp->SCp.ptr;
+		}
+		/* setup this command for dma if not already */
+		if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != tmp)) {
+			sun3scsi_dma_setup(d, count, rq_data_dir(tmp->request));
+			sun3_dma_setup_done = tmp;
+		}
+	}
+
+	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
+#endif
+
 	/* Accept message by clearing ACK */
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 
+#if defined(SUPPORT_TAGS) && defined(CONFIG_SUN3)
+	/* If the phase is still MSGIN, the target wants to send some more
+	 * messages. In case it supports tagged queuing, this is probably a
+	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
+	 */
+	tag = TAG_NONE;
+	if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
+		/* Accept previous IDENTIFY message by clearing ACK */
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
+		len = 2;
+		data = msg + 1;
+		if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
+		    msg[1] == SIMPLE_QUEUE_TAG)
+			tag = msg[2];
+		dprintk(NDEBUG_TAGS, "scsi%d: target mask %02x, lun %d sent tag %d at reselection\n"
+			HOSTNO, target_mask, lun, tag);
+	}
+#endif
+
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);

Index: linux/drivers/scsi/atari_scsi.c
===================================================================

drivers/scsi/atari_scsi.c +1 -0
@@ -89,6 +89,7 @@
 #define REAL_DMA
 #define SUPPORT_TAGS
 #define MAX_TAGS                        32
+#define DMA_MIN_SIZE                    32
 
Quoted 6 lines

drivers/scsi/atari_scsi.c line 95

Quoted 4 lines
drivers/scsi/atari_scsi.c +0 -0
 #define NCR5380_implementation_fields   /* none */
 

You reference a certain Sam Creasey in the code (and there is even his email in it). Has he contributed to this patch?

No, the patch is my work.

As I understand it, sun3_NCR5380.c was originally Sam's (derived) work.

Quoted 3 lines

If so, shouldn't he be added somewhere in the patch description, either with 'From;' (if the patch was originally by him) or with a 'Signed-off-by' tag?

I did Cc these patches to Sam, for comment/testing; perhaps a Cc tag might have been appropriate but I gather they are optional.

Reviewed-by
#76 lore raw

Re: [PATCH v2 30/36] atari_NCR5380: Merge from sun3_NCR5380.c

Quoted 122 lines · Finn Thain
Quoted 110 lines · Hannes Reinecke
Quoted 109 lines · Finn Thain

There is very little difference between the sun3_NCR5380.c core driver and atari_NCR5380.c. The former is a fork of the latter.

Merge the sun3_NCR5380.c core driver into atari_NCR5380.c so that sun3_scsi.c can adopt the latter and the former can be deleted.

---

This patch brings some undesirable #ifdef's to atari_NCR5380. It's a small price to pay for the elimination of so much duplication. Eventually, with some testing, it should be possible to remove many of these.

Elimination of the SUN3_SCSI_VME macro is necessary to reach the goal of a single platform driver to replace the {atari,mac,sun3,sun3_vme}_scsi modules.

Elimination of the #ifdef CONFIG_SUN3 tests is not necessary. But some of these would go away if the sun3 driver followed the atari logic more closely, such as use of PIO vs DMA for certain phases and transfer sizes.

After applying this patch it is easy to compare the new atari_NCR5380.c with sun3_NCR5380.c, to check that they are equivalent. E.g.

$ cp drivers/scsi/{sun3,atari}_NCR5380.c /tmp
$ sed -i -e 's/  *$//'      /tmp/{sun3,atari}_NCR5380.c
$ scripts/Lindent -l96 -hnl /tmp/{sun3,atari}_NCR5380.c
$ meld                      /tmp/{sun3,atari}_NCR5380.c

One can see that the two implementations of tagged command queueing have diverged since the fork. The atari version has been updated and the sun3 implementation is unused as sun3_scsi.c does not define SUPPORT_TAGS.

The remaining differences are merge_contiguous_buffers() and the falcon locking code. The falcon code disappears when suitable macro definitions are provided in sun3_scsi.c. merge_contiguous_buffers() could be a problem for sun3 (due to a DMA setup in an odd place) so it is #ifdef'd for sun3 until the DMA setup discrepancies can be reconciled or moved out of the core driver.

---
 drivers/scsi/atari_NCR5380.c |  210 +++++++++++++++++++++++++++++++++++++++----
 drivers/scsi/atari_scsi.c    |    1 
 2 files changed, 195 insertions(+), 16 deletions(-)

Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================

drivers/scsi/atari_NCR5380.c +13 -8
@@ -71,6 +71,9 @@
  * 1.  Test linked command handling code after Eric is ready with
  *     the high level code.
  */
+
+/* Adapted for the sun3 by Sam Creasey. */
+
 #include <scsi/scsi_dbg.h>
 #include <scsi/scsi_transport_spi.h>
 
@@ -458,6 +461,7 @@ static void free_all_tags(void)
 
 static void merge_contiguous_buffers(struct scsi_cmnd *cmd)
 {
+#if !defined(CONFIG_SUN3)
 	unsigned long endaddr;
 #if (NDEBUG & NDEBUG_MERGING)
 	unsigned long oldlen = cmd->SCp.this_residual;
@@ -482,6 +486,7 @@ static void merge_contiguous_buffers(str
 		dprintk(NDEBUG_MERGING, "merged %d buffers from %p, new length %08x\n",
 			   cnt, cmd->SCp.ptr, cmd->SCp.this_residual);
 #endif
+#endif /* !defined(CONFIG_SUN3) */
 }
 
 /*
@@ -1043,12 +1048,10 @@ static void NCR5380_main(struct work_str
 			     prev = NULL; tmp; prev = tmp, tmp = NEXT(tmp)) {
 				u8 lun = tmp->device->lun;
 
-#if (NDEBUG & NDEBUG_LISTS)
-				if (prev != tmp)
-					printk("MAIN tmp=%p   target=%d   busy=%d lun=%llu\n",
-					       tmp, tmp->device->id, hostdata->busy[tmp->device->id],
-					       lun);
-#endif
+				dprintk(NDEBUG_LISTS,
+				        "MAIN tmp=%p target=%d busy=%d lun=%d\n",
+				        tmp, scmd_id(tmp), hostdata->busy[scmd_id(tmp)],
+				        lun);
 				/*  When we find one, remove it from the issue queue. */
 				/* ++guenther: possible race with Falcon locking */
 				if (
@@ -1157,9 +1160,11 @@ static void NCR5380_main(struct work_str
 static void NCR5380_dma_complete(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
-	int transfered, saved_data = 0, overrun = 0, cnt, toPIO;
-	unsigned char **data, p;
+	int transfered;
+	unsigned char **data;
 	volatile int *count;
+	int saved_data = 0, overrun = 0;
+	unsigned char p;
 
Quoted 4 lines

drivers/scsi/atari_NCR5380.c static void NCR5380_main(struct work_str · line 1170

Quoted 2 lines
drivers/scsi/atari_NCR5380.c +0 -0
 	if (!hostdata->connected) {
 		printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "

nitpick: shouldn't that be 'transferred' ?

The intention of this patch was to merge two files into one file, in such a way that the result could be easily compared with the originals.

Quoted 9 lines

With that in mind, fixing this typo could be done pre-merger by patching both files, or post-merger by patching just one.

If this patch series ends up iterating again as v3, I'll add a new patch to the end to fix this (long standing) typo.

If there's no need for a re-spin, I'll send a separate patch with Cc to [email protected].

Okay, fair enough.
No need to clean it up now.

Quoted 346 lines
Quoted 334 lines
Quoted 334 lines
drivers/scsi/atari_NCR5380.c +181 -8
@@ -1185,6 +1190,26 @@ static void NCR5380_dma_complete(struct
 		   HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
 		   NCR5380_read(STATUS_REG));
 
+#if defined(CONFIG_SUN3)
+	if ((sun3scsi_dma_finish(rq_data_dir(hostdata->connected->request)))) {
+		pr_err("scsi%d: overrun in UDC counter -- not prepared to deal with this!\n",
+		       instance->host_no);
+		pr_err("please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+
+	/* make sure we're not stuck in a data phase */
+	if ((NCR5380_read(BUS_AND_STATUS_REG) & (BASR_PHASE_MATCH | BASR_ACK)) ==
+	    (BASR_PHASE_MATCH | BASR_ACK)) {
+		pr_err("scsi%d: BASR %02x\n", instance->host_no,
+		       NCR5380_read(BUS_AND_STATUS_REG));
+		pr_err("scsi%d: bus stuck in data phase -- probably a single byte overrun!\n",
+		       instance->host_no);
+		pr_err("not prepared for this error! please e-mail [email protected] with a description of how this error was produced.\n");
+		BUG();
+	}
+#endif
+
 	(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
 	NCR5380_write(MODE_REG, MR_BASE);
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
@@ -1198,6 +1223,8 @@ static void NCR5380_dma_complete(struct
 	*count -= transfered;
 
 	if (hostdata->read_overruns) {
+		int cnt, toPIO;
+
 		if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
 			cnt = toPIO = hostdata->read_overruns;
 			if (overrun) {
@@ -1277,11 +1304,14 @@ static irqreturn_t NCR5380_intr(int irq,
 			{
 /* MS: Ignore unknown phase mismatch interrupts (caused by EOP interrupt) */
 				if (basr & BASR_PHASE_MATCH)
-					printk(KERN_NOTICE "scsi%d: unknown interrupt, "
+					dprintk(NDEBUG_INTR, "scsi%d: unknown interrupt, "
 					       "BASR 0x%x, MR 0x%x, SR 0x%x\n",
 					       HOSTNO, basr, NCR5380_read(MODE_REG),
 					       NCR5380_read(STATUS_REG));
 				(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_DMA_ENABLE;
+#endif
 			}
 		} /* if !(SELECTION || PARITY) */
 		handled = 1;
@@ -1290,6 +1320,9 @@ static irqreturn_t NCR5380_intr(int irq,
 		       "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
 		       NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
 		(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+#ifdef SUN3_SCSI_VME
+		dregs->csr |= CSR_DMA_ENABLE;
+#endif
 	}
 
 	if (!done) {
@@ -1622,6 +1655,9 @@ static int NCR5380_select(struct Scsi_Ho
 #ifndef SUPPORT_TAGS
 	hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
 #endif
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
 
 	initialize_SCp(cmd);
 
@@ -1845,9 +1881,54 @@ static int NCR5380_transfer_dma(struct S
 	SETUP_HOSTDATA(instance);
 	register int c = *count;
 	register unsigned char p = *phase;
+	unsigned long flags;
+
+#if defined(CONFIG_SUN3)
+	/* sanity check */
+	if (!sun3_dma_setup_done) {
+		pr_err("scsi%d: transfer_dma without setup!\n",
+		       instance->host_no);
+		BUG();
+	}
+	hostdata->dma_len = c;
+
+	dprintk(NDEBUG_DMA, "scsi%d: initializing DMA for %s, %d bytes %s %p\n",
+		instance->host_no, (p & SR_IO) ? "reading" : "writing",
+		c, (p & SR_IO) ? "to" : "from", *data);
+
+	/* netbsd turns off ints here, why not be safe and do it too */
+	local_irq_save(flags);
+
+	/* send start chain */
+	sun3scsi_dma_start(c, *data);
+
+	if (p & SR_IO) {
+		NCR5380_write(TARGET_COMMAND_REG, 1);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, 0);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_INITIATOR_RECEIVE_REG, 0);
+	} else {
+		NCR5380_write(TARGET_COMMAND_REG, 0);
+		NCR5380_read(RESET_PARITY_INTERRUPT_REG);
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_DATA);
+		NCR5380_write(MODE_REG,
+			      (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
+		NCR5380_write(START_DMA_SEND_REG, 0);
+	}
+
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_DMA_ENABLE;
+#endif
+
+	local_irq_restore(flags);
+
+	sun3_dma_active = 1;
+
+#else /* !defined(CONFIG_SUN3) */
 	register unsigned char *d = *data;
 	unsigned char tmp;
-	unsigned long flags;
 
 	if ((tmp = (NCR5380_read(STATUS_REG) & PHASE_MASK)) != p) {
 		*phase = tmp;
@@ -1895,6 +1976,8 @@ static int NCR5380_transfer_dma(struct S
 			NCR5380_dma_write_setup(instance, d, c);
 		local_irq_restore(flags);
 	}
+#endif /* !defined(CONFIG_SUN3) */
+
 	return 0;
 }
 #endif /* defined(REAL_DMA) */
@@ -1930,6 +2013,10 @@ static void NCR5380_information_transfer
 	unsigned char phase, tmp, extended_msg[10], old_phase = 0xff;
 	struct scsi_cmnd *cmd = (struct scsi_cmnd *) hostdata->connected;
 
+#ifdef SUN3_SCSI_VME
+	dregs->csr |= CSR_INTR;
+#endif
+
 	while (1) {
 		tmp = NCR5380_read(STATUS_REG);
 		/* We only have a valid SCSI phase when REQ is asserted */
@@ -1939,6 +2026,33 @@ static void NCR5380_information_transfer
 				old_phase = phase;
 				NCR5380_dprint_phase(NDEBUG_INFORMATION, instance);
 			}
+#if defined(CONFIG_SUN3)
+			if (phase == PHASE_CMDOUT) {
+#if defined(REAL_DMA)
+				void *d;
+				unsigned long count;
+
+				if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
+					count = cmd->SCp.buffer->length;
+					d = sg_virt(cmd->SCp.buffer);
+				} else {
+					count = cmd->SCp.this_residual;
+					d = cmd->SCp.ptr;
+				}
+				/* this command setup for dma yet? */
+				if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != cmd)) {
+					if (cmd->request->cmd_type == REQ_TYPE_FS) {
+						sun3scsi_dma_setup(d, count,
+						                   rq_data_dir(cmd->request));
+						sun3_dma_setup_done = cmd;
+					}
+				}
+#endif
+#ifdef SUN3_SCSI_VME
+				dregs->csr |= CSR_INTR;
+#endif
+			}
+#endif /* CONFIG_SUN3 */
 
 			if (sink && (phase != PHASE_MSGOUT)) {
 				NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
@@ -2000,8 +2114,11 @@ static void NCR5380_information_transfer
 				 */
 
 #if defined(REAL_DMA)
-				if (!cmd->device->borken &&
-				    (transfersize = NCR5380_dma_xfer_len(instance,cmd,phase)) > 31) {
+				if (
+#if !defined(CONFIG_SUN3)
+				    !cmd->device->borken &&
+#endif
+				    (transfersize = NCR5380_dma_xfer_len(instance, cmd, phase)) >= DMA_MIN_SIZE) {
 					len = transfersize;
 					cmd->SCp.phase = phase;
 					if (NCR5380_transfer_dma(instance, &phase,
@@ -2038,6 +2155,11 @@ static void NCR5380_information_transfer
 					NCR5380_transfer_pio(instance, &phase,
 							     (int *)&cmd->SCp.this_residual,
 							     (unsigned char **)&cmd->SCp.ptr);
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+				/* if we had intended to dma that command clear it */
+				if (sun3_dma_setup_done == cmd)
+					sun3_dma_setup_done = NULL;
+#endif
 				break;
 			case PHASE_MSGIN:
 				len = 1;
@@ -2243,6 +2365,9 @@ static void NCR5380_information_transfer
 					/* Wait for bus free to avoid nasty timeouts */
 					while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
 						barrier();
+#ifdef SUN3_SCSI_VME
+					dregs->csr |= CSR_DMA_ENABLE;
+#endif
 					return;
 					/*
 					 * The SCSI data pointer is *IMPLICITLY* saved on a disconnect
@@ -2402,17 +2527,20 @@ static void NCR5380_information_transfer
  */
 
 
+/* it might eventually prove necessary to do a dma setup on
+   reselection, but it doesn't seem to be needed now -- sam */
+
 static void NCR5380_reselect(struct Scsi_Host *instance)
 {
 	SETUP_HOSTDATA(instance);
 	unsigned char target_mask;
-	unsigned char lun, phase;
-	int len;
+	unsigned char lun;
 #ifdef SUPPORT_TAGS
 	unsigned char tag;
 #endif
 	unsigned char msg[3];
-	unsigned char *data;
+	int __maybe_unused len;
+	unsigned char __maybe_unused *data, __maybe_unused phase;
 	struct scsi_cmnd *tmp = NULL, *prev;
 
 	/*
@@ -2449,10 +2577,18 @@ static void NCR5380_reselect(struct Scsi
 	while (!(NCR5380_read(STATUS_REG) & SR_REQ))
 		;
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* acknowledge toggle to MSGIN */
+	NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(PHASE_MSGIN));
+
+	/* peek at the byte without really hitting the bus */
+	msg[0] = NCR5380_read(CURRENT_SCSI_DATA_REG);
+#else
 	len = 1;
 	data = msg;
 	phase = PHASE_MSGIN;
 	NCR5380_transfer_pio(instance, &phase, &len, &data);
+#endif
 
 	if (!(msg[0] & 0x80)) {
 		printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
@@ -2462,7 +2598,7 @@ static void NCR5380_reselect(struct Scsi
 	}
 	lun = (msg[0] & 0x07);
 
-#ifdef SUPPORT_TAGS
+#if defined(SUPPORT_TAGS) && !defined(CONFIG_SUN3)
 	/* If the phase is still MSGIN, the target wants to send some more
 	 * messages. In case it supports tagged queuing, this is probably a
 	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
@@ -2524,9 +2660,51 @@ static void NCR5380_reselect(struct Scsi
 		return;
 	}
 
+#if defined(CONFIG_SUN3) && defined(REAL_DMA)
+	/* engage dma setup for the command we just saw */
+	{
+		void *d;
+		unsigned long count;
+
+		if (!tmp->SCp.this_residual && tmp->SCp.buffers_residual) {
+			count = tmp->SCp.buffer->length;
+			d = sg_virt(tmp->SCp.buffer);
+		} else {
+			count = tmp->SCp.this_residual;
+			d = tmp->SCp.ptr;
+		}
+		/* setup this command for dma if not already */
+		if ((count >= DMA_MIN_SIZE) && (sun3_dma_setup_done != tmp)) {
+			sun3scsi_dma_setup(d, count, rq_data_dir(tmp->request));
+			sun3_dma_setup_done = tmp;
+		}
+	}
+
+	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
+#endif
+
 	/* Accept message by clearing ACK */
 	NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 
+#if defined(SUPPORT_TAGS) && defined(CONFIG_SUN3)
+	/* If the phase is still MSGIN, the target wants to send some more
+	 * messages. In case it supports tagged queuing, this is probably a
+	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
+	 */
+	tag = TAG_NONE;
+	if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
+		/* Accept previous IDENTIFY message by clearing ACK */
+		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
+		len = 2;
+		data = msg + 1;
+		if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
+		    msg[1] == SIMPLE_QUEUE_TAG)
+			tag = msg[2];
+		dprintk(NDEBUG_TAGS, "scsi%d: target mask %02x, lun %d sent tag %d at reselection\n"
+			HOSTNO, target_mask, lun, tag);
+	}
+#endif
+
 	hostdata->connected = tmp;
 	dprintk(NDEBUG_RESELECTION, "scsi%d: nexus established, target = %d, lun = %llu, tag = %d\n",
 		   HOSTNO, tmp->device->id, tmp->device->lun, tmp->tag);

Index: linux/drivers/scsi/atari_scsi.c
===================================================================

drivers/scsi/atari_scsi.c +1 -0
@@ -89,6 +89,7 @@
 #define REAL_DMA
 #define SUPPORT_TAGS
 #define MAX_TAGS                        32
+#define DMA_MIN_SIZE                    32
 
Quoted 6 lines

drivers/scsi/atari_scsi.c line 95

Quoted 4 lines
drivers/scsi/atari_scsi.c +0 -0
 #define NCR5380_implementation_fields   /* none */
 

You reference a certain Sam Creasey in the code (and there is even his email in it). Has he contributed to this patch?

No, the patch is my work.

As I understand it, sun3_NCR5380.c was originally Sam's (derived) work.

Quoted 7 lines
Quoted 3 lines

If so, shouldn't he be added somewhere in the patch description, either with 'From;' (if the patch was originally by him) or with a 'Signed-off-by' tag?

I did Cc these patches to Sam, for comment/testing; perhaps a Cc tag might have been appropriate but I gather they are optional.

Hmm. I always feel a bit awkward by using personal names in the code. It's not good practice nowadays. Plus one can never be sure if that address is still valid. Or remains so for the foreseeable future.

But hey, these are just my personal opinions.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#77 lore raw

Re: [PATCH v2 30/36] atari_NCR5380: Merge from sun3_NCR5380.c

Quoted 3 lines · Hannes Reinecke

Hmm. I always feel a bit awkward by using personal names in the code. It's not good practice nowadays. Plus one can never be sure if that address is still valid. Or remains so for the foreseeable future.

It was valid as of a couple of months ago.

Quoted 2 lines

But hey, these are just my personal opinions.

I agree with your opinions and I'm not entirely happy with this patch either. But I don't know what to do about it.

author
#78 lore raw

PATCH v2 31/36 sun3_scsi: Adopt atari_NCR5380 core driver and remove sun3_NCR5380.c

In reply to Finn Thain

Given the preceding changes to atari_NCR5380.c, this patch should not change behaviour of the sun3_scsi and sun3_scsi_vme modules.

---
 MAINTAINERS                 |    1 
 drivers/scsi/sun3_NCR5380.c | 2849 --------------------------------------------
 drivers/scsi/sun3_scsi.c    |   10 
 3 files changed, 6 insertions(+), 2854 deletions(-)
drivers/scsi/sun3_scsi.c +6 -4
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -41,6 +41,8 @@
 #define REAL_DMA
 #define RESET_RUN_DONE
 /* #define SUPPORT_TAGS */
+/* minimum number of bytes to do dma on */
+#define DMA_MIN_SIZE                    129
 
 /* #define MAX_TAGS                     32 */
 
@@ -64,6 +66,9 @@
 #define NCR5380_dma_xfer_len(instance, cmd, phase) \
         sun3scsi_dma_xfer_len(cmd->SCp.this_residual, cmd, !((phase) & SR_IO))
 
+#define NCR5380_acquire_dma_irq(instance)    (1)
+#define NCR5380_release_dma_irq(instance)
+
 #include "NCR5380.h"
 
 
@@ -92,9 +97,6 @@ module_param(setup_hostid, int, 0);
 /* dvma buffer to allocate -- 32k should hopefully be more than sufficient */
 #define SUN3_DVMA_BUFSIZE 0xe000
 
-/* minimum number of bytes to do dma on */
-#define SUN3_DMA_MINSIZE 128
-
 static struct scsi_cmnd *sun3_dma_setup_done;
 static unsigned char *sun3_scsi_regp;
 static volatile struct sun3_dma_regs *dregs;
@@ -486,7 +488,7 @@ static int sun3scsi_dma_finish(int write
 
 }
 	
-#include "sun3_NCR5380.c"
+#include "atari_NCR5380.c"
 
 #ifdef SUN3_SCSI_VME
 #define SUN3_SCSI_NAME          "Sun3 NCR5380 VME SCSI"
MAINTAINERS +0 -1
Index: linux/MAINTAINERS
===================================================================
@@ -6171,7 +6171,6 @@ F:	drivers/scsi/g_NCR5380.*
 F:	drivers/scsi/g_NCR5380_mmio.c
 F:	drivers/scsi/mac_scsi.*
 F:	drivers/scsi/pas16.*
-F:	drivers/scsi/sun3_NCR5380.c
 F:	drivers/scsi/sun3_scsi.*
 F:	drivers/scsi/sun3_scsi_vme.c
 F:	drivers/scsi/t128.*
drivers/scsi/sun3_NCR5380.c deleted +0 -2849

2,849 lines not on this page · raw message

--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html

Reviewed-by on v2 31/36
#79 lore raw

Re: [PATCH v2 31/36] sun3_scsi: Adopt atari_NCR5380 core driver and remove sun3_NCR5380.c

Quoted 4 lines · Finn Thain

Given the preceding changes to atari_NCR5380.c, this patch should not change behaviour of the sun3_scsi and sun3_scsi_vme modules.

One down. Good work.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#80 lore raw

PATCH v2 32/36 atari_NCR5380: Merge from NCR5380.c

In reply to Finn Thain

The NCR5380.c core driver has moved on since atari_NCR5380.c was forked. Some of those changes are also relevant to atari_NCR5380.c so apply them there as well.

---
 drivers/scsi/atari_NCR5380.c |  209 +++++++++++++++++--------------------------
 1 file changed, 87 insertions(+), 122 deletions(-)
drivers/scsi/atari_NCR5380.c +87 -122
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -104,27 +104,7 @@
 
 /*
  * Design
- * Issues :
  *
- * The other Linux SCSI drivers were written when Linux was Intel PC-only,
- * and specifically for each board rather than each chip.  This makes their
- * adaptation to platforms like the Mac (Some of which use NCR5380's)
- * more difficult than it has to be.
- *
- * Also, many of the SCSI drivers were written before the command queuing
- * routines were implemented, meaning their implementations of queued
- * commands were hacked on rather than designed in from the start.
- *
- * When I designed the Linux SCSI drivers I figured that
- * while having two different SCSI boards in a system might be useful
- * for debugging things, two of the same type wouldn't be used.
- * Well, I was wrong and a number of users have mailed me about running
- * multiple high-performance SCSI boards in a server.
- *
- * Finally, when I get questions from users, I have no idea what
- * revision of my driver they are running.
- *
- * This driver attempts to address these problems :
  * This is a generic 5380 driver.  To use it on a different platform,
  * one simply writes appropriate system specific macros (ie, data
  * transfer - some PC's will use the I/O bus, 68K's must use
@@ -139,11 +119,6 @@
  * allowing multiple commands to propagate all the way to a SCSI-II device
  * while a command is already executing.
  *
- * To solve the multiple-boards-in-the-same-system problem,
- * there is a separate instance structure for each instance
- * of a 5380 in the system.  So, multiple NCR5380 drivers will
- * be able to coexist with appropriate changes to the high level
- * SCSI code.
  *
  * Issues specific to the NCR5380 :
  *
@@ -168,19 +143,17 @@
  * Architecture :
  *
  * At the heart of the design is a coroutine, NCR5380_main,
- * which is started when not running by the interrupt handler,
- * timer, and queue command function.  It attempts to establish
- * I_T_L or I_T_L_Q nexuses by removing the commands from the
- * issue queue and calling NCR5380_select() if a nexus
- * is not established.
+ * which is started from a workqueue for each NCR5380 host in the
+ * system.  It attempts to establish I_T_L or I_T_L_Q nexuses by
+ * removing the commands from the issue queue and calling
+ * NCR5380_select() if a nexus is not established.
  *
  * Once a nexus is established, the NCR5380_information_transfer()
  * phase goes through the various phases as instructed by the target.
  * if the target goes into MSG IN and sends a DISCONNECT message,
  * the command structure is placed into the per instance disconnected
- * queue, and NCR5380_main tries to find more work.  If USLEEP
- * was defined, and the target is idle for too long, the system
- * will try to sleep.
+ * queue, and NCR5380_main tries to find more work.  If the target is
+ * idle for too long, the system will try to sleep.
  *
  * If a command has disconnected, eventually an interrupt will trigger,
  * calling NCR5380_intr()  which will in turn call NCR5380_reselect
@@ -206,6 +179,9 @@
  * AUTOSENSE - if defined, REQUEST SENSE will be performed automatically
  *	for commands that return with a CHECK CONDITION status.
  *
+ * DIFFERENTIAL - if defined, NCR53c81 chips will use external differential
+ *	transceivers.
+ *
  * LINKED - if defined, linked commands are supported.
  *
  * REAL_DMA - if defined, REAL DMA is used during the data transfer phases.
@@ -218,6 +194,9 @@
  *
  * NCR5380_write(register, value) - write to the specific register
  *
+ * NCR5380_implementation_fields  - additional fields needed for this
+ *      specific implementation of the NCR5380
+ *
  * Either real DMA *or* pseudo DMA may be implemented
  * REAL functions :
  * NCR5380_REAL_DMA should be defined if real DMA is to be used.
@@ -236,20 +215,6 @@
  * NCR5380_pwrite(instance, src, count)
  * NCR5380_pread(instance, dst, count);
  *
- * If nothing specific to this implementation needs doing (ie, with external
- * hardware), you must also define
- *
- * NCR5380_queue_command
- * NCR5380_reset
- * NCR5380_abort
- *
- * to be the global entry points into the specific driver, ie
- * #define NCR5380_queue_command t128_queue_command.
- *
- * If this is not done, the routines will be defined as static functions
- * with the NCR5380* names and the user must provide a globally
- * accessible wrapper function.
- *
  * The generic driver is initialized by calling NCR5380_init(instance),
  * after setting the appropriate host specific fields and ID.  If the
  * driver wishes to autoprobe for an IRQ line, the NCR5380_probe_irq(instance,
@@ -489,13 +454,11 @@ static void merge_contiguous_buffers(str
 #endif /* !defined(CONFIG_SUN3) */
 }
 
-/*
- * Function : void initialize_SCp(struct scsi_cmnd *cmd)
- *
- * Purpose : initialize the saved data pointers for cmd to point to the
- *	start of the buffer.
+/**
+ * initialize_SCp - init the scsi pointer field
+ * @cmd: command block to set up
  *
- * Inputs : cmd - scsi_cmnd structure to have pointers reset.
+ * Set up the internal fields in the SCSI command.
  */
 
 static inline void initialize_SCp(struct scsi_cmnd *cmd)
@@ -548,12 +511,11 @@ static struct {
 	{0, NULL}
 };
 
-/*
- * Function : void NCR5380_print(struct Scsi_Host *instance)
- *
- * Purpose : print the SCSI bus signals for debugging purposes
+/**
+ * NCR5380_print - print scsi bus signals
+ * @instance: adapter state to dump
  *
- * Input : instance - which NCR5380
+ * Print the SCSI bus signals for debugging purposes
  */
 
 static void NCR5380_print(struct Scsi_Host *instance)
@@ -596,12 +558,13 @@ static struct {
 	{PHASE_UNKNOWN, "UNKNOWN"}
 };
 
-/*
- * Function : void NCR5380_print_phase(struct Scsi_Host *instance)
+/**
+ * NCR5380_print_phase - show SCSI phase
+ * @instance: adapter to dump
  *
- * Purpose : print the current SCSI phase for debugging purposes
+ * Print the current SCSI phase for debugging purposes
  *
- * Input : instance - which NCR5380
+ * Locks: none
  */
 
 static void NCR5380_print_phase(struct Scsi_Host *instance)
@@ -710,13 +673,12 @@ static void prepare_info(struct Scsi_Hos
 	         "");
 }
 
-/*
- * Function : void NCR5380_print_status (struct Scsi_Host *instance)
- *
- * Purpose : print commands in the various queues, called from
- *	NCR5380_abort and NCR5380_debug to aid debugging.
+/**
+ * NCR5380_print_status - dump controller info
+ * @instance: controller to dump
  *
- * Inputs : instance, pointer to this instance.
+ * Print commands in the various queues, called from NCR5380_abort
+ * to aid debugging.
  */
 
 static void lprint_Scsi_Cmnd(struct scsi_cmnd *cmd)
@@ -807,16 +769,18 @@ static int __maybe_unused NCR5380_show_i
 	return 0;
 }
 
-/*
- * Function : void NCR5380_init (struct Scsi_Host *instance)
- *
- * Purpose : initializes *instance and corresponding 5380 chip.
+/**
+ * NCR5380_init - initialise an NCR5380
+ * @instance: adapter to configure
+ * @flags: control flags
  *
- * Inputs : instance - instantiation of the 5380 driver.
+ * Initializes *instance and corresponding 5380 chip,
+ * with flags OR'd into the initial flags value.
  *
  * Notes : I assume that the host, hostno, and id bits have been
- *	set correctly.  I don't care about the irq and other fields.
+ * set correctly. I don't care about the irq and other fields.
  *
+ * Returns 0 for success
  */
 
 static int __init NCR5380_init(struct Scsi_Host *instance, int flags)
@@ -861,27 +825,26 @@ static int __init NCR5380_init(struct Sc
 	return 0;
 }
 
+/**
+ * NCR5380_exit - remove an NCR5380
+ * @instance: adapter to remove
+ *
+ * Assumes that no more work can be queued (e.g. by NCR5380_intr).
+ */
+
 static void NCR5380_exit(struct Scsi_Host *instance)
 {
-	/* Empty, as we didn't schedule any delayed work */
+	cancel_work_sync(&NCR5380_tqueue);
 }
 
-/*
- * Function : int NCR5380_queue_command (struct scsi_cmnd *cmd,
- *	void (*done)(struct scsi_cmnd *))
- *
- * Purpose :  enqueues a SCSI command
- *
- * Inputs : cmd - SCSI command, done - function called on completion, with
- *	a pointer to the command descriptor.
- *
- * Returns : 0
- *
- * Side effects :
- *      cmd is added to the per instance issue_queue, with minor
- *	twiddling done to the host specific fields of cmd.  If the
- *	main coroutine is not running, it is restarted.
- *
+/**
+ * NCR5380_queue_command - queue a command
+ * @instance: the relevant SCSI adapter
+ * @cmd: SCSI command
+ *
+ * cmd is added to the per instance issue_queue, with minor
+ * twiddling done to the host specific fields of cmd.  If the
+ * main coroutine is not running, it is restarted.
  */
 
 static int NCR5380_queue_command(struct Scsi_Host *instance,
@@ -937,6 +900,13 @@ static int NCR5380_queue_command(struct
 
 	local_irq_save(flags);
 
+	/*
+	 * Insert the cmd into the issue queue. Note that REQUEST SENSE
+	 * commands are added to the head of the queue since any command will
+	 * clear the contingent allegiance condition that exists and the
+	 * sense data is only guaranteed to be valid while the condition exists.
+	 */
+
 	if (!(hostdata->issue_queue) || (cmd->cmnd[0] == REQUEST_SENSE)) {
 		LIST(cmd, hostdata->issue_queue);
 		SET_NEXT(cmd, hostdata->issue_queue);
@@ -979,16 +949,15 @@ static inline void maybe_release_dma_irq
 		NCR5380_release_dma_irq(instance);
 }
 
-/*
- * Function : NCR5380_main (void)
+/**
+ * NCR5380_main - NCR state machines
  *
- * Purpose : NCR5380_main is a coroutine that runs as long as more work can
- *	be done on the NCR5380 host adapters in a system.  Both
- *	NCR5380_queue_command() and NCR5380_intr() will try to start it
- *	in case it is not running.
+ * NCR5380_main is a coroutine that runs as long as more work can
+ * be done on the NCR5380 host adapters in a system.  Both
+ * NCR5380_queue_command() and NCR5380_intr() will try to start it
+ * in case it is not running.
  *
- * NOTE : NCR5380_main exits with interrupts *disabled*, the caller should
- *  reenable them.  This prevents reentrancy and kernel stack overflow.
+ * Locks: called as its own thread with no locks held.
  */
 
 static void NCR5380_main(struct work_struct *work)
@@ -1243,15 +1212,14 @@ static void NCR5380_dma_complete(struct
 #endif /* REAL_DMA */
 
 
-/*
- * Function : void NCR5380_intr (int irq)
- *
- * Purpose : handle interrupts, reestablishing I_T_L or I_T_L_Q nexuses
- *	from the disconnected queue, and restarting NCR5380_main()
- *	as required.
- *
- * Inputs : int irq, irq that caused this interrupt.
- *
+/**
+ * NCR5380_intr - generic NCR5380 irq handler
+ * @irq: interrupt number
+ * @dev_id: device info
+ *
+ * Handle interrupts, reestablishing I_T_L or I_T_L_Q nexuses
+ * from the disconnected queue, and restarting NCR5380_main()
+ * as required.
  */
 
 static irqreturn_t NCR5380_intr(int irq, void *dev_id)
@@ -1544,7 +1512,7 @@ static int NCR5380_select(struct Scsi_Ho
 	 * selection.
 	 */
 
-	timeout = jiffies + 25;
+	timeout = jiffies + (250 * HZ / 1000);
 
 	/*
 	 * XXX very interesting - we're seeing a bounce where the BSY we
@@ -2127,9 +2095,8 @@ static void NCR5380_information_transfer
 						 * If the watchdog timer fires, all future
 						 * accesses to this device will use the
 						 * polled-IO. */
-						printk(KERN_NOTICE "scsi%d: switching target %d "
-							   "lun %llu to slow handshake\n", HOSTNO,
-							   cmd->device->id, cmd->device->lun);
+						scmd_printk(KERN_INFO, cmd,
+							"switching to slow handshake\n");
 						cmd->device->borken = 1;
 						NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
 							ICR_ASSERT_ATN);
@@ -2449,20 +2416,18 @@ static void NCR5380_information_transfer
 					 */
 				default:
 					if (!tmp) {
-						printk(KERN_DEBUG "scsi%d: rejecting message ", HOSTNO);
+						printk(KERN_INFO "scsi%d: rejecting message ",
+						       instance->host_no);
 						spi_print_msg(extended_msg);
 						printk("\n");
 					} else if (tmp != EXTENDED_MESSAGE)
-						printk(KERN_DEBUG "scsi%d: rejecting unknown "
-						       "message %02x from target %d, lun %llu\n",
-						       HOSTNO, tmp, cmd->device->id, cmd->device->lun);
+						scmd_printk(KERN_INFO, cmd,
+						            "rejecting unknown message %02x\n",
+						            tmp);
 					else
-						printk(KERN_DEBUG "scsi%d: rejecting unknown "
-						       "extended message "
-						       "code %02x, length %d from target %d, lun %llu\n",
-						       HOSTNO, extended_msg[1], extended_msg[0],
-						       cmd->device->id, cmd->device->lun);
-
+						scmd_printk(KERN_INFO, cmd,
+						            "rejecting unknown extended message code %02x, length %d\n",
+						            extended_msg[1], extended_msg[0]);
 
 					msgout = MESSAGE_REJECT;
 					NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN);
Reviewed-by on v2 32/36
#81 lore raw

Re: [PATCH v2 32/36] atari_NCR5380: Merge from NCR5380.c

Quoted 5 lines · Finn Thain

The NCR5380.c core driver has moved on since atari_NCR5380.c was forked. Some of those changes are also relevant to atari_NCR5380.c so apply them there as well.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#82 lore raw

PATCH v2 33/36 atari_NCR5380: Introduce FLAG_TAGGED_QUEUING

In reply to Finn Thain

The static variable setup_use_tagged_queuing is declared in mac_scsi.c, sun3_scsi.c and atari_scsi.c and doesn't belong in the core driver. None of the other NCR5380 drivers suffer from this layering issue which makes merging the core drivers more difficult and will likely hinder plans for future use of platform data to configure the driver.

Replace the static variable with a host flag. This way it can be reported along with the other flags.

---
 drivers/scsi/NCR5380.h       |    1 +
 drivers/scsi/atari_NCR5380.c |   22 +++++++++++++---------
 drivers/scsi/atari_scsi.c    |    8 ++++----
 drivers/scsi/mac_scsi.c      |    8 ++++----
 drivers/scsi/sun3_scsi.c     |   12 ++++++------
 5 files changed, 28 insertions(+), 23 deletions(-)
drivers/scsi/NCR5380.h +1 -0
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -242,6 +242,7 @@
 #define FLAG_NO_PSEUDO_DMA		8	/* Inhibit DMA */
 #define FLAG_DTC3181E			16	/* DTC3181E */
 #define FLAG_LATE_DMA_SETUP		32	/* Setup NCR before DMA H/W */
+#define FLAG_TAGGED_QUEUING		64	/* as X3T9.2 spelled it */
 
 #ifndef ASM
 struct NCR5380_hostdata {
drivers/scsi/atari_NCR5380.c +13 -9
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -283,12 +283,12 @@ typedef struct {
 static TAG_ALLOC TagAlloc[8][8];	/* 8 targets and 8 LUNs */
 
 
-static void __init init_tags(void)
+static void __init init_tags(struct NCR5380_hostdata *hostdata)
 {
 	int target, lun;
 	TAG_ALLOC *ta;
 
-	if (!setup_use_tagged_queuing)
+	if (!(hostdata->flags & FLAG_TAGGED_QUEUING))
 		return;
 
 	for (target = 0; target < 8; ++target) {
@@ -321,7 +321,8 @@ static int is_lun_busy(struct scsi_cmnd
 	if (hostdata->busy[cmd->device->id] & (1 << lun))
 		return 1;
 	if (!should_be_tagged ||
-	    !setup_use_tagged_queuing || !cmd->device->tagged_supported)
+	    !(hostdata->flags & FLAG_TAGGED_QUEUING) ||
+	    !cmd->device->tagged_supported)
 		return 0;
 	if (TagAlloc[cmd->device->id][lun].nr_allocated >=
 	    TagAlloc[cmd->device->id][lun].queue_size) {
@@ -347,7 +348,8 @@ static void cmd_get_tag(struct scsi_cmnd
 	 * an untagged command.
 	 */
 	if (!should_be_tagged ||
-	    !setup_use_tagged_queuing || !cmd->device->tagged_supported) {
+	    !(hostdata->flags & FLAG_TAGGED_QUEUING) ||
+	    !cmd->device->tagged_supported) {
 		cmd->tag = TAG_NONE;
 		hostdata->busy[cmd->device->id] |= (1 << lun);
 		dprintk(NDEBUG_TAGS, "scsi%d: target %d lun %d now allocated by untagged "
@@ -392,12 +394,12 @@ static void cmd_free_tag(struct scsi_cmn
 }
 
 
-static void free_all_tags(void)
+static void free_all_tags(struct NCR5380_hostdata *hostdata)
 {
 	int target, lun;
 	TAG_ALLOC *ta;
 
-	if (!setup_use_tagged_queuing)
+	if (!(hostdata->flags & FLAG_TAGGED_QUEUING))
 		return;
 
 	for (target = 0; target < 8; ++target) {
@@ -653,11 +655,13 @@ static void prepare_info(struct Scsi_Hos
 	         "base 0x%lx, irq %d, "
 	         "can_queue %d, cmd_per_lun %d, "
 	         "sg_tablesize %d, this_id %d, "
+	         "flags { %s}, "
 	         "options { %s} ",
 	         instance->hostt->name, instance->io_port, instance->n_io_port,
 	         instance->base, instance->irq,
 	         instance->can_queue, instance->cmd_per_lun,
 	         instance->sg_tablesize, instance->this_id,
+	         hostdata->flags & FLAG_TAGGED_QUEUING ? "TAGGED_QUEUING " : "",
 #ifdef DIFFERENTIAL
 	         "DIFFERENTIAL "
 #endif
@@ -799,7 +803,7 @@ static int __init NCR5380_init(struct Sc
 	for (i = 0; i < 8; ++i)
 		hostdata->busy[i] = 0;
 #ifdef SUPPORT_TAGS
-	init_tags();
+	init_tags(hostdata);
 #endif
 #if defined (REAL_DMA)
 	hostdata->dma_len = 0;
@@ -2569,7 +2573,7 @@ static void NCR5380_reselect(struct Scsi
 	 * SIMPLE_QUEUE_TAG for the I_T_L_Q nexus.
 	 */
 	tag = TAG_NONE;
-	if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
+	if (phase == PHASE_MSGIN && (hostdata->flags & FLAG_TAGGED_QUEUING)) {
 		/* Accept previous IDENTIFY message by clearing ACK */
 		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 		len = 2;
@@ -3025,7 +3029,7 @@ static int NCR5380_bus_reset(struct scsi
 	hostdata->connected = NULL;
 	hostdata->disconnected_queue = NULL;
 #ifdef SUPPORT_TAGS
-	free_all_tags();
+	free_all_tags(hostdata);
 #endif
 	for (i = 0; i < 8; ++i)
 		hostdata->busy[i] = 0;
drivers/scsi/atari_scsi.c +4 -4
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -891,10 +891,6 @@ static int __init atari_scsi_probe(struc
 		}
 	}
 
-#ifdef SUPPORT_TAGS
-	if (setup_use_tagged_queuing < 0)
-		setup_use_tagged_queuing = 0;
-#endif
 
 #ifdef REAL_DMA
 	/* If running on a Falcon and if there's TT-Ram (i.e., more than one
@@ -930,6 +926,10 @@ static int __init atari_scsi_probe(struc
 
 	host_flags |= IS_A_TT() ? 0 : FLAG_LATE_DMA_SETUP;
 
+#ifdef SUPPORT_TAGS
+	host_flags |= setup_use_tagged_queuing > 0 ? FLAG_TAGGED_QUEUING : 0;
+#endif
+
 	NCR5380_init(instance, host_flags);
 
 	if (IS_A_TT()) {
drivers/scsi/sun3_scsi.c +6 -6
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -522,6 +522,7 @@ static int __init sun3_scsi_probe(struct
 	int error;
 	struct resource *irq, *mem;
 	unsigned char *ioaddr;
+	int host_flags = 0;
 #ifdef SUN3_SCSI_VME
 	int i;
 #endif
@@ -535,11 +536,6 @@ static int __init sun3_scsi_probe(struct
 	if (setup_hostid >= 0)
 		sun3_scsi_template.this_id = setup_hostid & 7;
 
-#ifdef SUPPORT_TAGS
-	if (setup_use_tagged_queuing < 0)
-		setup_use_tagged_queuing = 1;
-#endif
-
 #ifdef SUN3_SCSI_VME
 	ioaddr = NULL;
 	for (i = 0; i < 2; i++) {
@@ -601,7 +597,11 @@ static int __init sun3_scsi_probe(struct
 	instance->io_port = (unsigned long)ioaddr;
 	instance->irq = irq->start;
 
-	NCR5380_init(instance, 0);
+#ifdef SUPPORT_TAGS
+	host_flags |= setup_use_tagged_queuing > 0 ? FLAG_TAGGED_QUEUING : 0;
+#endif
+
+	NCR5380_init(instance, host_flags);
 
 	error = request_irq(instance->irq, scsi_sun3_intr, 0,
 	                    "NCR5380", instance);
drivers/scsi/mac_scsi.c +4 -4
Index: linux/drivers/scsi/mac_scsi.c
===================================================================
@@ -411,10 +411,6 @@ static int __init mac_scsi_probe(struct
 		mac_scsi_template.sg_tablesize = setup_sg_tablesize;
 	if (setup_hostid >= 0)
 		mac_scsi_template.this_id = setup_hostid & 7;
-#ifdef SUPPORT_TAGS
-	if (setup_use_tagged_queuing < 0)
-		setup_use_tagged_queuing = 0;
-#endif
 	if (setup_use_pdma < 0)
 		setup_use_pdma = 0;
 
@@ -440,6 +436,10 @@ static int __init mac_scsi_probe(struct
 	mac_scsi_reset_boot(instance);
 #endif
 
+#ifdef SUPPORT_TAGS
+	host_flags |= setup_use_tagged_queuing > 0 ? FLAG_TAGGED_QUEUING : 0;
+#endif
+
 	NCR5380_init(instance, host_flags);
 
 	if (instance->irq != NO_IRQ) {
Reviewed-by on v2 33/36
#83 lore raw

Re: [PATCH v2 33/36] atari_NCR5380: Introduce FLAG_TAGGED_QUEUING

Quoted 10 lines · Finn Thain

The static variable setup_use_tagged_queuing is declared in mac_scsi.c, sun3_scsi.c and atari_scsi.c and doesn't belong in the core driver. None of the other NCR5380 drivers suffer from this layering issue which makes merging the core drivers more difficult and will likely hinder plans for future use of platform data to configure the driver.

Replace the static variable with a host flag. This way it can be reported along with the other flags.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#84 lore raw

PATCH v2 34/36 atari_NCR5380: Move static TagAlloc array to host data

In reply to Finn Thain

The atari_NCR5380.c core driver keeps some per-host data in a static variable which limits the driver to a single instance. Fix this by moving TagAlloc to the hostdata struct.

---
 drivers/scsi/NCR5380.h       |   12 ++++++++++++
 drivers/scsi/atari_NCR5380.c |   27 +++++++++------------------
 2 files changed, 21 insertions(+), 18 deletions(-)
drivers/scsi/NCR5380.h +12 -0
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -245,6 +245,15 @@
 #define FLAG_TAGGED_QUEUING		64	/* as X3T9.2 spelled it */
 
 #ifndef ASM
+
+#ifdef SUPPORT_TAGS
+struct tag_alloc {
+	DECLARE_BITMAP(allocated, MAX_TAGS);
+	int nr_allocated;
+	int queue_size;
+};
+#endif
+
 struct NCR5380_hostdata {
 	NCR5380_implementation_fields;		/* implementation specific */
 	struct Scsi_Host *host;			/* Host backpointer */
@@ -274,6 +283,9 @@ struct NCR5380_hostdata {
 	int read_overruns;                /* number of bytes to cut from a
 	                                   * transfer to handle chip overruns */
 	int retain_dma_intr;
+#ifdef SUPPORT_TAGS
+	struct tag_alloc TagAlloc[8][8];	/* 8 targets and 8 LUNs */
+#endif
 #ifdef PSEUDO_DMA
 	unsigned spin_max_r;
 	unsigned spin_max_w;
drivers/scsi/atari_NCR5380.c +9 -18
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -274,26 +274,17 @@ static struct scsi_host_template *the_te
  * important: the tag bit must be cleared before 'nr_allocated' is decreased.
  */
 
-typedef struct {
-	DECLARE_BITMAP(allocated, MAX_TAGS);
-	int nr_allocated;
-	int queue_size;
-} TAG_ALLOC;
-
-static TAG_ALLOC TagAlloc[8][8];	/* 8 targets and 8 LUNs */
-
-
 static void __init init_tags(struct NCR5380_hostdata *hostdata)
 {
 	int target, lun;
-	TAG_ALLOC *ta;
+	struct tag_alloc *ta;
 
 	if (!(hostdata->flags & FLAG_TAGGED_QUEUING))
 		return;
 
 	for (target = 0; target < 8; ++target) {
 		for (lun = 0; lun < 8; ++lun) {
-			ta = &TagAlloc[target][lun];
+			ta = &hostdata->TagAlloc[target][lun];
 			bitmap_zero(ta->allocated, MAX_TAGS);
 			ta->nr_allocated = 0;
 			/* At the beginning, assume the maximum queue size we could
@@ -324,8 +315,8 @@ static int is_lun_busy(struct scsi_cmnd
 	    !(hostdata->flags & FLAG_TAGGED_QUEUING) ||
 	    !cmd->device->tagged_supported)
 		return 0;
-	if (TagAlloc[cmd->device->id][lun].nr_allocated >=
-	    TagAlloc[cmd->device->id][lun].queue_size) {
+	if (hostdata->TagAlloc[scmd_id(cmd)][lun].nr_allocated >=
+	    hostdata->TagAlloc[scmd_id(cmd)][lun].queue_size) {
 		dprintk(NDEBUG_TAGS, "scsi%d: target %d lun %d: no free tags\n",
 			   H_NO(cmd), cmd->device->id, lun);
 		return 1;
@@ -355,7 +346,7 @@ static void cmd_get_tag(struct scsi_cmnd
 		dprintk(NDEBUG_TAGS, "scsi%d: target %d lun %d now allocated by untagged "
 			   "command\n", H_NO(cmd), cmd->device->id, lun);
 	} else {
-		TAG_ALLOC *ta = &TagAlloc[cmd->device->id][lun];
+		struct tag_alloc *ta = &hostdata->TagAlloc[scmd_id(cmd)][lun];
 
 		cmd->tag = find_first_zero_bit(ta->allocated, MAX_TAGS);
 		set_bit(cmd->tag, ta->allocated);
@@ -385,7 +376,7 @@ static void cmd_free_tag(struct scsi_cmn
 		printk(KERN_NOTICE "scsi%d: trying to free bad tag %d!\n",
 		       H_NO(cmd), cmd->tag);
 	} else {
-		TAG_ALLOC *ta = &TagAlloc[cmd->device->id][lun];
+		struct tag_alloc *ta = &hostdata->TagAlloc[scmd_id(cmd)][lun];
 		clear_bit(cmd->tag, ta->allocated);
 		ta->nr_allocated--;
 		dprintk(NDEBUG_TAGS, "scsi%d: freed tag %d for target %d lun %d\n",
@@ -397,14 +388,14 @@ static void cmd_free_tag(struct scsi_cmn
 static void free_all_tags(struct NCR5380_hostdata *hostdata)
 {
 	int target, lun;
-	TAG_ALLOC *ta;
+	struct tag_alloc *ta;
 
 	if (!(hostdata->flags & FLAG_TAGGED_QUEUING))
 		return;
 
 	for (target = 0; target < 8; ++target) {
 		for (lun = 0; lun < 8; ++lun) {
-			ta = &TagAlloc[target][lun];
+			ta = &hostdata->TagAlloc[target][lun];
 			bitmap_zero(ta->allocated, MAX_TAGS);
 			ta->nr_allocated = 0;
 		}
@@ -2209,7 +2200,7 @@ static void NCR5380_information_transfer
 						 */
 						/* ++Andreas: the mid level code knows about
 						   QUEUE_FULL now. */
-						TAG_ALLOC *ta = &TagAlloc[cmd->device->id][cmd->device->lun];
+						struct tag_alloc *ta = &hostdata->TagAlloc[scmd_id(cmd)][cmd->device->lun];
 						dprintk(NDEBUG_TAGS, "scsi%d: target %d lun %llu returned "
 							   "QUEUE_FULL after %d commands\n",
 							   HOSTNO, cmd->device->id, cmd->device->lun,
Reviewed-by on v2 34/36
#85 lore raw

Re: [PATCH v2 34/36] atari_NCR5380: Move static TagAlloc array to host data

Quoted 6 lines · Finn Thain

The atari_NCR5380.c core driver keeps some per-host data in a static variable which limits the driver to a single instance. Fix this by moving TagAlloc to the hostdata struct.

Hmm. This really cries to be converted to the generic blk-tag code. But it'll do for now.

Cheers,

Hannes

Signature · 4 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
author
#86 lore raw

PATCH v2 35/36 atari_NCR5380: Move static co-routine variables to host data

In reply to Finn Thain

Unlike NCR5380.c, the atari_NCR5380.c core driver is limited to a single instance because co-routine state is stored globally.

Fix this by removing the static scsi host pointer. For the co-routine, obtain this pointer from the work_struct pointer instead. For the interrupt handler, obtain it from the dev_id argument.

---
 drivers/scsi/NCR5380.h       |    2 +
 drivers/scsi/atari_NCR5380.c |   61 +++++++++++++++----------------------------
 drivers/scsi/atari_scsi.c    |    8 ++---
 3 files changed, 28 insertions(+), 43 deletions(-)
drivers/scsi/NCR5380.h +2 -0
Index: linux/drivers/scsi/NCR5380.h
===================================================================
@@ -283,6 +283,8 @@ struct NCR5380_hostdata {
 	int read_overruns;                /* number of bytes to cut from a
 	                                   * transfer to handle chip overruns */
 	int retain_dma_intr;
+	struct work_struct main_task;
+	volatile int main_running;
 #ifdef SUPPORT_TAGS
 	struct tag_alloc TagAlloc[8][8];	/* 8 targets and 8 LUNs */
 #endif
drivers/scsi/atari_NCR5380.c +22 -39

164 lines not on this page · raw message

drivers/scsi/atari_scsi.c +4 -4
Index: linux/drivers/scsi/atari_scsi.c
===================================================================
@@ -110,7 +110,7 @@
 #define NCR5380_dma_xfer_len(instance, cmd, phase) \
         atari_dma_xfer_len(cmd->SCp.this_residual, cmd, !((phase) & SR_IO))
 
-#define NCR5380_acquire_dma_irq(instance)      falcon_get_lock()
+#define NCR5380_acquire_dma_irq(instance)      falcon_get_lock(instance)
 #define NCR5380_release_dma_irq(instance)      falcon_release_lock()
 
 #include "NCR5380.h"
@@ -468,15 +468,15 @@ static void falcon_release_lock(void)
  * command immediately but tell the SCSI mid-layer to defer.
  */
 
-static int falcon_get_lock(void)
+static int falcon_get_lock(struct Scsi_Host *instance)
 {
 	if (IS_A_TT())
 		return 1;
 
 	if (in_interrupt()) {
-		return stdma_try_lock(scsi_falcon_intr, NULL);
+		return stdma_try_lock(scsi_falcon_intr, instance);
 	} else {
-		stdma_lock(scsi_falcon_intr, NULL);
+		stdma_lock(scsi_falcon_intr, instance);
 		return 1;
 	}
 }
Reviewed-by on v2 35/36
#87 lore raw

Re: [PATCH v2 35/36] atari_NCR5380: Move static co-routine variables to host data

Quoted 9 lines · Finn Thain

Unlike NCR5380.c, the atari_NCR5380.c core driver is limited to a single instance because co-routine state is stored globally.

Fix this by removing the static scsi host pointer. For the co-routine, obtain this pointer from the work_struct pointer instead. For the interrupt handler, obtain it from the dev_id argument.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
author
#88 lore raw

PATCH v2 36/36 atari_NCR5380: Remove RESET_RUN_DONE macro

In reply to Finn Thain

There's no need to run the cmd->done callback for aborted commands. Remove the old EH code and the RESET_RUN_DONE macro.

---
 drivers/scsi/atari_NCR5380.c |   88 -------------------------------------------
 drivers/scsi/sun3_scsi.c     |    1 
 2 files changed, 89 deletions(-)
drivers/scsi/atari_NCR5380.c +0 -88
Index: linux/drivers/scsi/atari_NCR5380.c
===================================================================
@@ -2881,9 +2881,6 @@ static int NCR5380_bus_reset(struct scsi
 	struct NCR5380_hostdata *hostdata = shost_priv(instance);
 	int i;
 	unsigned long flags;
-#if defined(RESET_RUN_DONE)
-	struct scsi_cmnd *connected, *disconnected_queue;
-#endif
 
 	NCR5380_print_status(instance);
 
@@ -2902,89 +2899,6 @@ static int NCR5380_bus_reset(struct scsi
 	 * through anymore ... */
 	(void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
 
-	/* MSch 20140115 - looking at the generic NCR5380 driver, all of this
-	 * should go.
-	 * Catch-22: if we don't clear all queues, the SCSI driver lock will
-	 * not be reset by atari_scsi_reset()!
-	 */
-
-#if defined(RESET_RUN_DONE)
-	/* XXX Should now be done by midlevel code, but it's broken XXX */
-	/* XXX see below                                            XXX */
-
-	/* MSch: old-style reset: actually abort all command processing here */
-
-	/* After the reset, there are no more connected or disconnected commands
-	 * and no busy units; to avoid problems with re-inserting the commands
-	 * into the issue_queue (via scsi_done()), the aborted commands are
-	 * remembered in local variables first.
-	 */
-	local_irq_save(flags);
-	connected = (struct scsi_cmnd *)hostdata->connected;
-	hostdata->connected = NULL;
-	disconnected_queue = (struct scsi_cmnd *)hostdata->disconnected_queue;
-	hostdata->disconnected_queue = NULL;
-#ifdef SUPPORT_TAGS
-	free_all_tags();
-#endif
-	for (i = 0; i < 8; ++i)
-		hostdata->busy[i] = 0;
-#ifdef REAL_DMA
-	hostdata->dma_len = 0;
-#endif
-	local_irq_restore(flags);
-
-	/* In order to tell the mid-level code which commands were aborted,
-	 * set the command status to DID_RESET and call scsi_done() !!!
-	 * This ultimately aborts processing of these commands in the mid-level.
-	 */
-
-	if ((cmd = connected)) {
-		dprintk(NDEBUG_ABORT, "scsi%d: reset aborted a connected command\n", H_NO(cmd));
-		cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
-		cmd->scsi_done(cmd);
-	}
-
-	for (i = 0; (cmd = disconnected_queue); ++i) {
-		disconnected_queue = NEXT(cmd);
-		SET_NEXT(cmd, NULL);
-		cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
-		cmd->scsi_done(cmd);
-	}
-	if (i > 0)
-		dprintk(NDEBUG_ABORT, "scsi: reset aborted %d disconnected command(s)\n", i);
-
-	/* The Falcon lock should be released after a reset...
-	 */
-	/* ++guenther: moved to atari_scsi_reset(), to prevent a race between
-	 * unlocking and enabling dma interrupt.
-	 */
-/*	falcon_release_lock_if_possible( hostdata );*/
-
-	/* since all commands have been explicitly terminated, we need to tell
-	 * the midlevel code that the reset was SUCCESSFUL, and there is no
-	 * need to 'wake up' the commands by a request_sense
-	 */
-	return SUCCESS;
-#else /* 1 */
-
-	/* MSch: new-style reset handling: let the mid-level do what it can */
-
-	/* ++guenther: MID-LEVEL IS STILL BROKEN.
-	 * Mid-level is supposed to requeue all commands that were active on the
-	 * various low-level queues. In fact it does this, but that's not enough
-	 * because all these commands are subject to timeout. And if a timeout
-	 * happens for any removed command, *_abort() is called but all queues
-	 * are now empty. Abort then gives up the falcon lock, which is fatal,
-	 * since the mid-level will queue more commands and must have the lock
-	 * (it's all happening inside timer interrupt handler!!).
-	 * Even worse, abort will return NOT_RUNNING for all those commands not
-	 * on any queue, so they won't be retried ...
-	 *
-	 * Conclusion: either scsi.c disables timeout for all resetted commands
-	 * immediately, or we lose!  As of linux-2.0.20 it doesn't.
-	 */
-
 	/* After the reset, there are no more connected or disconnected commands
 	 * and no busy units; so clear the low-level status here to avoid
 	 * conflicts when the mid-level code tries to wake up the affected
@@ -3014,7 +2928,5 @@ static int NCR5380_bus_reset(struct scsi
 	maybe_release_dma_irq(instance);
 	local_irq_restore(flags);
 
-	/* we did no complete reset of all commands, so a wakeup is required */
 	return SUCCESS;
-#endif /* 1 */
 }
drivers/scsi/sun3_scsi.c +0 -1
Index: linux/drivers/scsi/sun3_scsi.c
===================================================================
@@ -39,7 +39,6 @@
 /* Definitions for the core NCR5380 driver. */
 
 #define REAL_DMA
-#define RESET_RUN_DONE
 /* #define SUPPORT_TAGS */
 /* minimum number of bytes to do dma on */
 #define DMA_MIN_SIZE                    129
Reviewed-by on v2 36/36
#89 lore raw

Re: [PATCH v2 36/36] atari_NCR5380: Remove RESET_RUN_DONE macro

Quoted 5 lines · Finn Thain

There's no need to run the cmd->done callback for aborted commands. Remove the old EH code and the RESET_RUN_DONE macro.

Cheers,

Hannes

Signature · 8 lines
Dr. Hannes Reinecke		      zSeries & Storage
[email protected]			      +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: J. Hawn, J. Guild, F. Imendörffer, HRB 16746 (AG Nürnberg)
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
maintainer Tested-by on the v2 series
#90 lore raw
In reply to Finn Thain

Finn,

Quoted 12 lines

This patch series has fixes for bugs and compiler warnings as well as code cleanup and modernization. It covers all ten NCR5380 drivers and the three core NCR5380 drivers so it's fairly large.

These patches remove a lot of duplicated code and C pre-processor abuse. There are also patches for scsi_add_host() conversion for atari_scsi, mac_scsi and sun3_scsi.

Some steps are taken toward re-unification of the NCR5380 core driver forks by reducing divergence between them. Also, the atari_NCR5380.c core driver is generalized so it can be used by sun3_scsi.c (and others).

Quoted 8 lines

I have compile-tested all of the NCR5380 drivers (x86, ARM and m68k) and executed mac_scsi and dmx3191d on suitable hardware. I found no regressions but the core NCR5380 drivers have bugs unrelated to these patches.

Testing mac_scsi and dmx3191d provides only limited code coverage for these patches. Some testing on Sun 3, Atari ST and/or Atari TT would be nice (I don't have the hardware).

Tested atari_scsi on Falcon / CT60 hardware - no regressions over v1 that I've seen.

Quoted 65 lines

There are old bugs relating to exception handling and autosense in the core NCR5380 drivers that can make testing difficult. I'm working on a series of patches to address these bugs. Those patches are not yet ready for submission but they were helpful for the testing I did and may be helpful to other testers. Let me know if so.

Changes since v1:
- Re-based to v3.17.
- Addressed issues raised in code review (see relevant patches for details).
- Added patches 30 to 36, to remove sun3_NCR5380.c entirely and remove more static variables from atari_NCR5380.c.

This patch set stops short of parameterizing the drivers with platform_data and/or ops struct. IMHO, it would be premature to do such refactoring before drivers have been purged of static variables and certain #ifdefs. After that is done, entire modules could be replaced with platform devices.

Several patches in this set address issues with the tagged command queueing code (see patches 7, 33 and 34). I've since learned from recent discussions on the linux-scsi list that use of the tag member in struct scsi_cmnd is deprecated. If removal of the tag member is imminent then it may be better to remove TCQ support from all of the NCR5380 drivers instead of this cleanup. Or it could be done separately.

Removal of TCQ code might make re-unification easier, by bringing atari_NCR5380.c closer to NCR5380.c and eliminating some #ifdefs. Changes to the TCQ code would affect atari_scsi, being the only driver to #define SUPPORT_TAGS.

---
 MAINTAINERS                         |    1 
 arch/m68k/atari/config.c            |   27 
 arch/m68k/atari/stdma.c             |   61 
 arch/m68k/include/asm/atari_stdma.h |    4 
 arch/m68k/include/asm/macintosh.h   |    4 
 arch/m68k/mac/config.c              |  146 +
 arch/m68k/sun3/config.c             |   60 
 drivers/scsi/Kconfig                |    2 
 drivers/scsi/NCR5380.c              |  295 +--
 drivers/scsi/NCR5380.h              |   78 
 drivers/scsi/arm/cumana_1.c         |   18 
 drivers/scsi/arm/oak.c              |   23 
 drivers/scsi/atari_NCR5380.c        |  981 +++++-------
 drivers/scsi/atari_scsi.c           |  676 +++-----
 drivers/scsi/atari_scsi.h           |   60 
 drivers/scsi/dmx3191d.c             |   31 
 drivers/scsi/dtc.c                  |   85 -
 drivers/scsi/dtc.h                  |   26 
 drivers/scsi/g_NCR5380.c            |  224 --
 drivers/scsi/g_NCR5380.h            |   26 
 drivers/scsi/mac_scsi.c             |  542 ++----
 drivers/scsi/mac_scsi.h             |   74 
 drivers/scsi/pas16.c                |  106 -
 drivers/scsi/pas16.h                |   21 
 drivers/scsi/sun3_NCR5380.c         | 2933 ------------------------------------
 drivers/scsi/sun3_scsi.c            |  512 ++----
 drivers/scsi/sun3_scsi.h            |   84 -
 drivers/scsi/t128.c                 |   83 -
 drivers/scsi/t128.h                 |   23 
 29 files changed, 1745 insertions(+), 5461 deletions(-)
author
#91 lore raw
Quoted 5 lines · Michael Schmitz

Tested atari_scsi on Falcon / CT60 hardware - no regressions over v1 that I've seen.

Thanks for testing.

"No regressions over v1" means "no regressions", right?

A message that is not in the archive (sent off-list or not yet received): [email protected]

maintainer
#93 lore raw

Hi Finn,

Quoted 13 lines

Thanks for testing.

"No regressions over v1" means "no regressions", right?

Well, what would I compare the driver performance to? With your patches to sort out locking races, the driver is more stable than I've ever seen it in years. That's a definite win. Big improvement over the driver in its current state in m68k and mainstream (which locks up quite reliably with even moderate concurrent IDE and SCSI I/O for me). No regression over v1 or patches that you sent for me to test off-list.

Quoted 6 lines

On the other hand, I've seen warnings about lost bytes (stuck in the DMA fifo) for the first time _ever_ with the new driver - we've discussed that at length, and it is still unclear why these happen. This is a known NCR5380 issue, and pretty much anything could have precipitated that. Must have happened for other Falcon users before in the past, because the interrupt handler explicitly checks for this condition.

I went back and checked test logs from driver tests before any of your patches - no regressions over vanilla 3.17 or 3.16.

The 'lost bytes' error is rare enough that it would not have shown in those tests. Vanilla kernels run into the ST-DMA locking race at about 7% of the total test set.

The last kernel that performed with a similar stability as with your patches was 2.4.30 or thereabouts.

Cheers,

Michael

#94 lore raw

2014-11-05 0:36 GMT+01:00 Michael Schmitz <[email protected]>:

Quoted 23 lines

Hi Finn,

Quoted 19 lines

Thanks for testing.

"No regressions over v1" means "no regressions", right?

Well, what would I compare the driver performance to? With your patches to sort out locking races, the driver is more stable than I've ever seen it in years. That's a definite win. Big improvement over the driver in its current state in m68k and mainstream (which locks up quite reliably with even moderate concurrent IDE and SCSI I/O for me). No regression over v1 or patches that you sent for me to test off-list.

On the other hand, I've seen warnings about lost bytes (stuck in the DMA fifo) for the first time _ever_ with the new driver - we've discussed that at length, and it is still unclear why these happen. This is a known NCR5380 issue, and pretty much anything could have precipitated that. Must have happened for other Falcon users before in the past, because the interrupt handler explicitly checks for this condition.

Do you know about the Falcon's disturbance in the SDMA clock signal hardware problem?
Most Falcons, specially those used in music studios, have a hardware patch to fix this, it's normally called SCSI patch.

Some more info:

http://didierm.pagesperso-orange.fr/doc/eng/c_0a.htm

#95 lore raw
Quoted 8 lines · David Gálvez

Do you know about the Falcon's disturbance in the SDMA clock signal hardware problem?
Most Falcons, specially those used in music studios, have a hardware patch to fix this, it's normally called SCSI patch.

Some more info:

http://didierm.pagesperso-orange.fr/doc/eng/c_0a.htm

So this adds additional buffering to the clock.

Note that input pins 3 and 5 of the 74HC04 are left floating! I recommend tying them to either GND (pin 7) or VCC (pin 14), to avoid them picking up high-frequency signals and consuming power.

Gr{oetje,eeting}s,

Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- [email protected]

In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html

maintainer
#96 lore raw

David, Geert,

my Falcon has some variant of this clock patch installed - it may not be precisely the one described but reasonably close. It also has one of the old 030 accelerator tricks (clock doubling of the 030 if the CPU does not do bus cycles - named Skunk) fitted; the clock patch was installed at the same time.

The Falcon ran stable with just SCSI disks in use (so no locking races) until a few years ago when I started to use it for kernel hacking. There were the occasional SCSI lockups which I attributed to the SCSI clock problem, for want of a better explanation. IIRC when the clock signal to the 5380 becomes unstable, the chip locks up and needs to be reset. With the old 2.4 kernels, recovery from reset worked OK and I've not seen disk corruption or hard read errors.

2.6 kernels changed a lot of things around SCSI midlevel and error handling. I could never make error recovery from these SCSI lockups work in 2.6 or 3.x until Arnd's locking fixes (and my patch to defer command queueing if the lock had been taken by IDE). The lockups did not stop happening until Finn's patches - and I probably need to emphasize again that they are gone entirely now. It does seem 2.4 suffered from similar race problems, the driver just managed to recover from those.

Leaves the current instability - I did some work on the CT60 accelerator (reflashed the firmware so I can use the CTPCI board). This might have caused the system to become more unstable. Needs more investigation.

Cheers,

Michael

Quoted 26 lines · Geert Uytterhoeven
Quoted 8 lines · David Gálvez

Do you know about the Falcon's disturbance in the SDMA clock signal hardware problem?
Most Falcons, specially those used in music studios, have a hardware patch to fix this, it's normally called SCSI patch.

Some more info:

http://didierm.pagesperso-orange.fr/doc/eng/c_0a.htm

So this adds additional buffering to the clock.

Note that input pins 3 and 5 of the 74HC04 are left floating! I recommend tying them to either GND (pin 7) or VCC (pin 14), to avoid them picking up high-frequency signals and consuming power.

Gr{oetje,eeting}s,

Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- [email protected]

In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds

author
#97 lore raw
Quoted 3 lines · Michael Schmitz

Leaves the current instability - I did some work on the CT60 accelerator (reflashed the firmware so I can use the CTPCI board). This might have caused the system to become more unstable. Needs more investigation.

I gather from the emails we've exchanged that the "current" instability (data corruption) dates back to March or thereabouts, so it is unrelated to this patch series.

The lockups have been resolved, which leaves only the ST DMA FIFO issue, which seems to be an old problem. From the comments in atari_scsi, it doesn't look like this was ever resolved.

/* If the DMA was active, but now bit 1 is not clear, it is some
* other 5380 interrupt that finishes the DMA transfer. We have to
* calculate the number of residual bytes and give a warning if
* bytes are stuck in the ST-DMA fifo (there's no way to reach them!) */
if (atari_dma_active && (dma_stat & 0x02)) {
unsigned long transferred;

transferred = SCSI_DMA_GETADR() - atari_dma_startaddr; /* The ST-DMA address is incremented in 2-byte steps, but the
* data are written only in 16-byte chunks. If the number of
* transferred bytes is not divisible by 16, the remainder is
* lost somewhere in outer space.
*/
if (transferred & 15)
printk(KERN_ERR "SCSI DMA error: %ld bytes lost in "
"ST-DMA fifo\n", transferred & 15);

Presuming that this is an old issue (apparently timing sensitive), we can conclude that no regressions were observed in your tests. I'm content with this presumption. I gather that you are too, or you would not have sent a "tested-by" tag. Which seems to put the ball in Geert's court?

maintainer
#98 lore raw

Hi Finn,

Quoted 7 lines
Quoted 3 lines

Leaves the current instability - I did some work on the CT60 accelerator (reflashed the firmware so I can use the CTPCI board). This might have caused the system to become more unstable. Needs more investigation.

I gather from the emails we've exchanged that the "current" instability (data corruption) dates back to March or thereabouts, so it is unrelated to this patch series.

Absolutely right - meant to add that but got interrupted in that train of thought :-(

Quoted 22 lines

The lockups have been resolved, which leaves only the ST DMA FIFO issue, which seems to be an old problem. From the comments in atari_scsi, it doesn't look like this was ever resolved.

/* If the DMA was active, but now bit 1 is not clear, it is some
* other 5380 interrupt that finishes the DMA transfer. We have to
* calculate the number of residual bytes and give a warning if
* bytes are stuck in the ST-DMA fifo (there's no way to reach them!) */
if (atari_dma_active && (dma_stat & 0x02)) {
unsigned long transferred;

transferred = SCSI_DMA_GETADR() - atari_dma_startaddr; /* The ST-DMA address is incremented in 2-byte steps, but the
* data are written only in 16-byte chunks. If the number of
* transferred bytes is not divisible by 16, the remainder is
* lost somewhere in outer space.
*/
if (transferred & 15)
printk(KERN_ERR "SCSI DMA error: %ld bytes lost in "
"ST-DMA fifo\n", transferred & 15);

Quoted 4 lines

Presuming that this is an old issue (apparently timing sensitive), we can conclude that no regressions were observed in your tests. I'm content with this presumption. I gather that you are too, or you would not have sent a "tested-by" tag. Which seems to put the ball in Geert's court?

Right again - though it's probably not Geert but James who needs to give the go-ahead.

Cheers,

Michael

author
#99 lore raw
Quoted 1 line · Michael Schmitz

it's probably not Geert but James who needs to give the go-ahead.

Given Geert's objections to the changes under arch/m68k in v1, I'm hoping for an acked-by from Geert for v2...

maintainer Acked-by
#100 lore raw

Hi Finn,

Quoted 4 lines · Finn Thain
Quoted 1 line

it's probably not Geert but James who needs to give the go-ahead.

Given Geert's objections to the changes under arch/m68k in v1, I'm hoping for an acked-by from Geert for v2...

I'm happy with the arch/m68k changes in v2 (modulo the PAGE_SIZE comment on Sun-3), so please add my

after fixing that one.
As I'm not afraid of merge conflicts, I think this can go in through the SCSI tree? James?

Note that there's still room for improvement in the individual drivers, using more modern infrastructure (e.g. using devm_*() calls, and getting rid of the multiple ATARIHW_PRESENT() checks using e.g. platform_data or regmap). But this is already a giant step forward.

Thanks a lot for doing this cleanup!
Removing ca. 3700 LoC deserves you a spot in the LoC removal Hall of Fame!

Gr{oetje,eeting}s,

Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- [email protected]

In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds