diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2008-04-18 08:39:24 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2008-04-18 08:39:24 -0700 |
commit | 188da98800893691e47eea9335a234378e32aceb (patch) | |
tree | 57dbf491d23676e011b4946ec1867a6d55a02eef /drivers/ide/ide-generic.c | |
parent | 07fe944e87d79f8d7e1b090913fe9f2ace78f41d (diff) | |
parent | 273b8385e5817a4765f82257004c5ec661a6a5b2 (diff) | |
download | op-kernel-dev-188da98800893691e47eea9335a234378e32aceb.zip op-kernel-dev-188da98800893691e47eea9335a234378e32aceb.tar.gz |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/bart/ide-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/bart/ide-2.6: (58 commits)
ide: remove ide_init_default_irq() macro
ide: move default IDE ports setup to ide_generic host driver
ide: remove obsoleted "idex=noprobe" kernel parameter (take 2)
ide: remove needless hwif->irq check from ide_hwif_configure()
ide: init hwif->{io_ports,irq} explicitly in legacy VLB host drivers
ide: limit legacy VLB host drivers to alpha, x86 and mips
cmd640: init hwif->{io_ports,irq} explicitly
cmd640: cleanup setup_device_ptrs()
ide: add ide-4drives host driver (take 3)
ide: remove ppc ifdef from init_ide_data()
ide: remove ide_default_io_ctl() macro
ide: remove CONFIG_IDE_ARCH_OBSOLETE_INIT
ide: add CONFIG_IDE_ARCH_OBSOLETE_DEFAULTS (take 2)
ppc/pmac: remove no longer needed IDE quirk
ppc: don't include <linux/ide.h>
ppc: remove ppc_ide_md
ppc/pplus: remove ppc_ide_md.ide_init_hwif hook
ppc/sandpoint: remove ppc_ide_md hooks
ppc/lopec: remove ppc_ide_md hooks
ppc/mpc8xx: remove ppc_ide_md hooks
...
Diffstat (limited to 'drivers/ide/ide-generic.c')
-rw-r--r-- | drivers/ide/ide-generic.c | 89 |
1 files changed, 86 insertions, 3 deletions
diff --git a/drivers/ide/ide-generic.c b/drivers/ide/ide-generic.c index 9ebec08..25fda0a 100644 --- a/drivers/ide/ide-generic.c +++ b/drivers/ide/ide-generic.c @@ -1,17 +1,89 @@ /* * generic/default IDE host driver * - * Copyright (C) 2004 Bartlomiej Zolnierkiewicz + * Copyright (C) 2004, 2008 Bartlomiej Zolnierkiewicz * This code was split off from ide.c. See it for original copyrights. * * May be copied or modified under the terms of the GNU General Public License. */ +/* + * For special cases new interfaces may be added using sysfs, i.e. + * + * echo -n "0x168:0x36e:10" > /sys/class/ide_generic/add + * + * will add an interface using I/O ports 0x168-0x16f/0x36e and IRQ 10. + */ + #include <linux/kernel.h> #include <linux/init.h> #include <linux/module.h> #include <linux/ide.h> +#define DRV_NAME "ide_generic" + +static ssize_t store_add(struct class *cls, const char *buf, size_t n) +{ + ide_hwif_t *hwif; + unsigned int base, ctl; + int irq; + hw_regs_t hw; + u8 idx[] = { 0xff, 0xff, 0xff, 0xff }; + + if (sscanf(buf, "%x:%x:%d", &base, &ctl, &irq) != 3) + return -EINVAL; + + hwif = ide_find_port(base); + if (hwif == NULL) + return -ENOENT; + + memset(&hw, 0, sizeof(hw)); + ide_std_init_ports(&hw, base, ctl); + hw.irq = irq; + hw.chipset = ide_generic; + + ide_init_port_hw(hwif, &hw); + + idx[0] = hwif->index; + + ide_device_add(idx, NULL); + + return n; +}; + +static struct class_attribute ide_generic_class_attrs[] = { + __ATTR(add, S_IWUSR, NULL, store_add), + __ATTR_NULL +}; + +static void ide_generic_class_release(struct class *cls) +{ + kfree(cls); +} + +static int __init ide_generic_sysfs_init(void) +{ + struct class *cls; + int rc; + + cls = kzalloc(sizeof(*cls), GFP_KERNEL); + if (!cls) + return -ENOMEM; + + cls->name = DRV_NAME; + cls->owner = THIS_MODULE; + cls->class_release = ide_generic_class_release; + cls->class_attrs = ide_generic_class_attrs; + + rc = class_register(cls); + if (rc) { + kfree(cls); + return rc; + } + + return 0; +} + static int __init ide_generic_init(void) { u8 idx[MAX_HWIFS]; @@ -19,15 +91,26 @@ static int __init ide_generic_init(void) for (i = 0; i < MAX_HWIFS; i++) { ide_hwif_t *hwif = &ide_hwifs[i]; + unsigned long io_addr = ide_default_io_base(i); + hw_regs_t hw; + + if (hwif->chipset == ide_unknown && io_addr) { + memset(&hw, 0, sizeof(hw)); + ide_std_init_ports(&hw, io_addr, io_addr + 0x206); + hw.irq = ide_default_irq(io_addr); + ide_init_port_hw(hwif, &hw); - if (hwif->io_ports[IDE_DATA_OFFSET] && !hwif->present) idx[i] = i; - else + } else idx[i] = 0xff; } ide_device_add_all(idx, NULL); + if (ide_generic_sysfs_init()) + printk(KERN_ERR DRV_NAME ": failed to create ide_generic " + "class\n"); + return 0; } |