aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/s390/cio
diff options
context:
space:
mode:
authorSebastian Ott <sebott@linux.vnet.ibm.com>2013-04-13 07:06:27 -0400
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2013-04-17 08:07:33 -0400
commit0ad8f714a135cf993606c21fc1ed0e303ef17c0d (patch)
tree78ce400a47edecdce1921f2bb6cc536009778bb5 /drivers/s390/cio
parent4e5ebd51214a1851841f952e9e5b5072ce5f9da4 (diff)
s390/cio: fix early init counter usage
Via ccw_device_init_count we keep track of how many devices are in asynchronous device recognition/initialization. For early devices this variable was not only used prior to its initialization but used incorrectly (incremented but never decremented). Fix this by using static initialization for this variable (and friends), make them visible to device.c only, and decrement the counter after recognition of early devices is finished. Reviewed-by: Peter Oberparleiter <oberpar@linux.vnet.ibm.com> Signed-off-by: Sebastian Ott <sebott@linux.vnet.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'drivers/s390/cio')
-rw-r--r--drivers/s390/cio/device.c13
-rw-r--r--drivers/s390/cio/device.h2
2 files changed, 6 insertions, 9 deletions
diff --git a/drivers/s390/cio/device.c b/drivers/s390/cio/device.c
index 41a16785be29..1ab5f6c36d9b 100644
--- a/drivers/s390/cio/device.c
+++ b/drivers/s390/cio/device.c
@@ -44,6 +44,10 @@ static DEFINE_SPINLOCK(recovery_lock);
44static int recovery_phase; 44static int recovery_phase;
45static const unsigned long recovery_delay[] = { 3, 30, 300 }; 45static const unsigned long recovery_delay[] = { 3, 30, 300 };
46 46
47static atomic_t ccw_device_init_count = ATOMIC_INIT(0);
48static DECLARE_WAIT_QUEUE_HEAD(ccw_device_init_wq);
49static struct bus_type ccw_bus_type;
50
47/******************* bus type handling ***********************/ 51/******************* bus type handling ***********************/
48 52
49/* The Linux driver model distinguishes between a bus type and 53/* The Linux driver model distinguishes between a bus type and
@@ -128,8 +132,6 @@ static int ccw_uevent(struct device *dev, struct kobj_uevent_env *env)
128 return ret; 132 return ret;
129} 133}
130 134
131static struct bus_type ccw_bus_type;
132
133static void io_subchannel_irq(struct subchannel *); 135static void io_subchannel_irq(struct subchannel *);
134static int io_subchannel_probe(struct subchannel *); 136static int io_subchannel_probe(struct subchannel *);
135static int io_subchannel_remove(struct subchannel *); 137static int io_subchannel_remove(struct subchannel *);
@@ -138,8 +140,6 @@ static int io_subchannel_sch_event(struct subchannel *, int);
138static int io_subchannel_chp_event(struct subchannel *, struct chp_link *, 140static int io_subchannel_chp_event(struct subchannel *, struct chp_link *,
139 int); 141 int);
140static void recovery_func(unsigned long data); 142static void recovery_func(unsigned long data);
141wait_queue_head_t ccw_device_init_wq;
142atomic_t ccw_device_init_count;
143 143
144static struct css_device_id io_subchannel_ids[] = { 144static struct css_device_id io_subchannel_ids[] = {
145 { .match_flags = 0x1, .type = SUBCHANNEL_TYPE_IO, }, 145 { .match_flags = 0x1, .type = SUBCHANNEL_TYPE_IO, },
@@ -192,10 +192,7 @@ int __init io_subchannel_init(void)
192{ 192{
193 int ret; 193 int ret;
194 194
195 init_waitqueue_head(&ccw_device_init_wq);
196 atomic_set(&ccw_device_init_count, 0);
197 setup_timer(&recovery_timer, recovery_func, 0); 195 setup_timer(&recovery_timer, recovery_func, 0);
198
199 ret = bus_register(&ccw_bus_type); 196 ret = bus_register(&ccw_bus_type);
200 if (ret) 197 if (ret)
201 return ret; 198 return ret;
@@ -1093,6 +1090,8 @@ static int io_subchannel_probe(struct subchannel *sch)
1093 put_device(&cdev->dev); 1090 put_device(&cdev->dev);
1094 goto out_schedule; 1091 goto out_schedule;
1095 } 1092 }
1093 if (atomic_dec_and_test(&ccw_device_init_count))
1094 wake_up(&ccw_device_init_wq);
1096 return 0; 1095 return 0;
1097 } 1096 }
1098 io_subchannel_init_fields(sch); 1097 io_subchannel_init_fields(sch);
diff --git a/drivers/s390/cio/device.h b/drivers/s390/cio/device.h
index 7d4ecb65db00..8d1d29873172 100644
--- a/drivers/s390/cio/device.h
+++ b/drivers/s390/cio/device.h
@@ -81,8 +81,6 @@ dev_fsm_final_state(struct ccw_device *cdev)
81 cdev->private->state == DEV_STATE_BOXED); 81 cdev->private->state == DEV_STATE_BOXED);
82} 82}
83 83
84extern wait_queue_head_t ccw_device_init_wq;
85extern atomic_t ccw_device_init_count;
86int __init io_subchannel_init(void); 84int __init io_subchannel_init(void);
87 85
88void io_subchannel_recog_done(struct ccw_device *cdev); 86void io_subchannel_recog_done(struct ccw_device *cdev);