diff options
Diffstat (limited to 'drivers/ide/pci/piix.c')
-rw-r--r-- | drivers/ide/pci/piix.c | 12 |
1 files changed, 10 insertions, 2 deletions
diff --git a/drivers/ide/pci/piix.c b/drivers/ide/pci/piix.c index e9b83e1a3028..7fac6f57b5d6 100644 --- a/drivers/ide/pci/piix.c +++ b/drivers/ide/pci/piix.c | |||
@@ -222,6 +222,8 @@ static void piix_tune_drive (ide_drive_t *drive, u8 pio) | |||
222 | unsigned long flags; | 222 | unsigned long flags; |
223 | u16 master_data; | 223 | u16 master_data; |
224 | u8 slave_data; | 224 | u8 slave_data; |
225 | static DEFINE_SPINLOCK(tune_lock); | ||
226 | |||
225 | /* ISP RTC */ | 227 | /* ISP RTC */ |
226 | u8 timings[][2] = { { 0, 0 }, | 228 | u8 timings[][2] = { { 0, 0 }, |
227 | { 0, 0 }, | 229 | { 0, 0 }, |
@@ -230,7 +232,13 @@ static void piix_tune_drive (ide_drive_t *drive, u8 pio) | |||
230 | { 2, 3 }, }; | 232 | { 2, 3 }, }; |
231 | 233 | ||
232 | pio = ide_get_best_pio_mode(drive, pio, 5, NULL); | 234 | pio = ide_get_best_pio_mode(drive, pio, 5, NULL); |
233 | spin_lock_irqsave(&ide_lock, flags); | 235 | |
236 | /* | ||
237 | * Master vs slave is synchronized above us but the slave register is | ||
238 | * shared by the two hwifs so the corner case of two slave timeouts in | ||
239 | * parallel must be locked. | ||
240 | */ | ||
241 | spin_lock_irqsave(&tune_lock, flags); | ||
234 | pci_read_config_word(dev, master_port, &master_data); | 242 | pci_read_config_word(dev, master_port, &master_data); |
235 | if (is_slave) { | 243 | if (is_slave) { |
236 | master_data = master_data | 0x4000; | 244 | master_data = master_data | 0x4000; |
@@ -250,7 +258,7 @@ static void piix_tune_drive (ide_drive_t *drive, u8 pio) | |||
250 | pci_write_config_word(dev, master_port, master_data); | 258 | pci_write_config_word(dev, master_port, master_data); |
251 | if (is_slave) | 259 | if (is_slave) |
252 | pci_write_config_byte(dev, slave_port, slave_data); | 260 | pci_write_config_byte(dev, slave_port, slave_data); |
253 | spin_unlock_irqrestore(&ide_lock, flags); | 261 | spin_unlock_irqrestore(&tune_lock, flags); |
254 | } | 262 | } |
255 | 263 | ||
256 | /** | 264 | /** |