diff options
author | Jan-Bernd Themann <ossthema@de.ibm.com> | 2007-10-26 08:37:28 -0400 |
---|---|---|
committer | Jeff Garzik <jeff@garzik.org> | 2007-10-29 05:47:09 -0400 |
commit | 2a6f4e4983918b18fe5d3fb364afe33db7139870 (patch) | |
tree | 2887c2f847ca02caf87de3bf1d5445417091806e /drivers/net/ehea/ehea_main.c | |
parent | f920c186be09718542dfa77f6ebe1814be7d35cb (diff) |
ehea: add kexec support
eHEA resources that are allocated via H_CALLs have a unique identifier each.
These identifiers are necessary to free the resources. A reboot notifier
is used to free all eHEA resources before the indentifiers get lost, i.e
before kexec starts a new kernel.
Signed-off-by: Jan-Bernd Themann <themann@de.ibm.com>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
Diffstat (limited to 'drivers/net/ehea/ehea_main.c')
-rw-r--r-- | drivers/net/ehea/ehea_main.c | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/drivers/net/ehea/ehea_main.c b/drivers/net/ehea/ehea_main.c index 0a7e78925540..f0319f1e8e05 100644 --- a/drivers/net/ehea/ehea_main.c +++ b/drivers/net/ehea/ehea_main.c | |||
@@ -33,6 +33,9 @@ | |||
33 | #include <linux/if.h> | 33 | #include <linux/if.h> |
34 | #include <linux/list.h> | 34 | #include <linux/list.h> |
35 | #include <linux/if_ether.h> | 35 | #include <linux/if_ether.h> |
36 | #include <linux/notifier.h> | ||
37 | #include <linux/reboot.h> | ||
38 | |||
36 | #include <net/ip.h> | 39 | #include <net/ip.h> |
37 | 40 | ||
38 | #include "ehea.h" | 41 | #include "ehea.h" |
@@ -3295,6 +3298,20 @@ static int __devexit ehea_remove(struct of_device *dev) | |||
3295 | return 0; | 3298 | return 0; |
3296 | } | 3299 | } |
3297 | 3300 | ||
3301 | static int ehea_reboot_notifier(struct notifier_block *nb, | ||
3302 | unsigned long action, void *unused) | ||
3303 | { | ||
3304 | if (action == SYS_RESTART) { | ||
3305 | ehea_info("Reboot: freeing all eHEA resources"); | ||
3306 | ibmebus_unregister_driver(&ehea_driver); | ||
3307 | } | ||
3308 | return NOTIFY_DONE; | ||
3309 | } | ||
3310 | |||
3311 | static struct notifier_block ehea_reboot_nb = { | ||
3312 | .notifier_call = ehea_reboot_notifier, | ||
3313 | }; | ||
3314 | |||
3298 | static int check_module_parm(void) | 3315 | static int check_module_parm(void) |
3299 | { | 3316 | { |
3300 | int ret = 0; | 3317 | int ret = 0; |
@@ -3351,6 +3368,8 @@ int __init ehea_module_init(void) | |||
3351 | if (ret) | 3368 | if (ret) |
3352 | goto out; | 3369 | goto out; |
3353 | 3370 | ||
3371 | register_reboot_notifier(&ehea_reboot_nb); | ||
3372 | |||
3354 | ret = ibmebus_register_driver(&ehea_driver); | 3373 | ret = ibmebus_register_driver(&ehea_driver); |
3355 | if (ret) { | 3374 | if (ret) { |
3356 | ehea_error("failed registering eHEA device driver on ebus"); | 3375 | ehea_error("failed registering eHEA device driver on ebus"); |
@@ -3362,6 +3381,7 @@ int __init ehea_module_init(void) | |||
3362 | if (ret) { | 3381 | if (ret) { |
3363 | ehea_error("failed to register capabilities attribute, ret=%d", | 3382 | ehea_error("failed to register capabilities attribute, ret=%d", |
3364 | ret); | 3383 | ret); |
3384 | unregister_reboot_notifier(&ehea_reboot_nb); | ||
3365 | ibmebus_unregister_driver(&ehea_driver); | 3385 | ibmebus_unregister_driver(&ehea_driver); |
3366 | goto out; | 3386 | goto out; |
3367 | } | 3387 | } |
@@ -3375,6 +3395,7 @@ static void __exit ehea_module_exit(void) | |||
3375 | flush_scheduled_work(); | 3395 | flush_scheduled_work(); |
3376 | driver_remove_file(&ehea_driver.driver, &driver_attr_capabilities); | 3396 | driver_remove_file(&ehea_driver.driver, &driver_attr_capabilities); |
3377 | ibmebus_unregister_driver(&ehea_driver); | 3397 | ibmebus_unregister_driver(&ehea_driver); |
3398 | unregister_reboot_notifier(&ehea_reboot_nb); | ||
3378 | ehea_destroy_busmap(); | 3399 | ehea_destroy_busmap(); |
3379 | } | 3400 | } |
3380 | 3401 | ||