#undef REALLY_SLOW_IO /* most systems can safely undef this */
-#include <linux/config.h>
#include <linux/module.h>
#include <linux/types.h>
#include <linux/string.h>
#include <linux/slab.h>
#include <linux/delay.h>
#include <linux/ide.h>
-#include <linux/devfs_fs_kernel.h>
#include <linux/spinlock.h>
#include <linux/kmod.h>
#include <linux/pci.h>
}
}
-/**
- * drive_is_flashcard - check for compact flash
- * @drive: drive to check
- *
- * CompactFlash cards and their brethern pretend to be removable
- * hard disks, except:
- * (1) they never have a slave unit, and
- * (2) they don't have doorlock mechanisms.
- * This test catches them, and is invoked elsewhere when setting
- * appropriate config bits.
- *
- * FIXME: This treatment is probably applicable for *all* PCMCIA (PC CARD)
- * devices, so in linux 2.3.x we should change this to just treat all
- * PCMCIA drives this way, and get rid of the model-name tests below
- * (too big of an interface change for 2.4.x).
- * At that time, we might also consider parameterizing the timeouts and
- * retries, since these are MUCH faster than mechanical drives. -M.Lord
- */
-
-static inline int drive_is_flashcard (ide_drive_t *drive)
-{
- struct hd_driveid *id = drive->id;
-
- if (drive->removable) {
- if (id->config == 0x848a) return 1; /* CompactFlash */
- if (!strncmp(id->model, "KODAK ATA_FLASH", 15) /* Kodak */
- || !strncmp(id->model, "Hitachi CV", 10) /* Hitachi */
- || !strncmp(id->model, "SunDisk SDCFB", 13) /* old SanDisk */
- || !strncmp(id->model, "SanDisk SDCFB", 13) /* SanDisk */
- || !strncmp(id->model, "HAGIWARA HPC", 12) /* Hagiwara */
- || !strncmp(id->model, "LEXAR ATA_FLASH", 15) /* Lexar */
- || !strncmp(id->model, "ATA_FLASH", 9)) /* Simple Tech */
- {
- return 1; /* yes, it is a flash memory card */
- }
- }
- return 0; /* no, it is not a flash memory card */
-}
-
/**
* do_identify - identify a drive
* @drive: drive to identify
/*
* Not an ATAPI device: looks like a "regular" hard disk
*/
- if (id->config & (1<<7))
+
+ /*
+ * 0x848a = CompactFlash device
+ * These are *not* removable in Linux definition of the term
+ */
+
+ if ((id->config != 0x848a) && (id->config & (1<<7)))
drive->removable = 1;
- if (drive_is_flashcard(drive))
- drive->is_flash = 1;
drive->media = ide_disk;
- printk("%s DISK drive\n", (drive->is_flash) ? "CFA" : "ATA" );
+ printk("%s DISK drive\n", (id->config == 0x848a) ? "CFA" : "ATA" );
QUIRK_LIST(drive);
return;
* Also note that 0 everywhere means "can't do X"
*/
- drive->id = kmalloc(SECTOR_WORDS *4, GFP_KERNEL);
+ drive->id = kzalloc(SECTOR_WORDS *4, GFP_KERNEL);
drive->id_read = 0;
if(drive->id == NULL)
{
printk(KERN_ERR "ide: out of memory for id data.\n");
return 0;
}
- memset(drive->id, 0, SECTOR_WORDS * 4);
strcpy(drive->id->model, "UNKNOWN");
/* skip probing? */
{
ide_hwif_t *hwif = container_of(dev, ide_hwif_t, gendev);
- up(&hwif->gendev_rel_sem);
+ complete(&hwif->gendev_rel_comp);
}
static void hwif_register (ide_hwif_t *hwif)
{
+ int ret;
+
/* register with global device tree */
strlcpy(hwif->gendev.bus_id,hwif->name,BUS_ID_SIZE);
hwif->gendev.driver_data = hwif;
hwif->gendev.parent = NULL;
}
hwif->gendev.release = hwif_release_dev;
- device_register(&hwif->gendev);
+ ret = device_register(&hwif->gendev);
+ if (ret < 0)
+ printk(KERN_WARNING "IDE: %s: device_register error: %d\n",
+ __FUNCTION__, ret);
}
static int wait_hwif_ready(ide_hwif_t *hwif)
}
}
}
+
+ for (unit = 0; unit < MAX_DRIVES; ++unit) {
+ ide_drive_t *drive = &hwif->drives[unit];
+
+ if (hwif->no_io_32bit)
+ drive->no_io_32bit = 1;
+ else
+ drive->no_io_32bit = drive->id->dword_io ? 1 : 0;
+ }
}
static int hwif_init(ide_hwif_t *hwif);
if (hwif->present) {
u16 unit = 0;
+ int ret;
+
for (unit = 0; unit < MAX_DRIVES; ++unit) {
ide_drive_t *drive = &hwif->drives[unit];
/* For now don't attach absent drives, we may
want them on default or a new "empty" class
for hotplug reprobing ? */
if (drive->present) {
- device_register(&drive->gendev);
+ ret = device_register(&drive->gendev);
+ if (ret < 0)
+ printk(KERN_WARNING "IDE: %s: "
+ "device_register error: %d\n",
+ __FUNCTION__, ret);
}
}
}
* limits and LBA48 we could raise it but as yet
* do not.
*/
-
- q = blk_init_queue(do_ide_request, &ide_lock);
+
+ q = blk_init_queue_node(do_ide_request, &ide_lock, hwif_to_node(hwif));
if (!q)
return 1;
/* needs drive->queue to be set */
ide_toggle_bounce(drive, 1);
- /* enable led activity for disk drives only */
- if (drive->media == ide_disk && hwif->led_act)
- blk_queue_activity_fn(q, hwif->led_act, drive);
-
return 0;
}
* and irq serialization situations. This is somewhat complex because
* it handles static as well as dynamic (PCMCIA) IDE interfaces.
*
- * The SA_INTERRUPT in sa_flags means ide_intr() is always entered with
+ * The IRQF_DISABLED in sa_flags means ide_intr() is always entered with
* interrupts completely disabled. This can be bad for interrupt latency,
* but anything else has led to problems on some machines. We re-enable
* interrupts as much as we can safely do in most places.
BUG_ON(in_interrupt());
BUG_ON(irqs_disabled());
+ BUG_ON(hwif == NULL);
+
down(&ide_cfg_sem);
hwif->hwgroup = NULL;
#if MAX_HWIFS > 1
hwgroup->hwif->next = hwif;
spin_unlock_irq(&ide_lock);
} else {
- hwgroup = kmalloc(sizeof(ide_hwgroup_t),GFP_KERNEL);
+ hwgroup = kmalloc_node(sizeof(ide_hwgroup_t), GFP_KERNEL,
+ hwif_to_node(hwif->drives[0].hwif));
if (!hwgroup)
goto out_up;
* Allocate the irq, if not already obtained for another hwif
*/
if (!match || match->irq != hwif->irq) {
- int sa = SA_INTERRUPT;
+ int sa = IRQF_DISABLED;
#if defined(__mc68000__) || defined(CONFIG_APUS)
- sa = SA_SHIRQ;
+ sa = IRQF_SHARED;
#endif /* __mc68000__ || CONFIG_APUS */
if (IDE_CHIPSET_IS_PCI(hwif->chipset)) {
- sa = SA_SHIRQ;
+ sa = IRQF_SHARED;
#ifndef CONFIG_IDEPCI_SHARE_IRQ
- sa |= SA_INTERRUPT;
+ sa |= IRQF_DISABLED;
#endif /* CONFIG_IDEPCI_SHARE_IRQ */
}
spin_unlock_irq(&ide_lock);
}
-#if !defined(__mc68000__) && !defined(CONFIG_APUS) && !defined(__sparc__)
+#if !defined(__mc68000__) && !defined(CONFIG_APUS)
printk("%s at 0x%03lx-0x%03lx,0x%03lx on irq %d", hwif->name,
hwif->io_ports[IDE_DATA_OFFSET],
hwif->io_ports[IDE_DATA_OFFSET]+7,
hwif->io_ports[IDE_CONTROL_OFFSET], hwif->irq);
-#elif defined(__sparc__)
- printk("%s at 0x%03lx-0x%03lx,0x%03lx on irq %s", hwif->name,
- hwif->io_ports[IDE_DATA_OFFSET],
- hwif->io_ports[IDE_DATA_OFFSET]+7,
- hwif->io_ports[IDE_CONTROL_OFFSET], __irq_itoa(hwif->irq));
#else
printk("%s at 0x%08lx on irq %d", hwif->name,
hwif->io_ports[IDE_DATA_OFFSET], hwif->irq);
ide_drive_t *drive = container_of(dev, ide_drive_t, gendev);
spin_lock_irq(&ide_lock);
- if (drive->devfs_name[0] != '\0') {
- devfs_remove(drive->devfs_name);
- drive->devfs_name[0] = '\0';
- }
ide_remove_drive_from_hwgroup(drive);
- if (drive->id != NULL) {
- kfree(drive->id);
- drive->id = NULL;
- }
+ kfree(drive->id);
+ drive->id = NULL;
drive->present = 0;
/* Messed up locking ... */
spin_unlock_irq(&ide_lock);
drive->queue = NULL;
spin_unlock_irq(&ide_lock);
- up(&drive->gendev_rel_sem);
+ complete(&drive->gendev_rel_comp);
}
/*
drive->gendev.bus = &ide_bus_type;
drive->gendev.driver_data = drive;
drive->gendev.release = drive_release_dev;
- if (drive->present) {
- sprintf(drive->devfs_name, "ide/host%d/bus%d/target%d/lun%d",
- (hwif->channel && hwif->mate) ?
- hwif->mate->index : hwif->index,
- hwif->channel, unit, drive->lun);
- }
}
blk_register_region(MKDEV(hwif->major, 0), MAX_DRIVES << PARTN_BITS,
THIS_MODULE, ata_probe, ata_lock, hwif);
if (hwif->chipset == ide_unknown || hwif->chipset == ide_forced)
hwif->chipset = ide_generic;
for (unit = 0; unit < MAX_DRIVES; ++unit)
- if (hwif->drives[unit].present)
- device_register(&hwif->drives[unit].gendev);
+ if (hwif->drives[unit].present) {
+ int ret = device_register(
+ &hwif->drives[unit].gendev);
+ if (ret < 0)
+ printk(KERN_WARNING "IDE: %s: "
+ "device_register error: %d\n",
+ __FUNCTION__, ret);
+ }
}
}
return 0;