Commit 5d125f63 authored by Christoph Hellwig's avatar Christoph Hellwig Committed by Christoph Hellwig

[PATCH] further sim710 updates

James, your sim710 changes look nice, but I think there's some more
stuff to do in this driver.  I've started with the following (all
untested due to lack of the hardware):

  - move to scsi_add_host/scsi_remove_host interface
  - remove a bunch of unneeded ifdefs
  - add missing statics
  - unregister driver templates on unload

and I think there's more that should be done, but this would change
user-visiable attributes:

  - remove the ugly single module option code and the command line
    parsing in favour of Rusty's new module_param stuff
  - split the driver into two drivers: 53c700_eisa and 53c700_mca.
    There's no logic shared between those two busses, just a little
    bit of helper in the setup/remove code

And after looking a this driver I have some rants about the new
mac/eisa code:

  - mca_register_driver/mca_unregister_driver should check for
    the precense of an MCA bus by themselves instead of leaving
    it to the caller
  - eisa_driver_register should really return 0 for sucess
  - mca_register_driver/mca_unregister_driver should be named
    mca_driver_register/mca_driver_unregister to be more similar
    to the other *driver_(un)registers.
parent 78b00649
...@@ -32,51 +32,18 @@ ...@@ -32,51 +32,18 @@
#include <linux/blk.h> #include <linux/blk.h>
#include <linux/device.h> #include <linux/device.h>
#include <linux/init.h> #include <linux/init.h>
#ifdef CONFIG_MCA
#include <linux/mca.h> #include <linux/mca.h>
#endif
#ifdef CONFIG_EISA
#include <linux/eisa.h> #include <linux/eisa.h>
#endif
#include "scsi.h" #include "scsi.h"
#include "hosts.h" #include "hosts.h"
#include "53c700.h" #include "53c700.h"
/* Must be enough for both EISA and MCA */ /* Must be enough for both EISA and MCA */
#define MAX_SLOTS 8 #define MAX_SLOTS 8
static __u8 __initdata id_array[MAX_SLOTS] = { [0 ... MAX_SLOTS-1] = 7 }; static __u8 __initdata id_array[MAX_SLOTS] = { [0 ... MAX_SLOTS-1] = 7 };
/* info is used to communicate global data across the driver register
* because the struct device_driver doesn't have any info fields. Sigh */
struct sim710_info {
Scsi_Host_Template *tpnt;
int found;
};
static __initdata struct sim710_info sim710_global_info;
#if defined(CONFIG_MCA)
/* CARD ID 01BB and 01BA use the same pos values */
#define MCA_01BB_IO_PORTS { 0x0000, 0x0000, 0x0800, 0x0C00, 0x1000, 0x1400, \
0x1800, 0x1C00, 0x2000, 0x2400, 0x2800, \
0x2C00, 0x3000, 0x3400, 0x3800, 0x3C00, \
0x4000, 0x4400, 0x4800, 0x4C00, 0x5000 }
#define MCA_01BB_IRQS { 3, 5, 11, 14 }
/* CARD ID 004f */
#define MCA_004F_IO_PORTS { 0x0000, 0x0200, 0x0300, 0x0400, 0x0500, 0x0600 }
#define MCA_004F_IRQS { 5, 9, 14 }
#endif
#ifdef MODULE
char *sim710; /* command line passed by insmod */ char *sim710; /* command line passed by insmod */
MODULE_AUTHOR("Richard Hirst"); MODULE_AUTHOR("Richard Hirst");
...@@ -85,8 +52,6 @@ MODULE_LICENSE("GPL"); ...@@ -85,8 +52,6 @@ MODULE_LICENSE("GPL");
MODULE_PARM(sim710, "s"); MODULE_PARM(sim710, "s");
#endif
#ifdef MODULE #ifdef MODULE
#define ARG_SEP ' ' #define ARG_SEP ' '
#else #else
...@@ -118,12 +83,15 @@ param_setup(char *str) ...@@ -118,12 +83,15 @@ param_setup(char *str)
} }
return 1; return 1;
} }
#ifndef MODULE
__setup("sim710=", param_setup); __setup("sim710=", param_setup);
#endif
__init int static Scsi_Host_Template sim710_driver_template = {
.name = "LSI (Symbios) 710 MCA/EISA",
.proc_name = "sim710",
.this_id = 7,
};
static __devinit int
sim710_probe_common(struct device *dev, unsigned long base_addr, sim710_probe_common(struct device *dev, unsigned long base_addr,
int irq, int clock, int differential, int scsi_id) int irq, int clock, int differential, int scsi_id)
{ {
...@@ -154,7 +122,7 @@ sim710_probe_common(struct device *dev, unsigned long base_addr, ...@@ -154,7 +122,7 @@ sim710_probe_common(struct device *dev, unsigned long base_addr,
hostdata->chip710 = 1; hostdata->chip710 = 1;
/* and register the chip */ /* and register the chip */
if((host = NCR_700_detect(sim710_global_info.tpnt, hostdata)) == NULL) { if((host = NCR_700_detect(&sim710_driver_template, hostdata)) == NULL) {
printk(KERN_ERR "sim710: No host detected; card configuration problem?\n"); printk(KERN_ERR "sim710: No host detected; card configuration problem?\n");
goto out_release; goto out_release;
} }
...@@ -168,11 +136,9 @@ sim710_probe_common(struct device *dev, unsigned long base_addr, ...@@ -168,11 +136,9 @@ sim710_probe_common(struct device *dev, unsigned long base_addr,
goto out_unregister; goto out_unregister;
} }
scsi_set_device(host, dev); scsi_add_host(host, dev);
hostdata->dev = dev; hostdata->dev = dev;
sim710_global_info.found++;
return 0; return 0;
out_unregister: out_unregister:
...@@ -185,10 +151,37 @@ sim710_probe_common(struct device *dev, unsigned long base_addr, ...@@ -185,10 +151,37 @@ sim710_probe_common(struct device *dev, unsigned long base_addr,
return -ENODEV; return -ENODEV;
} }
static __devexit int
sim710_device_remove(struct device *dev)
{
struct Scsi_Host *host = to_scsi_host(dev);
struct NCR_700_Host_Parameters *hostdata =
(struct NCR_700_Host_Parameters *)host->hostdata[0];
scsi_remove_host(host);
NCR_700_release(host);
kfree(hostdata);
free_irq(host->irq, host);
return 0;
}
#ifdef CONFIG_MCA #ifdef CONFIG_MCA
/* CARD ID 01BB and 01BA use the same pos values */
#define MCA_01BB_IO_PORTS { 0x0000, 0x0000, 0x0800, 0x0C00, 0x1000, 0x1400, \
0x1800, 0x1C00, 0x2000, 0x2400, 0x2800, \
0x2C00, 0x3000, 0x3400, 0x3800, 0x3C00, \
0x4000, 0x4400, 0x4800, 0x4C00, 0x5000 }
#define MCA_01BB_IRQS { 3, 5, 11, 14 }
/* CARD ID 004f */
#define MCA_004F_IO_PORTS { 0x0000, 0x0200, 0x0300, 0x0400, 0x0500, 0x0600 }
#define MCA_004F_IRQS { 5, 9, 14 }
static short sim710_mca_id_table[] = { 0x01bb, 0x01ba, 0x004f, 0}; static short sim710_mca_id_table[] = { 0x01bb, 0x01ba, 0x004f, 0};
__init int static __init int
sim710_mca_probe(struct device *dev) sim710_mca_probe(struct device *dev)
{ {
struct mca_device *mca_dev = to_mca_device(dev); struct mca_device *mca_dev = to_mca_device(dev);
...@@ -268,26 +261,27 @@ sim710_mca_probe(struct device *dev) ...@@ -268,26 +261,27 @@ sim710_mca_probe(struct device *dev)
0, id_array[slot]); 0, id_array[slot]);
} }
struct mca_driver sim710_mca_driver = { static struct mca_driver sim710_mca_driver = {
.id_table = sim710_mca_id_table, .id_table = sim710_mca_id_table,
.driver = { .driver = {
.name = "sim710", .name = "sim710",
.bus = &mca_bus_type, .bus = &mca_bus_type,
.probe = sim710_mca_probe, .probe = sim710_mca_probe,
.remove = __devexit_p(sim710_device_remove),
}, },
}; };
#endif /* CONFIG_MCA */ #endif /* CONFIG_MCA */
#ifdef CONFIG_EISA #ifdef CONFIG_EISA
struct eisa_device_id sim710_eisa_ids[] = { static struct eisa_device_id sim710_eisa_ids[] = {
{ "CPQ4410" }, { "CPQ4410" },
{ "CPQ4411" }, { "CPQ4411" },
{ "HWP0C80" }, { "HWP0C80" },
{ "" } { "" }
}; };
__init int static __init int
sim710_eisa_probe(struct device *dev) sim710_eisa_probe(struct device *dev)
{ {
struct eisa_device *edev = to_eisa_device(dev); struct eisa_device *edev = to_eisa_device(dev);
...@@ -329,29 +323,11 @@ struct eisa_driver sim710_eisa_driver = { ...@@ -329,29 +323,11 @@ struct eisa_driver sim710_eisa_driver = {
.remove = __devexit_p(sim710_device_remove), .remove = __devexit_p(sim710_device_remove),
}, },
}; };
#endif /* CONFIG_EISA */ #endif /* CONFIG_EISA */
static int __init sim710_init(void)
int
sim710_release(struct Scsi_Host *host)
{ {
struct D700_Host_Parameters *hostdata = int err = -ENODEV, err2;
(struct D700_Host_Parameters *)host->hostdata[0];
NCR_700_release(host);
kfree(hostdata);
free_irq(host->irq, host);
/* should do a refcount here and unregister the drivers when
* it reaches zero */
return 1;
}
int __init
sim710_detect(Scsi_Host_Template *tpnt)
{
sim710_global_info.tpnt = tpnt;
sim710_global_info.found = 0;
#ifdef MODULE #ifdef MODULE
if (sim710) if (sim710)
...@@ -359,22 +335,37 @@ sim710_detect(Scsi_Host_Template *tpnt) ...@@ -359,22 +335,37 @@ sim710_detect(Scsi_Host_Template *tpnt)
#endif #endif
#ifdef CONFIG_MCA #ifdef CONFIG_MCA
if(MCA_bus) if (MCA_bus)
mca_register_driver(&sim710_mca_driver); err = mca_register_driver(&sim710_mca_driver);
#endif #endif
#ifdef CONFIG_EISA #ifdef CONFIG_EISA
eisa_driver_register(&sim710_eisa_driver); err2 = eisa_driver_register(&sim710_eisa_driver);
/*
* The eise_driver_register return values are strange. I have
* no idea why we don't just use river_register directly anyway..
*/
if (err2 == 1)
err2 = 0;
#endif #endif
return sim710_global_info.found;
if (err < 0 || err2 < 0)
return (err < 0) ? err : err2;
return 0;
} }
static Scsi_Host_Template driver_template = { static void __exit sim710_exit(void)
.name = "LSI (Symbios) 710 MCA/EISA", {
.proc_name = "sim710", #ifdef CONFIG_MCA
.detect = sim710_detect, if (MCA_bus)
.release = sim710_release, mca_unregister_driver(&sim710_mca_driver);
.this_id = 7, #endif
};
#ifdef CONFIG_EISA
eisa_driver_unregister(&sim710_eisa_driver);
#endif
}
#include "scsi_module.c" module_init(sim710_init);
module_exit(sim710_exit);
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment