1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * wakeup.c - support wakeup devices 4 * Copyright (C) 2004 Li Shaohua <shaohua.li@intel.com> 5 */ 6 7 #include <linux/init.h> 8 #include <linux/acpi.h> 9 #include <linux/kernel.h> 10 #include <linux/types.h> 11 12 #include "internal.h" 13 #include "sleep.h" 14 15 struct acpi_wakeup_handler { 16 struct list_head list_node; 17 bool (*wakeup)(void *context); 18 void *context; 19 }; 20 21 static LIST_HEAD(acpi_wakeup_handler_head); 22 static DEFINE_MUTEX(acpi_wakeup_handler_mutex); 23 24 /* 25 * We didn't lock acpi_device_lock in the file, because it invokes oops in 26 * suspend/resume and isn't really required as this is called in S-state. At 27 * that time, there is no device hotplug 28 **/ 29 #define _COMPONENT ACPI_SYSTEM_COMPONENT 30 ACPI_MODULE_NAME("wakeup_devices") 31 32 /** 33 * acpi_enable_wakeup_devices - Enable wake-up device GPEs. 34 * @sleep_state: ACPI system sleep state. 35 * 36 * Enable wakeup device power of devices with the state.enable flag set and set 37 * the wakeup enable mask bits in the GPE registers that correspond to wakeup 38 * devices. 39 */ 40 void acpi_enable_wakeup_devices(u8 sleep_state) 41 { 42 struct acpi_device *dev, *tmp; 43 44 list_for_each_entry_safe(dev, tmp, &acpi_wakeup_device_list, 45 wakeup_list) { 46 if (!dev->wakeup.flags.valid 47 || sleep_state > (u32) dev->wakeup.sleep_state 48 || !(device_may_wakeup(&dev->dev) 49 || dev->wakeup.prepare_count)) 50 continue; 51 52 if (device_may_wakeup(&dev->dev)) 53 acpi_enable_wakeup_device_power(dev, sleep_state); 54 55 /* The wake-up power should have been enabled already. */ 56 acpi_set_gpe_wake_mask(dev->wakeup.gpe_device, dev->wakeup.gpe_number, 57 ACPI_GPE_ENABLE); 58 } 59 } 60 61 /** 62 * acpi_disable_wakeup_devices - Disable devices' wakeup capability. 63 * @sleep_state: ACPI system sleep state. 64 */ 65 void acpi_disable_wakeup_devices(u8 sleep_state) 66 { 67 struct acpi_device *dev, *tmp; 68 69 list_for_each_entry_safe(dev, tmp, &acpi_wakeup_device_list, 70 wakeup_list) { 71 if (!dev->wakeup.flags.valid 72 || sleep_state > (u32) dev->wakeup.sleep_state 73 || !(device_may_wakeup(&dev->dev) 74 || dev->wakeup.prepare_count)) 75 continue; 76 77 acpi_set_gpe_wake_mask(dev->wakeup.gpe_device, dev->wakeup.gpe_number, 78 ACPI_GPE_DISABLE); 79 80 if (device_may_wakeup(&dev->dev)) 81 acpi_disable_wakeup_device_power(dev); 82 } 83 } 84 85 int __init acpi_wakeup_device_init(void) 86 { 87 struct acpi_device *dev, *tmp; 88 89 mutex_lock(&acpi_device_lock); 90 list_for_each_entry_safe(dev, tmp, &acpi_wakeup_device_list, 91 wakeup_list) { 92 if (device_can_wakeup(&dev->dev)) { 93 /* Button GPEs are supposed to be always enabled. */ 94 acpi_enable_gpe(dev->wakeup.gpe_device, 95 dev->wakeup.gpe_number); 96 device_set_wakeup_enable(&dev->dev, true); 97 } 98 } 99 mutex_unlock(&acpi_device_lock); 100 return 0; 101 } 102 103 /** 104 * acpi_register_wakeup_handler - Register wakeup handler 105 * @wake_irq: The IRQ through which the device may receive wakeups 106 * @wakeup: Wakeup-handler to call when the SCI has triggered a wakeup 107 * @context: Context to pass to the handler when calling it 108 * 109 * Drivers which may share an IRQ with the SCI can use this to register 110 * a handler which returns true when the device they are managing wants 111 * to trigger a wakeup. 112 */ 113 int acpi_register_wakeup_handler(int wake_irq, bool (*wakeup)(void *context), 114 void *context) 115 { 116 struct acpi_wakeup_handler *handler; 117 118 /* 119 * If the device is not sharing its IRQ with the SCI, there is no 120 * need to register the handler. 121 */ 122 if (!acpi_sci_irq_valid() || wake_irq != acpi_sci_irq) 123 return 0; 124 125 handler = kmalloc(sizeof(*handler), GFP_KERNEL); 126 if (!handler) 127 return -ENOMEM; 128 129 handler->wakeup = wakeup; 130 handler->context = context; 131 132 mutex_lock(&acpi_wakeup_handler_mutex); 133 list_add(&handler->list_node, &acpi_wakeup_handler_head); 134 mutex_unlock(&acpi_wakeup_handler_mutex); 135 136 return 0; 137 } 138 EXPORT_SYMBOL_GPL(acpi_register_wakeup_handler); 139 140 /** 141 * acpi_unregister_wakeup_handler - Unregister wakeup handler 142 * @wakeup: Wakeup-handler passed to acpi_register_wakeup_handler() 143 * @context: Context passed to acpi_register_wakeup_handler() 144 */ 145 void acpi_unregister_wakeup_handler(bool (*wakeup)(void *context), 146 void *context) 147 { 148 struct acpi_wakeup_handler *handler; 149 150 mutex_lock(&acpi_wakeup_handler_mutex); 151 list_for_each_entry(handler, &acpi_wakeup_handler_head, list_node) { 152 if (handler->wakeup == wakeup && handler->context == context) { 153 list_del(&handler->list_node); 154 kfree(handler); 155 break; 156 } 157 } 158 mutex_unlock(&acpi_wakeup_handler_mutex); 159 } 160 EXPORT_SYMBOL_GPL(acpi_unregister_wakeup_handler); 161 162 bool acpi_check_wakeup_handlers(void) 163 { 164 struct acpi_wakeup_handler *handler; 165 166 /* No need to lock, nothing else is running when we're called. */ 167 list_for_each_entry(handler, &acpi_wakeup_handler_head, list_node) { 168 if (handler->wakeup(handler->context)) 169 return true; 170 } 171 172 return false; 173 } 174