1 /* 2 * Power off by restarting and let u-boot keep hold of the machine 3 * until the user presses a button for example. 4 * 5 * Andrew Lunn <andrew@lunn.ch> 6 * 7 * Copyright (C) 2012 Andrew Lunn 8 * 9 * This program is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License version 2 as 11 * published by the Free Software Foundation. 12 */ 13 #include <linux/kernel.h> 14 #include <linux/init.h> 15 #include <linux/platform_device.h> 16 #include <linux/of_platform.h> 17 #include <linux/module.h> 18 #include <asm/system_misc.h> 19 20 static void restart_poweroff_do_poweroff(void) 21 { 22 arm_pm_restart('h', NULL); 23 } 24 25 static int restart_poweroff_probe(struct platform_device *pdev) 26 { 27 /* If a pm_power_off function has already been added, leave it alone */ 28 if (pm_power_off != NULL) { 29 dev_err(&pdev->dev, 30 "pm_power_off function already registered"); 31 return -EBUSY; 32 } 33 34 pm_power_off = &restart_poweroff_do_poweroff; 35 return 0; 36 } 37 38 static int restart_poweroff_remove(struct platform_device *pdev) 39 { 40 if (pm_power_off == &restart_poweroff_do_poweroff) 41 pm_power_off = NULL; 42 43 return 0; 44 } 45 46 static const struct of_device_id of_restart_poweroff_match[] = { 47 { .compatible = "restart-poweroff", }, 48 {}, 49 }; 50 51 static struct platform_driver restart_poweroff_driver = { 52 .probe = restart_poweroff_probe, 53 .remove = restart_poweroff_remove, 54 .driver = { 55 .name = "poweroff-restart", 56 .owner = THIS_MODULE, 57 .of_match_table = of_restart_poweroff_match, 58 }, 59 }; 60 module_platform_driver(restart_poweroff_driver); 61 62 MODULE_AUTHOR("Andrew Lunn <andrew@lunn.ch"); 63 MODULE_DESCRIPTION("restart poweroff driver"); 64 MODULE_LICENSE("GPLv2"); 65 MODULE_ALIAS("platform:poweroff-restart"); 66