diff options
author | Felix Beck <felix.beck@de.ibm.com> | 2009-12-07 06:52:00 -0500 |
---|---|---|
committer | Martin Schwidefsky <sky@mschwide.boeblingen.de.ibm.com> | 2009-12-07 06:51:36 -0500 |
commit | 93521314cb3132f40a4bf6d76b4bbcdbc9e59dfb (patch) | |
tree | 9a601e06ef26aae3f2d02cd387427886b7a55a84 /drivers/s390 | |
parent | 7a6f5cd07ee5648f5768637ff082133384af415c (diff) |
[S390] zcrypt: Do not simultaneously schedule hrtimer
Protect the hrtimer ap_poll_timer from being scheduled at the same
time from several processes.
Signed-off-by: Felix Beck <felix.beck@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'drivers/s390')
-rw-r--r-- | drivers/s390/crypto/ap_bus.c | 11 |
1 files changed, 8 insertions, 3 deletions
diff --git a/drivers/s390/crypto/ap_bus.c b/drivers/s390/crypto/ap_bus.c index 21077f4b8c50..20836eff88c5 100644 --- a/drivers/s390/crypto/ap_bus.c +++ b/drivers/s390/crypto/ap_bus.c | |||
@@ -102,6 +102,7 @@ static atomic_t ap_poll_requests = ATOMIC_INIT(0); | |||
102 | static DECLARE_WAIT_QUEUE_HEAD(ap_poll_wait); | 102 | static DECLARE_WAIT_QUEUE_HEAD(ap_poll_wait); |
103 | static struct task_struct *ap_poll_kthread = NULL; | 103 | static struct task_struct *ap_poll_kthread = NULL; |
104 | static DEFINE_MUTEX(ap_poll_thread_mutex); | 104 | static DEFINE_MUTEX(ap_poll_thread_mutex); |
105 | static DEFINE_SPINLOCK(ap_poll_timer_lock); | ||
105 | static void *ap_interrupt_indicator; | 106 | static void *ap_interrupt_indicator; |
106 | static struct hrtimer ap_poll_timer; | 107 | static struct hrtimer ap_poll_timer; |
107 | /* In LPAR poll with 4kHz frequency. Poll every 250000 nanoseconds. | 108 | /* In LPAR poll with 4kHz frequency. Poll every 250000 nanoseconds. |
@@ -1170,16 +1171,19 @@ ap_config_timeout(unsigned long ptr) | |||
1170 | static inline void ap_schedule_poll_timer(void) | 1171 | static inline void ap_schedule_poll_timer(void) |
1171 | { | 1172 | { |
1172 | ktime_t hr_time; | 1173 | ktime_t hr_time; |
1174 | |||
1175 | spin_lock_bh(&ap_poll_timer_lock); | ||
1173 | if (ap_using_interrupts() || ap_suspend_flag) | 1176 | if (ap_using_interrupts() || ap_suspend_flag) |
1174 | return; | 1177 | goto out; |
1175 | if (hrtimer_is_queued(&ap_poll_timer)) | 1178 | if (hrtimer_is_queued(&ap_poll_timer)) |
1176 | return; | 1179 | goto out; |
1177 | if (ktime_to_ns(hrtimer_expires_remaining(&ap_poll_timer)) <= 0) { | 1180 | if (ktime_to_ns(hrtimer_expires_remaining(&ap_poll_timer)) <= 0) { |
1178 | hr_time = ktime_set(0, poll_timeout); | 1181 | hr_time = ktime_set(0, poll_timeout); |
1179 | hrtimer_forward_now(&ap_poll_timer, hr_time); | 1182 | hrtimer_forward_now(&ap_poll_timer, hr_time); |
1180 | hrtimer_restart(&ap_poll_timer); | 1183 | hrtimer_restart(&ap_poll_timer); |
1181 | } | 1184 | } |
1182 | return; | 1185 | out: |
1186 | spin_unlock_bh(&ap_poll_timer_lock); | ||
1183 | } | 1187 | } |
1184 | 1188 | ||
1185 | /** | 1189 | /** |
@@ -1668,6 +1672,7 @@ int __init ap_module_init(void) | |||
1668 | */ | 1672 | */ |
1669 | if (MACHINE_IS_VM) | 1673 | if (MACHINE_IS_VM) |
1670 | poll_timeout = 1500000; | 1674 | poll_timeout = 1500000; |
1675 | spin_lock_init(&ap_poll_timer_lock); | ||
1671 | hrtimer_init(&ap_poll_timer, CLOCK_MONOTONIC, HRTIMER_MODE_ABS); | 1676 | hrtimer_init(&ap_poll_timer, CLOCK_MONOTONIC, HRTIMER_MODE_ABS); |
1672 | ap_poll_timer.function = ap_poll_timeout; | 1677 | ap_poll_timer.function = ap_poll_timeout; |
1673 | 1678 | ||