Skip to contentSkip to conversation

[2.5.21] s390 tape fixes.

PATCH New Martin Schwidefsky 1 participant 1 message Jun 13, 2002 s390

lore
Share & tools
lore
#0 lore raw

PATCH 1/1 [2.5.21] s390 tape fixes.

Hi,
the new tape driver in 2.5.21 is a more or less 1:1 copy of the 2.4 code. To get it to work some adaptions are needed. Here they are.

blue skies,
Martin.

drivers/s390/char/tape.c +61 -23
diff -urN linux-2.5.21/drivers/s390/char/tape.c linux-2.5.21-s390/drivers/s390/char/tape.c
@@ -47,7 +47,9 @@
 #define TAPE_NO_IO          0
 #define TAPE_DO_IO          1
 
-#define TAPE_CIO_PRIVATE_DATA
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,4,16))
+	#define TAPE_CIO_PRIVATE_DATA
+#endif
 
 #ifdef CONFIG_KMOD
 #define tape_request_module(a) request_module(a)
@@ -142,9 +144,12 @@
 	"WTM",
 	"MSN",
 	"LOA",
-	"RCF", /* 3590 */
-	"RAT", /* 3590 */
-	"NOT"
+	"RCF",
+	"RAT",
+	"NOT",
+	"DIS",
+	"ASS",
+	"UAS"
 };
 
 /*******************************************************************
@@ -204,12 +209,21 @@
 	release:tape_proc_devices_release,	/* close */
 };
 
+static struct inode_operations tape_proc_devices_inode_ops =
+{
+#if !(LINUX_VERSION_CODE > KERNEL_VERSION(2,3,98))
+	default_file_ops:&tape_proc_devices_file_ops		/* file ops */
+#endif				/* LINUX_IS_24 */
+};
+
+
 /* 
  * Initialize procfs stuff on startup
  */
 
 static inline void
 tape_proc_init (void) {
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,3,98))
 	tape_proc_devices = create_proc_entry ("tapedevices",
 						S_IFREG | S_IRUGO | S_IWUSR,
 						&proc_root);
@@ -217,6 +231,24 @@
 	        goto error;
 	tape_proc_devices->proc_fops = &tape_proc_devices_file_ops;
 	tape_proc_devices->proc_iops = &tape_proc_devices_inode_ops;
+#else
+	tape_proc_devices = (struct proc_dir_entry *) kmalloc 
+            (sizeof (struct proc_dir_entry), GFP_ATOMIC);
+	if (tape_proc_devices == NULL) 
+	        goto error;
+	memset (tape_proc_devices, 0, sizeof (struct proc_dir_entry));
+	tape_proc_devices->name = "tapedevices";
+	tape_proc_devices->namelen = strlen ("tapedevices");
+	tape_proc_devices->low_ino = 0;
+	tape_proc_devices->mode = (S_IFREG | S_IRUGO | S_IWUSR);
+	tape_proc_devices->nlink = 1;
+	tape_proc_devices->uid = 0;
+	tape_proc_devices->gid = 0;
+	tape_proc_devices->size = 0;
+	tape_proc_devices->get_info = NULL;
+	tape_proc_devices->ops = &tape_proc_devices_inode_ops;
+	proc_register (&proc_root, tape_proc_devices);
+#endif
 	return;
  error:
 	PRINT_WARN ("tape: Cannot register procfs entry tapedevices\n");
@@ -359,8 +391,14 @@
 static inline void
 tape_proc_cleanup (void)
 {
-        if (tape_proc_devices != NULL)
+        if (tape_proc_devices != NULL){
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,3,98))
 		remove_proc_entry ("tapedevices", &proc_root);
+#else
+		proc_unregister (&proc_root, tape_proc_devices->low_ino);
+		kfree (tape_proc_devices);
+#endif /* LINUX_IS_24 */
+	}
 }
 
 #endif /* CONFIG_PROC_FS */
@@ -384,12 +422,12 @@
         wake_up_interruptible(&treq->wq);
 }
  
-#ifdef CONFIG_S390_TAPE_BLOCK
 static void tape_schedule_tapeblock(tape_ccw_req_t* treq){
         treq->wakeup = NULL;
+#ifdef CONFIG_S390_TAPE_BLOCK
         tapeblock_schedule_exec_io((tape_dev_t*)(treq->tape_dev));;
-}
 #endif
+}
  
 static void tape_wait_event(tape_ccw_req_t* treq){
         wait_event (treq->wq,(treq->wakeup == NULL));
@@ -400,9 +438,9 @@
 	if (signal_pending (current)) {
 		treq->rc = tape_halt_io(treq->tape_dev);
 		if(treq->rc == -ERESTARTSYS)
-		        PRINT_INFO("IO stopped on irq %d\n",treq->tape_dev->devinfo.irq); /* FIXME: only put into dbf */
+		        tape_sprintf_event(tape_dbf_area, 3, "IO stopped on irq %d\n", treq->tape_dev->devinfo.irq);
                 else if(treq->rc == 0)
-		        PRINT_INFO("could not stop IO,irq was faster on irq %d\n",treq->tape_dev->devinfo.irq); /* FIXME: only put into dbf */
+		        tape_sprintf_event(tape_dbf_area, 3, "could not stop IO,irq was faster on irq %d\n", treq->tape_dev->devinfo.irq);
                 else
 			PRINT_WARN("IO error while stopping IO on irq %d\n",treq->tape_dev->devinfo.irq);
 	}
@@ -632,7 +670,9 @@
 	return 1;
 }
 
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,3,99))
 __setup("tape=", tape_parm_call_setup);
+#endif   /* kernel >2.3.99 */
 #endif   /* not defined MODULE */
 
 
@@ -736,9 +776,8 @@
 	}
 		
 	for (frontend=tape_first_front;frontend!=NULL;frontend=frontend->next){
-		if(frontend->mkdevfstree(td) == NULL){
+		if(frontend->setup_device(td) != 0)
 			goto out_undo;
-		}
 	}
 #endif
 #ifdef TAPE_CIO_PRIVATE_DATA
@@ -771,7 +810,7 @@
 	free_irq (td->devinfo.irq, &(td->devstat)); 
 #ifdef CONFIG_DEVFS_FS
         for (frontend=tape_first_front;frontend!=NULL;frontend=frontend->next)
-                frontend->rmdevfstree(td);
+                frontend->cleanup_device(td);
         tape_rmdevfsroot(td);
 #endif
 	tape_state_set(td,TS_NOT_OPER);
@@ -1007,8 +1046,8 @@
 			/* Wrong type - try next one */
 			continue;
 
-		tape_sprintf_event (tape_dbf_area,3,"det irq:  %x\n",irq);
-		tape_sprintf_event (tape_dbf_area,3,"cu     :  %x\n",disc->cu_type);
+		tape_sprintf_event (tape_dbf_area, 4, "det irq:  %x\n", irq);
+		tape_sprintf_event (tape_dbf_area, 4, "cu     :  %x\n", disc->cu_type);
 
 
 		if(!tape_autoprobe) {
@@ -1219,13 +1258,13 @@
 			rc = -ERESTARTSYS;
 			goto out;
 		case -ENODEV:
-		        PRINT_INFO ("device gone, retry\n"); /* FIXME: s390dbf only */
+		        tape_sprintf_exception(tape_dbf_area, 2, "device gone, retry\n");
 			break;
 		case -EIO:
-			PRINT_INFO ("I/O error, retry\n"); /* FIXME: s390dbf only */
+			tape_sprintf_exception(tape_dbf_area, 2, "I/O error, retry\n");
 			break;
 		case -EBUSY:
-			PRINT_INFO ( "device busy, retry later\n"); /* FIXME: s390dbf only */
+			tape_sprintf_exception(tape_dbf_area, 2, "device busy, retry later\n");
 			break;
 		default:
 			PRINT_ERR ( "line %d unknown RC=%d, please report"
@@ -1709,9 +1748,9 @@
 
 	tape_init_devregs();
 #ifdef TAPE_DEBUG
-        tape_dbf_area = debug_register ( "tape", 2, 2, 3*sizeof(long));
+        tape_dbf_area = debug_register ( "tape", 1, 2, 3*sizeof(long));
         debug_register_view(tape_dbf_area,&debug_sprintf_view);
-        tape_sprintf_event (tape_dbf_area,3,"begin init\n");
+        tape_sprintf_event (tape_dbf_area,3,"begin init: ($Revision: 1.87 $)\n");
 #endif /* TAPE_DEBUG */
 	tape_print_banner();
 #ifndef MODULE
@@ -1720,7 +1759,6 @@
 #ifdef CONFIG_DEVFS_FS
         tape_devfs_root_entry=devfs_mk_dir (NULL, "tape", NULL);
 #endif /* CONFIG_DEVFS_FS */
-
         tape_sprintf_event (tape_dbf_area,3,"dev detect\n");
 	/* Allocate the tape structures */
         if (*tape!=NULL) { /* if parameters are present */
@@ -1766,7 +1804,7 @@
 
 #ifdef MODULE
 MODULE_AUTHOR("(C) 2001 IBM Deutschland Entwicklung GmbH by Carsten Otte and Michael Holzheu ([email protected],[email protected])");
-MODULE_DESCRIPTION("Linux on zSeries channel attached tape device driver");
+MODULE_DESCRIPTION("Linux on zSeries channel attached tape device driver ($Revision: 1.87 $)");
 MODULE_PARM (tape, "1-" __MODULE_STRING (256) "s");
 
 /*
@@ -1820,7 +1858,7 @@
 	tape_cleanup_disciplines();
 #ifdef CONFIG_DEVFS_FS
 	devfs_unregister (tape_devfs_root_entry); /* devfs checks for NULL */
-#endif CONFIG_DEVFS_FS
+#endif /* CONFIG_DEVFS_FS */
 #ifdef CONFIG_PROC_FS
 	tape_proc_cleanup();
 #endif 
@@ -1879,7 +1917,7 @@
 		case MS_LOADED:
 			PRINT_INFO("(%x): Tape has been mounted\n",td->devstat.devno);
 			break;
-		default:
+		default: 
 			// print nothing
 			break;
 	}
drivers/s390/char/tape.h +12 -7
diff -urN linux-2.5.21/drivers/s390/char/tape.h linux-2.5.21-s390/drivers/s390/char/tape.h
@@ -94,10 +94,12 @@
 	TO_WTM,
 	TO_MSEN,
 	TO_LOAD,
-	TO_READ_CONFIG, /* 3590 */
-	TO_READ_ATTMSG, /* 3590 */
+	TO_READ_CONFIG,
+	TO_READ_ATTMSG,
 	TO_NOTHING,
 	TO_DIS,
+	TO_ASSIGN,
+	TO_UNASSIGN,
 	TO_SIZE
 } tape_op_t;
 
@@ -142,6 +144,8 @@
 typedef int (*tape_setup_device_t) (struct _tape_dev_t*);
 typedef void (*tape_cleanup_device_t) (struct _tape_dev_t*);
 typedef int (*tape_disc_ioctl_overl_t)(struct _tape_dev_t*, unsigned int,unsigned long);
+typedef tape_ccw_req_t* (*tape_assign_dev_t)(struct _tape_dev_t*);
+typedef tape_ccw_req_t* (*tape_unassign_dev_t)(struct _tape_dev_t*);
 #ifdef CONFIG_DEVFS_FS
 typedef devfs_handle_t (*tape_devfs_constructor_t) (struct _tape_dev_t*);
 typedef void (*tape_devfs_destructor_t) (struct _tape_dev_t*);
@@ -165,17 +169,16 @@
 	tape_reqgen_ioctl_t         ioctl;
 	tape_disc_shutdown_t        shutdown;
 	tape_disc_ioctl_overl_t     discipline_ioctl_overload;
+        tape_assign_dev_t           assign;
+        tape_unassign_dev_t         unassign;
 	void*                       next;
 } tape_discipline_t  __attribute__ ((aligned(8)));
 
 /* Frontend */
 
 typedef struct _tape_frontend_t {
-	tape_setup_device_t device_setup;
-#ifdef CONFIG_DEVFS_FS
-	tape_devfs_constructor_t mkdevfstree;
-	tape_devfs_destructor_t rmdevfstree;
-#endif
+	tape_setup_device_t setup_device;
+	tape_cleanup_device_t cleanup_device;
 	void* next;
 } tape_frontend_t  __attribute__ ((aligned(8)));
 
@@ -194,6 +197,7 @@
 
 typedef struct _tape_blk_front_data_t{
 	request_queue_t request_queue;
+	spinlock_t request_queue_lock;
 	struct request* current_request;
 	int blk_retries;
 	long position;
@@ -215,6 +219,7 @@
 	struct file *filp;             /* backpointer to file structure */
 	int tape_state;                /* State of the device. See tape_stat */
 	int medium_state;              /* loaded, unloaded, unkown etc. */
+        int assigned;                  /* for reserve on open */
 	tape_discipline_t* discipline; /* The used discipline */
 	void* discdata;                /* discipline specific data */
 	tape_ccw_req_t* treq;          /* Active Tape request */
drivers/s390/char/tape3480.c +32 -4
diff -urN linux-2.5.21/drivers/s390/char/tape3480.c linux-2.5.21-s390/drivers/s390/char/tape3480.c
@@ -18,6 +18,15 @@
 #include "tape34xx.h"
 #include "tape3480.h"
 
+#ifdef  TAPE_DEBUG
+#ifdef  MODULE
+#define TAPE_DBF (tape_dbf_3480)
+        debug_info_t *tape_dbf_3480 = NULL;
+#else
+#define TAPE_DBF (tape_dbf_area)
+#endif  /* MODULE */
+#endif  /* TAPE_DEBUG */
+
 #ifdef CONFIG_S390_TAPE_3480_MODULE
 static tape_discipline_t* disc;
 
@@ -36,14 +45,25 @@
 		tape_unregister_discipline(disc);
 		kfree(disc);
 	}
+#ifdef TAPE_DEBUG
+#ifdef MODULE
+       debug_unregister(tape_dbf_3480);
+#endif /* MODULE */
+#endif /* TAPE_DEBUG */
 }
+
+#ifdef MODULE
+MODULE_AUTHOR("(C) 2001-2002 IBM Deutschland Entwicklung GmbH");
+MODULE_DESCRIPTION("Linux on zSeries channel attached 3480 tape device driver ($Revision: 1.30 $)");
+#endif /* MODULE */
+
 #endif /* CONFIG_S390_TAPE_3480_MODULE */
 
 int
 tape3480_setup_device(tape_dev_t * td)
 {
 	tape3480_disc_data_t *data = NULL;
-	tape_sprintf_event (tape_dbf_area,6,"3480 dsetup:  %x\n",td->first_minor);
+	tape_sprintf_event (TAPE_DBF, 6, "3480 minor1: %x\n", td->first_minor);
 	data = kmalloc (sizeof (tape3480_disc_data_t), GFP_KERNEL | GFP_DMA);
 	if(data == NULL)
 		return -1;
@@ -69,10 +89,16 @@
 tape3480_init (void)
 {
 	tape_discipline_t *disc;
-	tape_sprintf_event (tape_dbf_area,3,"3480 init\n");
+#ifdef TAPE_DEBUG
+#ifdef MODULE
+        tape_dbf_3480 = debug_register("tape3480", 1, 2, 3*sizeof(long));
+        debug_register_view(tape_dbf_3480, &debug_sprintf_view);
+#endif /* MODULE */
+#endif /* TAPE_DEBUG */
+	tape_sprintf_event (TAPE_DBF,3,"3480 init: $Revision: 1.30 $\n");
 	disc = kmalloc (sizeof (tape_discipline_t), GFP_ATOMIC);
 	if (disc == NULL) {
-	        tape_sprintf_exception (tape_dbf_area,3,"disc:nomem\n");
+	        tape_sprintf_exception (TAPE_DBF,3,"disc:nomem\n");
 		return disc;
 	}
 	disc->owner = THIS_MODULE;
@@ -90,7 +116,9 @@
 	disc->bread = tape34xx_bread;
 	disc->free_bread = tape34xx_free_bread;
 	disc->bread_enable_locate = tape34xx_bread_enable_locate;
+	disc->assign = tape34xx_assign;
+	disc->unassign = tape34xx_unassign;
 	disc->next = NULL;
-	tape_sprintf_event (tape_dbf_area,3,"3480 regis\n");
+	tape_sprintf_event (TAPE_DBF,3,"3480 registered\n");
 	return disc;
 }
drivers/s390/char/tape3490.c +32 -4
diff -urN linux-2.5.21/drivers/s390/char/tape3490.c linux-2.5.21-s390/drivers/s390/char/tape3490.c
@@ -18,6 +18,15 @@
 #include "tape34xx.h"
 #include "tape3490.h"
 
+#ifdef  TAPE_DEBUG
+#ifdef  MODULE
+#define TAPE_DBF (tape_dbf_3490)
+        debug_info_t *tape_dbf_3490 = NULL;
+#else
+#define TAPE_DBF (tape_dbf_area)
+#endif  /* MODULE */
+#endif  /* TAPE_DEBUG */
+
 #ifdef CONFIG_S390_TAPE_3490_MODULE 
 static tape_discipline_t* disc;
 
@@ -36,14 +45,25 @@
 		tape_unregister_discipline(disc);
 		kfree(disc);
 	}
+#ifdef TAPE_DEBUG
+#ifdef MODULE
+       debug_unregister(tape_dbf_3490);
+#endif /* MODULE */
+#endif /* TAPE_DEBUG */
 }
+
+#ifdef MODULE
+MODULE_AUTHOR("(C) 2001-2002 IBM Deutschland Entwicklung GmbH");
+MODULE_DESCRIPTION("Linux on zSeries channel attached 3490 tape device driver ($Revision: 1.34 $)");
+#endif /* MODULE */
+
 #endif /* CONFIG_S390_TAPE_3490_MODULE */
 
 int
 tape3490_setup_device (tape_dev_t * td)
 {
 	tape3490_disc_data_t *data = NULL;
-	tape_sprintf_event (tape_dbf_area,1,"3490 dsetup: %x\n",td->first_minor);
+	tape_sprintf_event (TAPE_DBF, 6, "3490 minor1: %x\n", td->first_minor);
 	data = kmalloc (sizeof (tape3490_disc_data_t), GFP_KERNEL | GFP_DMA);
 	if(data == NULL)
 		return -1;
@@ -70,10 +90,16 @@
 tape3490_init (void)
 {
 	tape_discipline_t *disc;
-	tape_sprintf_event (tape_dbf_area,3,"3490 init\n");
+#ifdef TAPE_DEBUG
+#ifdef MODULE
+        tape_dbf_3490 = debug_register("tape3490", 1, 2, 3*sizeof(long));
+        debug_register_view(tape_dbf_3490, &debug_sprintf_view);
+#endif /* MODULE */
+#endif /* TAPE_DEBUG */
+	tape_sprintf_event (TAPE_DBF,3,"3490 init: $Revision: 1.34 $\n");
 	disc = kmalloc (sizeof (tape_discipline_t), GFP_ATOMIC);
 	if (disc == NULL) {
-	        tape_sprintf_exception (tape_dbf_area,3,"disc:nomem\n");
+	        tape_sprintf_exception (TAPE_DBF,3,"disc:nomem\n");
 		return disc;
 	}
 	disc->owner = THIS_MODULE;
@@ -91,7 +117,9 @@
 	disc->bread = tape34xx_bread;
 	disc->free_bread = tape34xx_free_bread;
 	disc->bread_enable_locate = tape34xx_bread_enable_locate;
+	disc->assign = tape34xx_assign;
+	disc->unassign = tape34xx_unassign;
 	disc->next = NULL;
-	tape_sprintf_event (tape_dbf_area,3,"3490 regis\n");
+	tape_sprintf_event (TAPE_DBF,3,"3490 registered\n");
 	return disc;
 }
drivers/s390/char/tape34xx.c +132 -56

297 lines not on this page · raw message

drivers/s390/char/tape34xx.h +2 -0
diff -urN linux-2.5.21/drivers/s390/char/tape34xx.h linux-2.5.21-s390/drivers/s390/char/tape34xx.h
@@ -113,6 +113,8 @@
 tape_ccw_req_t * tape34xx_read_block (const char *data, size_t count, tape_dev_t* td);
 tape_ccw_req_t * tape34xx_ioctl(tape_dev_t* td, int op,int count, int* rc);
 tape_ccw_req_t * tape34xx_bread (struct request *req, tape_dev_t* td,int tapeblock_major);
+tape_ccw_req_t * tape34xx_assign(tape_dev_t* td);
+tape_ccw_req_t * tape34xx_unassign(tape_dev_t* td);
 void tape34xx_free_bread (tape_ccw_req_t* treq);
 void tape34xx_bread_enable_locate (tape_ccw_req_t * treq);
 tape_ccw_req_t * tape34xx_bwrite (struct request *req, tape_dev_t* td,int tapeblock_major);
drivers/s390/char/tapeblock.c +91 -59

299 lines not on this page · raw message

drivers/s390/char/tapeblock.h +3 -2
diff -urN linux-2.5.21/drivers/s390/char/tapeblock.h linux-2.5.21-s390/drivers/s390/char/tapeblock.h
@@ -17,14 +17,15 @@
 #define TAPEBLOCK_H
 #include <linux/config.h>
 
-#define TAPEBLOCK_READAHEAD 30
 #define TAPEBLOCK_MAJOR 0
 
 #define TAPEBLOCK_DEVFSMODE 0060644 // blkdev, rwx for user, rw for group&others
 
+#define TAPEBLOCK_HSEC_SIZE 2048
+#define S2B 2 /* bits to shift 512 to get a block (2048) */
+
 int tapeblock_open(struct inode *, struct file *);
 int tapeblock_release(struct inode *, struct file *);
-void tapeblock_setup(tape_dev_t* td);
 void tapeblock_schedule_exec_io (tape_dev_t *td);
 int tapeblock_mediumdetect(tape_dev_t* td);
 #ifdef CONFIG_DEVFS_FS
drivers/s390/char/tapechar.c +120 -51

362 lines not on this page · raw message

drivers/s390/char/tapedefs.h +11 -1
diff -urN linux-2.5.21/drivers/s390/char/tapedefs.h linux-2.5.21-s390/drivers/s390/char/tapedefs.h
@@ -33,6 +33,9 @@
 #define CONFIG_S390_TAPE_DYNAMIC // allow devices to be attached or detached on the fly
 #define TAPEBLOCK_RETRIES 20     // number of retries, when a block-dev request fails.
 
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,4,98))
+	#define rq_data_dir(req) ((req)->cmd)
+#endif
 
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,3,98))
 #define INIT_BLK_DEV(d_major,d_request_fn,d_queue_fn,d_current) \
@@ -40,10 +43,17 @@
         blk_dev[d_major].queue = d_queue_fn; \
 } while(0)
 static inline struct request * 
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,4,99))
+tape_next_request( request_queue_t *queue )
+{
+	return elv_next_request(queue);
+}
+#else
 tape_next_request( request_queue_t *queue ) 
 {
-        return elv_next_request(queue);
+        return blkdev_entry_next_request(&queue->queue_head);
 }
+#endif
 static inline void 
 tape_dequeue_request( request_queue_t * q, struct request *req )
 {