diff options
author | Russell King <rmk@dyn-67.arm.linux.org.uk> | 2005-11-05 21:22:13 +0000 |
---|---|---|
committer | Russell King <rmk+kernel@arm.linux.org.uk> | 2005-11-05 21:22:13 +0000 |
commit | abbf268ae8f51e19779cdf3f5fbb8144f1a5fbc3 (patch) | |
tree | 735185fb11797c7afdc885267f84a19337693897 /drivers/video | |
parent | 8d972a962177a261fc894f767fa3014f63d661e9 (diff) | |
download | op-kernel-dev-abbf268ae8f51e19779cdf3f5fbb8144f1a5fbc3.zip op-kernel-dev-abbf268ae8f51e19779cdf3f5fbb8144f1a5fbc3.tar.gz |
[DRIVER MODEL] Fix gbefb
Statically allocated devices in module data is a potential cause
of oopsen. The device may be in use by a userspace process, which
will keep a reference to the device. If the module is unloaded,
the module data will be freed. Subsequent use of the platform
device will cause a kernel oops.
Use generic platform device allocation/release code in modules.
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Acked-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/video')
-rw-r--r-- | drivers/video/gbefb.c | 18 |
1 files changed, 12 insertions, 6 deletions
diff --git a/drivers/video/gbefb.c b/drivers/video/gbefb.c index 316bfe9..ed853be 100644 --- a/drivers/video/gbefb.c +++ b/drivers/video/gbefb.c @@ -1260,24 +1260,30 @@ static struct device_driver gbefb_driver = { .remove = __devexit_p(gbefb_remove), }; -static struct platform_device gbefb_device = { - .name = "gbefb", -}; +static struct platform_device *gbefb_device; int __init gbefb_init(void) { int ret = driver_register(&gbefb_driver); if (!ret) { - ret = platform_device_register(&gbefb_device); - if (ret) + gbefb_device = platform_device_alloc("gbefb", 0); + if (gbefb_device) { + ret = platform_device_add(gbefb_device); + } else { + ret = -ENOMEM; + } + if (ret) { + platform_device_put(gbefb_device); driver_unregister(&gbefb_driver); + } } return ret; } void __exit gbefb_exit(void) { - driver_unregister(&gbefb_driver); + platform_device_unregister(gbefb_device); + driver_unregister(&gbefb_driver); } module_init(gbefb_init); |