s390 (3/16): common i/o layer update.
Subsystems (2)
PATCH 1/1 s390 (3/16): common i/o layer update.
Common i/o layer fixes:
- Fix for path no operational condition in cio_start.
- Fix handling of user interruption parameter.
- Add code to wait for devices in init_ccw_bus_type.
- Move qdio states out of main cio state machine.
- Reworked chsc data structures.
- Add ccw_device_start_timeout.
- Handle path verification required flag.
diffstat:
cio/airq.c | 6 cio/airq.h | 4 cio/chsc.c | 338 ++++++++++++++++----------- cio/chsc.h | 83 ------ cio/cio.c | 29 -- cio/cio.h | 9 cio/css.c | 8 cio/css.h | 1 cio/device.c | 70 +++++ cio/device.h | 10 cio/device_fsm.c | 200 +++++++--------- cio/device_id.c | 10 cio/device_ops.c | 98 +++++--- cio/device_pgid.c | 27 +- cio/device_status.c | 4 cio/qdio.c | 635 ++++++++++++++++++++++++++++------------------------ cio/qdio.h | 110 +-------- cio/requestirq.c | 6 s390mach.c | 14 - 19 files changed, 859 insertions(+), 803 deletions(-)
drivers/s390/cio/airq.c +3 -3
@@ -2,7 +2,7 @@* drivers/s390/cio/airq.c * S/390 common I/O routines -- support for adapter interruptions * -* $Revision: 1.10 $ +* $Revision: 1.11 $ * * Copyright (C) 1999-2002 IBM Deutschland Entwicklung GmbH, * IBM Corporation
@@ -87,14 +87,14 @@ }void -do_adapter_IO (__u32 intparm) +do_adapter_IO (void ) {CIO_TRACE_EVENT (4 ,"doaio" );spin_lock (&adapter_lock);if (adapter_handler) - (*adapter_handler) (intparm); + (*adapter_handler) ();spin_unlock (&adapter_lock);
drivers/s390/cio/airq.h +2 -2
@@ -1,10 +1,10 @@#ifndef S390_AINTERRUPT_H #define S390_AINTERRUPT_H -typedef int (*adapter_int_handler_t )(__u32 intparm); +typedef int (*adapter_int_handler_t )(void );extern int s390_register_adapter_interrupt (adapter_int_handler_t handler);extern int s390_unregister_adapter_interrupt (adapter_int_handler_t handler); -extern void do_adapter_IO (__u32 intparm); +extern void do_adapter_IO (void );#endif
drivers/s390/cio/chsc.c +199 -139
535 lines not on this page · raw message
drivers/s390/cio/chsc.h +4 -79
89 lines not on this page · raw message
drivers/s390/cio/cio.c +11 -18
@@ -1,7 +1,7 @@/* * drivers/s390/cio/cio.c * S/390 common I/O routines -- low level i/o calls -* $Revision: 1.91 $ +* $Revision: 1.97 $ * * Copyright (C) 1999-2002 IBM Deutschland Entwicklung GmbH, * IBM Corporation
@@ -176,13 +176,13 @@CIO_TRACE_EVENT (0 , dbf_text);CIO_HEX_EVENT (0 , &sch->schib,sizeof (struct schib )); -return -ENODEV ; +return (sch->lpm ? -EACCES : -ENODEV ); }int cio_start (struct subchannel *sch,/* subchannel structure */ struct ccw1 * cpa,/* logical channel prog addr */ -unsigned long intparm,/* interruption parameter */ +unsigned int intparm,/* interruption parameter */ __u8 lpm)/* logical path mask */ {char dbf_txt[15 ];
@@ -191,7 +191,7 @@sprintf (dbf_txt,"stIO%x" , sch->irq);CIO_TRACE_EVENT (4 , dbf_txt); - sch->orb.intparm = (__u32) (long) &sch->u_intparm; + sch->orb.intparm = intparm; sch->orb.fmt =1 ; sch->orb.pfch = sch->options.prefetch ==0 ;
@@ -219,7 +219,6 @@/* * initialize device status information */ - sch->u_intparm = intparm; sch->schib.scsw.actl |=SCSW_ACTL_START_PEND ;return 0 ;case 1 :/* status pending */
@@ -265,13 +264,10 @@ }/* -* Note: The "intparm" parameter is not used by the halt_IO() function -* itself, as no ORB is built for the HSCH instruction. However, -* it allows the device interrupt handler to associate the upcoming -* interrupt with the halt_IO() request. +* halt I/O operation */ int -cio_halt (struct subchannel *sch,unsigned long intparm) +cio_halt (struct subchannel *sch) {char dbf_txt[15 ];int ccode;
@@ -297,7 +293,6 @@switch (ccode) {case 0 : - sch->u_intparm = intparm; sch->schib.scsw.actl |=SCSW_ACTL_HALT_PEND ;return 0 ;case 1 :/* status pending */
@@ -309,13 +304,10 @@ }/* -* Note: The "intparm" parameter is not used by the clear_IO() function -* itself, as no ORB is built for the CSCH instruction. However, -* it allows the device interrupt handler to associate the upcoming -* interrupt with the clear_IO() request. +* Clear I/O operation */ int -cio_clear (struct subchannel *sch,unsigned long intparm) +cio_clear (struct subchannel *sch) {char dbf_txt[15 ];int ccode;
@@ -340,7 +332,6 @@switch (ccode) {case 0 : - sch->u_intparm = intparm; sch->schib.scsw.actl |=SCSW_ACTL_CLEAR_PEND ;return 0 ;default :/* device not operational */
@@ -374,6 +365,8 @@switch (ccode) {case 0 :/* success */ +/* Update information in scsw. */ +stsch (sch->irq, &sch->schib);return 0 ;case 1 :/* status pending */ return -EBUSY ;
@@ -620,7 +613,7 @@*/ if (tpi_info->adapter_IO ==1 && tpi_info->int_type ==IO_INTERRUPT_TYPE ) { -do_adapter_IO (tpi_info->intparm); +do_adapter_IO ();continue ; } sch = ioinfo[tpi_info->irq];
drivers/s390/cio/cio.h +3 -6
@@ -98,8 +98,6 @@__u8 vpm;/* verified path mask */ __u8 lpm;/* logical path mask */ -// TODO: intparm for second start i/o -unsigned long u_intparm;/* user interruption parameter */ struct schib schib;/* subchannel information block */ struct orb orb;/* operation request block */ struct ccw1 sense_ccw;/* static ccw for sense command */
@@ -116,11 +114,10 @@extern int cio_enable_subchannel (struct subchannel *,unsigned int );extern int cio_disable_subchannel (struct subchannel *);extern int cio_cancel (struct subchannel *); -extern int cio_clear (struct subchannel *,unsigned long ); -extern int cio_do_io (struct subchannel *,struct ccw1 *,unsigned long ,__u8 ); +extern int cio_clear (struct subchannel *);extern int cio_resume (struct subchannel *); -extern int cio_halt (struct subchannel *,unsigned long ); -extern int cio_start (struct subchannel *,struct ccw1 *,unsigned long ,__u8 ); +extern int cio_halt (struct subchannel *); +extern int cio_start (struct subchannel *,struct ccw1 *,unsigned int ,__u8 );extern int cio_cancel (struct subchannel *);extern int cio_set_options (struct subchannel *,int );extern int cio_get_options (struct subchannel *);
drivers/s390/cio/css.c +4 -4
@@ -1,7 +1,7 @@/* * drivers/s390/cio/css.c * driver for channel subsystem -* $Revision: 1.40 $ +* $Revision: 1.43 $ * * Copyright (C) 2002 IBM Deutschland Entwicklung GmbH, * IBM Corporation
@@ -41,7 +41,7 @@/* There already is a struct subchannel for this irq. */ return -EBUSY ; - sch =kmalloc (sizeof (*sch),GFP_DMA ); + sch =kmalloc (sizeof (*sch),GFP_KERNEL |GFP_DMA );if (sch ==NULL )return -ENOMEM ; ret =cio_validate_subchannel (sch, irq);
@@ -161,7 +161,7 @@ sch = ioinfo[irq];if (sch ==NULL ) { -schedule_work (&work); +queue_work (ccw_device_work, &work);return ; }if (!sch->dev.driver_data)
@@ -172,7 +172,7 @@ ccode =stsch (irq, &sch->schib);if (!ccode)if (devno != sch->schib.pmcw.dev) -schedule_work (&work); +queue_work (ccw_device_work, &work); }/*
drivers/s390/cio/css.h +1 -0
@@ -79,6 +79,7 @@ unsigned int esid:1; /* Ext. SenseID supported by HW */ unsigned int dosense:1; /* delayed SENSE required */ } __attribute__((packed)) flags; +unsigned long intparm;/* user interruption parameter */ struct qdio_irq *qdio_data;struct irb irb;/* device status */ struct senseid senseid;/* SenseID info */
drivers/s390/cio/device.c +66 -4
131 lines not on this page · raw message
drivers/s390/cio/device.h +5 -5
@@ -14,13 +14,11 @@DEV_STATE_W4SENSE ,DEV_STATE_DISBAND_PGID ,DEV_STATE_BOXED , -/* special states for qdio */ -DEV_STATE_QDIO_INIT , -DEV_STATE_QDIO_ACTIVE , -DEV_STATE_QDIO_CLEANUP ,/* states to wait for i/o completion before doing something */ DEV_STATE_ONLINE_VERIFY ,DEV_STATE_W4SENSE_VERIFY , +DEV_STATE_CLEAR_VERIFY , +DEV_STATE_TIMEOUT_KILL ,/* last element! */ NR_DEV_STATES };
@@ -63,7 +61,9 @@ cdev->private->state == DEV_STATE_BOXED); } -void io_subchannel_register (void *data); +extern struct workqueue_struct *ccw_device_work; + +void io_subchannel_recog_done (struct ccw_device *cdev);int ccw_device_recognition (struct ccw_device *);int ccw_device_online (struct ccw_device *);
drivers/s390/cio/device_fsm.c +88 -112
324 lines not on this page · raw message
drivers/s390/cio/device_id.c +6 -4
@@ -198,11 +198,13 @@/* 0x00E2C9C4 == ebcdic "SID" */ ret =cio_start (sch, cdev->private->iccws,0x00E2C9C4 , cdev->private->imask); -/* ret is 0, -EBUSY or -ENODEV */ -if (ret != -EBUSY ) +/* ret is 0, -EBUSY, -EACCES or -ENODEV */ +if (ret == -EBUSY ) { +udelay (100 ); +continue ; + } +if (ret != -EACCES )return ret; -udelay (100 ); -continue ; } cdev->private->imask >>=1 ; cdev->private->iretry =5 ;
drivers/s390/cio/device_ops.c +66 -32
198 lines not on this page · raw message
drivers/s390/cio/device_pgid.c +19 -8
@@ -51,14 +51,23 @@/* 0xe2d5c9c4 == ebcdic "SNID" */ ret =cio_start (sch, cdev->private->iccws,0xE2D5C9C4 , cdev->private->imask); -/* ret is 0, -EBUSY or -ENODEV */ -if (ret != -EBUSY ) +/* ret is 0, -EBUSY, -EACCES or -ENODEV */ +if (ret == -EBUSY ) { +CIO_MSG_EVENT (2 , +"SNID - device %04X, start_io() " +"reports rc : %d, retrying ...\n" , + sch->schib.pmcw.dev, ret); +udelay (100 ); +continue ; + } +if (ret != -EACCES )return ret; -CIO_MSG_EVENT (2 ,"SNID - device %04X, start_io() " -"reports rc : %d, retrying ...\n" , - sch->schib.pmcw.dev, ret); -udelay (100 ); -continue ; +CIO_MSG_EVENT (2 ,"SNID - Device %04X on Subchannel " +"%04X, lpm %02X, became 'not " +"operational'\n" , + sch->schib.pmcw.dev, sch->irq, + cdev->private->imask); + } cdev->private->imask >>=1 ; cdev->private->iretry =5 ;
@@ -231,7 +240,9 @@/* 0xE2D7C9C4 == ebcdic "SPID" */ ret =cio_start (sch, cdev->private->iccws,0xE2D7C9C4 , cdev->private->imask); -/* ret is 0, -EBUSY or -ENODEV */ +/* ret is 0, -EBUSY, -EACCES or -ENODEV */ +if (ret == -EACCES ) +break ;if (ret != -EBUSY )return ret;udelay (100 );
drivers/s390/cio/device_status.c +2 -2
@@ -167,7 +167,7 @@/* Copy authorization bit. */ cdev_irb->esw.esw0.erw.auth = irb->esw.esw0.erw.auth; -/* Copy path verification required flag. FIXME: how to verify ?? */ +/* Copy path verification required flag. */ cdev_irb->esw.esw0.erw.pvrf = irb->esw.esw0.erw.pvrf;/* Copy concurrent sense bit. */ cdev_irb->esw.esw0.erw.cons = irb->esw.esw0.erw.cons;
@@ -309,7 +309,7 @@ sch->sense_ccw.flags =CCW_FLAG_SLI ;/* 0xe2C5D5E2 == "SENS" in ebcdic */ -return cio_start (sch, &sch->sense_ccw,0xE2C5D5E2 ,0 ); +return cio_start (sch, &sch->sense_ccw,0xE2C5D5E2 ,0xff ); }/*
drivers/s390/cio/qdio.c +348 -287
1,112 lines not on this page · raw message
drivers/s390/cio/qdio.h +15 -95
155 lines not on this page · raw message
drivers/s390/cio/requestirq.c +5 -1
@@ -44,7 +44,11 @@/* * Let's build our path group ID here. */ - global_pgid.cpu_addr = *(__u16 *) __LC_CPUADDR; +#ifdef CONFIG_SMP + global_pgid.cpu_addr =hard_smp_processor_id (); +#else + global_pgid.cpu_addr =0 ; +#endif global_pgid.cpu_id = ((cpuid_t *) __LC_CPUID)->ident; global_pgid.cpu_model = ((cpuid_t *) __LC_CPUID)->machine; global_pgid.tod_high = (__u32) (get_clock () >>32 );
drivers/s390/s390mach.c +12 -2
@@ -21,7 +21,7 @@extern void css_process_crw (int );extern void chsc_process_crw (void ); -extern void chp_process_crw (int ); +extern void chp_process_crw (int ,int );static void s390_handle_damage (char *msg)
@@ -62,7 +62,17 @@break ;case CRW_RSC_CPATH :pr_debug ("source is channel path %02X\n" , crw.rsid); -chp_process_crw (crw.rsid); +switch (crw.erc) { +case CRW_ERC_IPARM :/* Path has come. */ +chp_process_crw (crw.rsid,1 ); +break ; +case CRW_ERC_PERRI :/* Path has gone. */ +chp_process_crw (crw.rsid,0 ); +break ; +default : +pr_debug ("Don't know how to handle erc=%x\n" , + crw.erc); + }break ;case CRW_RSC_CONFIG :pr_debug ("source is configuration-alert facility\n" );