ehea: add kexec support
authorJan-Bernd Themann <ossthema@de.ibm.com>
Fri, 26 Oct 2007 12:37:28 +0000 (14:37 +0200)
committerJeff Garzik <jeff@garzik.org>
Mon, 29 Oct 2007 09:47:09 +0000 (05:47 -0400)
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>
drivers/net/ehea/ehea.h
drivers/net/ehea/ehea_main.c

index 4b4b74e47a670d1d958120a6f4c5b1f74051af30..f78e5bf7cb3334f7dba7e1dcdddf35c10fd79a7b 100644 (file)
@@ -40,7 +40,7 @@
 #include <asm/io.h>
 
 #define DRV_NAME       "ehea"
-#define DRV_VERSION    "EHEA_0079"
+#define DRV_VERSION    "EHEA_0080"
 
 /* eHEA capability flags */
 #define DLPAR_PORT_ADD_REM 1
index 0a7e789255402c306d88eedf01c9ef426f401733..f0319f1e8e052e99adfde7ca658cfaf7074b1ac1 100644 (file)
@@ -33,6 +33,9 @@
 #include <linux/if.h>
 #include <linux/list.h>
 #include <linux/if_ether.h>
+#include <linux/notifier.h>
+#include <linux/reboot.h>
+
 #include <net/ip.h>
 
 #include "ehea.h"
@@ -3295,6 +3298,20 @@ static int __devexit ehea_remove(struct of_device *dev)
        return 0;
 }
 
+static int ehea_reboot_notifier(struct notifier_block *nb,
+                               unsigned long action, void *unused)
+{
+       if (action == SYS_RESTART) {
+               ehea_info("Reboot: freeing all eHEA resources");
+               ibmebus_unregister_driver(&ehea_driver);
+       }
+       return NOTIFY_DONE;
+}
+
+static struct notifier_block ehea_reboot_nb = {
+        .notifier_call = ehea_reboot_notifier,
+};
+
 static int check_module_parm(void)
 {
        int ret = 0;
@@ -3351,6 +3368,8 @@ int __init ehea_module_init(void)
        if (ret)
                goto out;
 
+       register_reboot_notifier(&ehea_reboot_nb);
+
        ret = ibmebus_register_driver(&ehea_driver);
        if (ret) {
                ehea_error("failed registering eHEA device driver on ebus");
@@ -3362,6 +3381,7 @@ int __init ehea_module_init(void)
        if (ret) {
                ehea_error("failed to register capabilities attribute, ret=%d",
                           ret);
+               unregister_reboot_notifier(&ehea_reboot_nb);
                ibmebus_unregister_driver(&ehea_driver);
                goto out;
        }
@@ -3375,6 +3395,7 @@ static void __exit ehea_module_exit(void)
        flush_scheduled_work();
        driver_remove_file(&ehea_driver.driver, &driver_attr_capabilities);
        ibmebus_unregister_driver(&ehea_driver);
+       unregister_reboot_notifier(&ehea_reboot_nb);
        ehea_destroy_busmap();
 }