aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/ide/ide-lib.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@woody.linux-foundation.org>2007-07-19 19:31:22 -0400
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-07-19 19:31:22 -0400
commit64fb98fc40738ae1a98bcea9ca3145b89fb71524 (patch)
tree24130f9c56b04638e91969d216db199652470a17 /drivers/ide/ide-lib.c
parent5f47c7eac65a45e33d7fe390effe75ec5c74f8bf (diff)
parent89636af25d75d8672aea05d258be357d0dc4bd70 (diff)
Merge master.kernel.org:/pub/scm/linux/kernel/git/bart/ide-2.6
* master.kernel.org:/pub/scm/linux/kernel/git/bart/ide-2.6: (23 commits) ide: add support for SCSI ioctls to ide-floppy ide: remove stale changelog from setup-pci.c ide: remove stale changelog/comments/TODO from ide.c ide-cris: handle PIO auto-tuning in tune_cris_ide() ide: add PIO masks ide: remove ide_find_best_pio_mode() ide: drop "PIO data" argument from ide_get_best_pio_mode() ide: ide_find_best_pio_mode() fixes (take 2) ide: add ide_pio_cycle_time() helper (take 2) sc1200: remove stale Power Management code ide: ide_start_power_step() fix WRT disabling DMA serverworks: fix DMA serverworks: always tune PIO ide: add ide_pci_device_t.host_flags (take 2) ide: add ide_dev_has_iordy() helper (take 4) ide: make ide_get_best_pio_mode() print info if overriding PIO mode siimage: PIO mode setup fixes (take 2) atiixp: PIO mode setup fixes ide: Stop mapping ROMs IDE: Remove references to dead ETRAX-related variables. ...
Diffstat (limited to 'drivers/ide/ide-lib.c')
-rw-r--r--drivers/ide/ide-lib.c72
1 files changed, 42 insertions, 30 deletions
diff --git a/drivers/ide/ide-lib.c b/drivers/ide/ide-lib.c
index 074bb32a4a40..92a6c7bcf527 100644
--- a/drivers/ide/ide-lib.c
+++ b/drivers/ide/ide-lib.c
@@ -249,12 +249,34 @@ static int ide_scan_pio_blacklist (char *model)
249 return -1; 249 return -1;
250} 250}
251 251
252unsigned int ide_pio_cycle_time(ide_drive_t *drive, u8 pio)
253{
254 struct hd_driveid *id = drive->id;
255 int cycle_time = 0;
256
257 if (id->field_valid & 2) {
258 if (id->capability & 8)
259 cycle_time = id->eide_pio_iordy;
260 else
261 cycle_time = id->eide_pio;
262 }
263
264 /* conservative "downgrade" for all pre-ATA2 drives */
265 if (pio < 3) {
266 if (cycle_time && cycle_time < ide_pio_timings[pio].cycle_time)
267 cycle_time = 0; /* use standard timing */
268 }
269
270 return cycle_time ? cycle_time : ide_pio_timings[pio].cycle_time;
271}
272
273EXPORT_SYMBOL_GPL(ide_pio_cycle_time);
274
252/** 275/**
253 * ide_get_best_pio_mode - get PIO mode from drive 276 * ide_get_best_pio_mode - get PIO mode from drive
254 * @drive: drive to consider 277 * @drive: drive to consider
255 * @mode_wanted: preferred mode 278 * @mode_wanted: preferred mode
256 * @max_mode: highest allowed mode 279 * @max_mode: highest allowed mode
257 * @d: PIO data
258 * 280 *
259 * This routine returns the recommended PIO settings for a given drive, 281 * This routine returns the recommended PIO settings for a given drive,
260 * based on the drive->id information and the ide_pio_blacklist[]. 282 * based on the drive->id information and the ide_pio_blacklist[].
@@ -263,22 +285,18 @@ static int ide_scan_pio_blacklist (char *model)
263 * This is used by most chipset support modules when "auto-tuning". 285 * This is used by most chipset support modules when "auto-tuning".
264 */ 286 */
265 287
266u8 ide_get_best_pio_mode (ide_drive_t *drive, u8 mode_wanted, u8 max_mode, ide_pio_data_t *d) 288u8 ide_get_best_pio_mode (ide_drive_t *drive, u8 mode_wanted, u8 max_mode)
267{ 289{
268 int pio_mode; 290 int pio_mode;
269 int cycle_time = 0;
270 int use_iordy = 0;
271 struct hd_driveid* id = drive->id; 291 struct hd_driveid* id = drive->id;
272 int overridden = 0; 292 int overridden = 0;
273 293
274 if (mode_wanted != 255) { 294 if (mode_wanted != 255)
275 pio_mode = mode_wanted; 295 return min_t(u8, mode_wanted, max_mode);
276 use_iordy = (pio_mode > 2); 296
277 } else if (!drive->id) { 297 if ((drive->hwif->host_flags & IDE_HFLAG_PIO_NO_BLACKLIST) == 0 &&
278 pio_mode = 0; 298 (pio_mode = ide_scan_pio_blacklist(id->model)) != -1) {
279 } else if ((pio_mode = ide_scan_pio_blacklist(id->model)) != -1) { 299 printk(KERN_INFO "%s: is on PIO blacklist\n", drive->name);
280 overridden = 1;
281 use_iordy = (pio_mode > 2);
282 } else { 300 } else {
283 pio_mode = id->tPIO; 301 pio_mode = id->tPIO;
284 if (pio_mode > 2) { /* 2 is maximum allowed tPIO value */ 302 if (pio_mode > 2) { /* 2 is maximum allowed tPIO value */
@@ -286,9 +304,7 @@ u8 ide_get_best_pio_mode (ide_drive_t *drive, u8 mode_wanted, u8 max_mode, ide_p
286 overridden = 1; 304 overridden = 1;
287 } 305 }
288 if (id->field_valid & 2) { /* drive implements ATA2? */ 306 if (id->field_valid & 2) { /* drive implements ATA2? */
289 if (id->capability & 8) { /* drive supports use_iordy? */ 307 if (id->capability & 8) { /* IORDY supported? */
290 use_iordy = 1;
291 cycle_time = id->eide_pio_iordy;
292 if (id->eide_pio_modes & 7) { 308 if (id->eide_pio_modes & 7) {
293 overridden = 0; 309 overridden = 0;
294 if (id->eide_pio_modes & 4) 310 if (id->eide_pio_modes & 4)
@@ -298,31 +314,27 @@ u8 ide_get_best_pio_mode (ide_drive_t *drive, u8 mode_wanted, u8 max_mode, ide_p
298 else 314 else
299 pio_mode = 3; 315 pio_mode = 3;
300 } 316 }
301 } else {
302 cycle_time = id->eide_pio;
303 } 317 }
304 } 318 }
305 319
320 if (overridden)
321 printk(KERN_INFO "%s: tPIO > 2, assuming tPIO = 2\n",
322 drive->name);
323
306 /* 324 /*
307 * Conservative "downgrade" for all pre-ATA2 drives 325 * Conservative "downgrade" for all pre-ATA2 drives
308 */ 326 */
309 if (pio_mode && pio_mode < 4) { 327 if ((drive->hwif->host_flags & IDE_HFLAG_PIO_NO_DOWNGRADE) == 0 &&
328 pio_mode && pio_mode < 4) {
310 pio_mode--; 329 pio_mode--;
311 overridden = 1; 330 printk(KERN_INFO "%s: applying conservative "
312 if (cycle_time && cycle_time < ide_pio_timings[pio_mode].cycle_time) 331 "PIO \"downgrade\"\n", drive->name);
313 cycle_time = 0; /* use standard timing */
314 } 332 }
315 } 333 }
316 if (pio_mode > max_mode) { 334
335 if (pio_mode > max_mode)
317 pio_mode = max_mode; 336 pio_mode = max_mode;
318 cycle_time = 0; 337
319 }
320 if (d) {
321 d->pio_mode = pio_mode;
322 d->cycle_time = cycle_time ? cycle_time : ide_pio_timings[pio_mode].cycle_time;
323 d->use_iordy = use_iordy;
324 d->overridden = overridden;
325 }
326 return pio_mode; 338 return pio_mode;
327} 339}
328 340