diff options
Diffstat (limited to 'drivers/input/gameport')
-rw-r--r-- | drivers/input/gameport/fm801-gp.c | 22 | ||||
-rw-r--r-- | drivers/input/gameport/gameport.c | 38 | ||||
-rw-r--r-- | drivers/input/gameport/lightning.c | 4 |
3 files changed, 43 insertions, 21 deletions
diff --git a/drivers/input/gameport/fm801-gp.c b/drivers/input/gameport/fm801-gp.c index 90de5afe03c..1dec00e20db 100644 --- a/drivers/input/gameport/fm801-gp.c +++ b/drivers/input/gameport/fm801-gp.c @@ -82,17 +82,19 @@ static int __devinit fm801_gp_probe(struct pci_dev *pci, const struct pci_device { struct fm801_gp *gp; struct gameport *port; + int error; gp = kzalloc(sizeof(struct fm801_gp), GFP_KERNEL); port = gameport_allocate_port(); if (!gp || !port) { printk(KERN_ERR "fm801-gp: Memory allocation failed\n"); - kfree(gp); - gameport_free_port(port); - return -ENOMEM; + error = -ENOMEM; + goto err_out_free; } - pci_enable_device(pci); + error = pci_enable_device(pci); + if (error) + goto err_out_free; port->open = fm801_gp_open; #ifdef HAVE_COOKED @@ -108,9 +110,8 @@ static int __devinit fm801_gp_probe(struct pci_dev *pci, const struct pci_device if (!gp->res_port) { printk(KERN_DEBUG "fm801-gp: unable to grab region 0x%x-0x%x\n", port->io, port->io + 0x0f); - gameport_free_port(port); - kfree(gp); - return -EBUSY; + error = -EBUSY; + goto err_out_disable_dev; } pci_set_drvdata(pci, gp); @@ -119,6 +120,13 @@ static int __devinit fm801_gp_probe(struct pci_dev *pci, const struct pci_device gameport_register_port(port); return 0; + + err_out_disable_dev: + pci_disable_device(pci); + err_out_free: + gameport_free_port(port); + kfree(gp); + return error; } static void __devexit fm801_gp_remove(struct pci_dev *pci) diff --git a/drivers/input/gameport/gameport.c b/drivers/input/gameport/gameport.c index 3f47ae55c6f..a00fe470a82 100644 --- a/drivers/input/gameport/gameport.c +++ b/drivers/input/gameport/gameport.c @@ -23,6 +23,7 @@ #include <linux/kthread.h> #include <linux/sched.h> /* HZ */ #include <linux/mutex.h> +#include <linux/freezer.h> /*#include <asm/io.h>*/ @@ -191,6 +192,8 @@ static void gameport_run_poll_handler(unsigned long d) static void gameport_bind_driver(struct gameport *gameport, struct gameport_driver *drv) { + int error; + down_write(&gameport_bus.subsys.rwsem); gameport->dev.driver = &drv->driver; @@ -198,8 +201,20 @@ static void gameport_bind_driver(struct gameport *gameport, struct gameport_driv gameport->dev.driver = NULL; goto out; } - device_bind_driver(&gameport->dev); -out: + + error = device_bind_driver(&gameport->dev); + if (error) { + printk(KERN_WARNING + "gameport: device_bind_driver() failed " + "for %s (%s) and %s, error: %d\n", + gameport->phys, gameport->name, + drv->description, error); + drv->disconnect(gameport); + gameport->dev.driver = NULL; + goto out; + } + + out: up_write(&gameport_bus.subsys.rwsem); } @@ -716,12 +731,6 @@ static int gameport_driver_remove(struct device *dev) return 0; } -static struct bus_type gameport_bus = { - .name = "gameport", - .probe = gameport_driver_probe, - .remove = gameport_driver_remove, -}; - static void gameport_add_driver(struct gameport_driver *drv) { int error; @@ -767,6 +776,15 @@ static int gameport_bus_match(struct device *dev, struct device_driver *drv) return !gameport_drv->ignore; } +static struct bus_type gameport_bus = { + .name = "gameport", + .dev_attrs = gameport_device_attrs, + .drv_attrs = gameport_driver_attrs, + .match = gameport_bus_match, + .probe = gameport_driver_probe, + .remove = gameport_driver_remove, +}; + static void gameport_set_drv(struct gameport *gameport, struct gameport_driver *drv) { mutex_lock(&gameport->drv_mutex); @@ -776,7 +794,6 @@ static void gameport_set_drv(struct gameport *gameport, struct gameport_driver * int gameport_open(struct gameport *gameport, struct gameport_driver *drv, int mode) { - if (gameport->open) { if (gameport->open(gameport, mode)) { return -1; @@ -804,9 +821,6 @@ static int __init gameport_init(void) { int error; - gameport_bus.dev_attrs = gameport_device_attrs; - gameport_bus.drv_attrs = gameport_driver_attrs; - gameport_bus.match = gameport_bus_match; error = bus_register(&gameport_bus); if (error) { printk(KERN_ERR "gameport: failed to register gameport bus, error: %d\n", error); diff --git a/drivers/input/gameport/lightning.c b/drivers/input/gameport/lightning.c index d65d8108025..6b4d4561d46 100644 --- a/drivers/input/gameport/lightning.c +++ b/drivers/input/gameport/lightning.c @@ -309,7 +309,7 @@ static int __init l4_init(void) int i, cards = 0; if (!request_region(L4_PORT, 1, "lightning")) - return -1; + return -EBUSY; for (i = 0; i < 2; i++) if (l4_add_card(i) == 0) @@ -319,7 +319,7 @@ static int __init l4_init(void) if (!cards) { release_region(L4_PORT, 1); - return -1; + return -ENODEV; } return 0; |