diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2011-02-21 18:08:33 -0500 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2011-02-21 18:08:33 -0500 |
| commit | 5fb24b8109e0cb343cc89cb148a836d490caa456 (patch) | |
| tree | c8d97a55a303c8c710d8dc7888c52554960cb4b2 | |
| parent | 99273ac4dc4db0cfb38fec65d4afb8a0f6bc6e58 (diff) | |
| parent | a3d77411e8b2ad661958c1fbee65beb476ec6d70 (diff) | |
Merge branch 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mjg59/platform-drivers-x86
* 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mjg59/platform-drivers-x86:
dell-laptop: Toggle the unsupported hardware killswitch
thinkpad_acpi: Always report scancodes for hotkeys
acer-wmi: Fix capitalisation of GUID
platform/x86: ideapad-laptop depends on INPUT
platform: x86: acer-wmi: world-writable sysfs threeg file
platform: x86: asus_acpi: world-writable procfs files
platform: x86: tc1100-wmi: world-writable sysfs wireless and jogdial files
platform-drivers: x86: pmic: Use request_irq instead of chained handler
platform-drivers: x86: pmic: Use irq_chip buslock mechanism
platform-drivers: x86: Convert pmic to new irq_chip functions
platform-drivers: x86: pmic: Fix up bogus irq hackery
| -rw-r--r-- | drivers/platform/x86/Kconfig | 2 | ||||
| -rw-r--r-- | drivers/platform/x86/acer-wmi.c | 4 | ||||
| -rw-r--r-- | drivers/platform/x86/asus_acpi.c | 8 | ||||
| -rw-r--r-- | drivers/platform/x86/dell-laptop.c | 24 | ||||
| -rw-r--r-- | drivers/platform/x86/intel_pmic_gpio.c | 116 | ||||
| -rw-r--r-- | drivers/platform/x86/tc1100-wmi.c | 2 | ||||
| -rw-r--r-- | drivers/platform/x86/thinkpad_acpi.c | 8 |
7 files changed, 61 insertions, 103 deletions
diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig index d163bc2e2b9..a59af5b24f0 100644 --- a/drivers/platform/x86/Kconfig +++ b/drivers/platform/x86/Kconfig | |||
| @@ -227,7 +227,7 @@ config SONYPI_COMPAT | |||
| 227 | config IDEAPAD_LAPTOP | 227 | config IDEAPAD_LAPTOP |
| 228 | tristate "Lenovo IdeaPad Laptop Extras" | 228 | tristate "Lenovo IdeaPad Laptop Extras" |
| 229 | depends on ACPI | 229 | depends on ACPI |
| 230 | depends on RFKILL | 230 | depends on RFKILL && INPUT |
| 231 | select INPUT_SPARSEKMAP | 231 | select INPUT_SPARSEKMAP |
| 232 | help | 232 | help |
| 233 | This is a driver for the rfkill switches on Lenovo IdeaPad netbooks. | 233 | This is a driver for the rfkill switches on Lenovo IdeaPad netbooks. |
diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c index c5c4b8c32eb..38b34a73866 100644 --- a/drivers/platform/x86/acer-wmi.c +++ b/drivers/platform/x86/acer-wmi.c | |||
| @@ -84,7 +84,7 @@ MODULE_LICENSE("GPL"); | |||
| 84 | */ | 84 | */ |
| 85 | #define AMW0_GUID1 "67C3371D-95A3-4C37-BB61-DD47B491DAAB" | 85 | #define AMW0_GUID1 "67C3371D-95A3-4C37-BB61-DD47B491DAAB" |
| 86 | #define AMW0_GUID2 "431F16ED-0C2B-444C-B267-27DEB140CF9C" | 86 | #define AMW0_GUID2 "431F16ED-0C2B-444C-B267-27DEB140CF9C" |
| 87 | #define WMID_GUID1 "6AF4F258-B401-42fd-BE91-3D4AC2D7C0D3" | 87 | #define WMID_GUID1 "6AF4F258-B401-42FD-BE91-3D4AC2D7C0D3" |
| 88 | #define WMID_GUID2 "95764E09-FB56-4e83-B31A-37761F60994A" | 88 | #define WMID_GUID2 "95764E09-FB56-4e83-B31A-37761F60994A" |
| 89 | #define WMID_GUID3 "61EF69EA-865C-4BC3-A502-A0DEBA0CB531" | 89 | #define WMID_GUID3 "61EF69EA-865C-4BC3-A502-A0DEBA0CB531" |
| 90 | 90 | ||
| @@ -1280,7 +1280,7 @@ static ssize_t set_bool_threeg(struct device *dev, | |||
| 1280 | return -EINVAL; | 1280 | return -EINVAL; |
| 1281 | return count; | 1281 | return count; |
| 1282 | } | 1282 | } |
| 1283 | static DEVICE_ATTR(threeg, S_IWUGO | S_IRUGO | S_IWUSR, show_bool_threeg, | 1283 | static DEVICE_ATTR(threeg, S_IRUGO | S_IWUSR, show_bool_threeg, |
| 1284 | set_bool_threeg); | 1284 | set_bool_threeg); |
| 1285 | 1285 | ||
| 1286 | static ssize_t show_interface(struct device *dev, struct device_attribute *attr, | 1286 | static ssize_t show_interface(struct device *dev, struct device_attribute *attr, |
diff --git a/drivers/platform/x86/asus_acpi.c b/drivers/platform/x86/asus_acpi.c index 4633fd8532c..fe495939c30 100644 --- a/drivers/platform/x86/asus_acpi.c +++ b/drivers/platform/x86/asus_acpi.c | |||
| @@ -1081,14 +1081,8 @@ static int asus_hotk_add_fs(struct acpi_device *device) | |||
| 1081 | struct proc_dir_entry *proc; | 1081 | struct proc_dir_entry *proc; |
| 1082 | mode_t mode; | 1082 | mode_t mode; |
| 1083 | 1083 | ||
| 1084 | /* | ||
| 1085 | * If parameter uid or gid is not changed, keep the default setting for | ||
| 1086 | * our proc entries (-rw-rw-rw-) else, it means we care about security, | ||
| 1087 | * and then set to -rw-rw---- | ||
| 1088 | */ | ||
| 1089 | |||
| 1090 | if ((asus_uid == 0) && (asus_gid == 0)) { | 1084 | if ((asus_uid == 0) && (asus_gid == 0)) { |
| 1091 | mode = S_IFREG | S_IRUGO | S_IWUGO; | 1085 | mode = S_IFREG | S_IRUGO | S_IWUSR | S_IWGRP; |
| 1092 | } else { | 1086 | } else { |
| 1093 | mode = S_IFREG | S_IRUSR | S_IRGRP | S_IWUSR | S_IWGRP; | 1087 | mode = S_IFREG | S_IRUSR | S_IRGRP | S_IWUSR | S_IWGRP; |
| 1094 | printk(KERN_WARNING " asus_uid and asus_gid parameters are " | 1088 | printk(KERN_WARNING " asus_uid and asus_gid parameters are " |
diff --git a/drivers/platform/x86/dell-laptop.c b/drivers/platform/x86/dell-laptop.c index 34657f96b5a..ad24ef36f9f 100644 --- a/drivers/platform/x86/dell-laptop.c +++ b/drivers/platform/x86/dell-laptop.c | |||
| @@ -290,9 +290,12 @@ static int dell_rfkill_set(void *data, bool blocked) | |||
| 290 | dell_send_request(buffer, 17, 11); | 290 | dell_send_request(buffer, 17, 11); |
| 291 | 291 | ||
| 292 | /* If the hardware switch controls this radio, and the hardware | 292 | /* If the hardware switch controls this radio, and the hardware |
| 293 | switch is disabled, don't allow changing the software state */ | 293 | switch is disabled, don't allow changing the software state. |
| 294 | If the hardware switch is reported as not supported, always | ||
| 295 | fire the SMI to toggle the killswitch. */ | ||
| 294 | if ((hwswitch_state & BIT(hwswitch_bit)) && | 296 | if ((hwswitch_state & BIT(hwswitch_bit)) && |
| 295 | !(buffer->output[1] & BIT(16))) { | 297 | !(buffer->output[1] & BIT(16)) && |
| 298 | (buffer->output[1] & BIT(0))) { | ||
| 296 | ret = -EINVAL; | 299 | ret = -EINVAL; |
| 297 | goto out; | 300 | goto out; |
| 298 | } | 301 | } |
| @@ -398,6 +401,23 @@ static const struct file_operations dell_debugfs_fops = { | |||
| 398 | 401 | ||
| 399 | static void dell_update_rfkill(struct work_struct *ignored) | 402 | static void dell_update_rfkill(struct work_struct *ignored) |
| 400 | { | 403 | { |
| 404 | int status; | ||
| 405 | |||
| 406 | get_buffer(); | ||
| 407 | dell_send_request(buffer, 17, 11); | ||
| 408 | status = buffer->output[1]; | ||
| 409 | release_buffer(); | ||
| 410 | |||
| 411 | /* if hardware rfkill is not supported, set it explicitly */ | ||
| 412 | if (!(status & BIT(0))) { | ||
| 413 | if (wifi_rfkill) | ||
| 414 | dell_rfkill_set((void *)1, !((status & BIT(17)) >> 17)); | ||
| 415 | if (bluetooth_rfkill) | ||
| 416 | dell_rfkill_set((void *)2, !((status & BIT(18)) >> 18)); | ||
| 417 | if (wwan_rfkill) | ||
| 418 | dell_rfkill_set((void *)3, !((status & BIT(19)) >> 19)); | ||
| 419 | } | ||
| 420 | |||
| 401 | if (wifi_rfkill) | 421 | if (wifi_rfkill) |
| 402 | dell_rfkill_query(wifi_rfkill, (void *)1); | 422 | dell_rfkill_query(wifi_rfkill, (void *)1); |
| 403 | if (bluetooth_rfkill) | 423 | if (bluetooth_rfkill) |
diff --git a/drivers/platform/x86/intel_pmic_gpio.c b/drivers/platform/x86/intel_pmic_gpio.c index 930e6276236..61433d49286 100644 --- a/drivers/platform/x86/intel_pmic_gpio.c +++ b/drivers/platform/x86/intel_pmic_gpio.c | |||
| @@ -60,69 +60,20 @@ enum pmic_gpio_register { | |||
| 60 | #define GPOSW_DOU 0x08 | 60 | #define GPOSW_DOU 0x08 |
| 61 | #define GPOSW_RDRV 0x30 | 61 | #define GPOSW_RDRV 0x30 |
| 62 | 62 | ||
| 63 | #define GPIO_UPDATE_TYPE 0x80000000 | ||
| 63 | 64 | ||
| 64 | #define NUM_GPIO 24 | 65 | #define NUM_GPIO 24 |
| 65 | 66 | ||
| 66 | struct pmic_gpio_irq { | ||
| 67 | spinlock_t lock; | ||
| 68 | u32 trigger[NUM_GPIO]; | ||
| 69 | u32 dirty; | ||
| 70 | struct work_struct work; | ||
| 71 | }; | ||
| 72 | |||
| 73 | |||
| 74 | struct pmic_gpio { | 67 | struct pmic_gpio { |
| 68 | struct mutex buslock; | ||
| 75 | struct gpio_chip chip; | 69 | struct gpio_chip chip; |
| 76 | struct pmic_gpio_irq irqtypes; | ||
| 77 | void *gpiointr; | 70 | void *gpiointr; |
| 78 | int irq; | 71 | int irq; |
| 79 | unsigned irq_base; | 72 | unsigned irq_base; |
| 73 | unsigned int update_type; | ||
| 74 | u32 trigger_type; | ||
| 80 | }; | 75 | }; |
| 81 | 76 | ||
| 82 | static void pmic_program_irqtype(int gpio, int type) | ||
| 83 | { | ||
| 84 | if (type & IRQ_TYPE_EDGE_RISING) | ||
| 85 | intel_scu_ipc_update_register(GPIO0 + gpio, 0x20, 0x20); | ||
| 86 | else | ||
| 87 | intel_scu_ipc_update_register(GPIO0 + gpio, 0x00, 0x20); | ||
| 88 | |||
| 89 | if (type & IRQ_TYPE_EDGE_FALLING) | ||
| 90 | intel_scu_ipc_update_register(GPIO0 + gpio, 0x10, 0x10); | ||
| 91 | else | ||
| 92 | intel_scu_ipc_update_register(GPIO0 + gpio, 0x00, 0x10); | ||
| 93 | }; | ||
| 94 | |||
| 95 | static void pmic_irqtype_work(struct work_struct *work) | ||
| 96 | { | ||
| 97 | struct pmic_gpio_irq *t = | ||
| 98 | container_of(work, struct pmic_gpio_irq, work); | ||
| 99 | unsigned long flags; | ||
| 100 | int i; | ||
| 101 | u16 type; | ||
| 102 | |||
| 103 | spin_lock_irqsave(&t->lock, flags); | ||
| 104 | /* As we drop the lock, we may need multiple scans if we race the | ||
| 105 | pmic_irq_type function */ | ||
| 106 | while (t->dirty) { | ||
| 107 | /* | ||
| 108 | * For each pin that has the dirty bit set send an IPC | ||
| 109 | * message to configure the hardware via the PMIC | ||
| 110 | */ | ||
| 111 | for (i = 0; i < NUM_GPIO; i++) { | ||
| 112 | if (!(t->dirty & (1 << i))) | ||
| 113 | continue; | ||
| 114 | t->dirty &= ~(1 << i); | ||
| 115 | /* We can't trust the array entry or dirty | ||
| 116 | once the lock is dropped */ | ||
| 117 | type = t->trigger[i]; | ||
| 118 | spin_unlock_irqrestore(&t->lock, flags); | ||
| 119 | pmic_program_irqtype(i, type); | ||
| 120 | spin_lock_irqsave(&t->lock, flags); | ||
| 121 | } | ||
| 122 | } | ||
| 123 | spin_unlock_irqrestore(&t->lock, flags); | ||
| 124 | } | ||
| 125 | |||
| 126 | static int pmic_gpio_direction_input(struct gpio_chip *chip, unsigned offset) | 77 | static int pmic_gpio_direction_input(struct gpio_chip *chip, unsigned offset) |
| 127 | { | 78 | { |
| 128 | if (offset > 8) { | 79 | if (offset > 8) { |
| @@ -190,25 +141,24 @@ static void pmic_gpio_set(struct gpio_chip *chip, unsigned offset, int value) | |||
| 190 | 1 << (offset - 16)); | 141 | 1 << (offset - 16)); |
| 191 | } | 142 | } |
| 192 | 143 | ||
| 193 | static int pmic_irq_type(unsigned irq, unsigned type) | 144 | /* |
| 145 | * This is called from genirq with pg->buslock locked and | ||
| 146 | * irq_desc->lock held. We can not access the scu bus here, so we | ||
| 147 | * store the change and update in the bus_sync_unlock() function below | ||
| 148 | */ | ||
| 149 | static int pmic_irq_type(struct irq_data *data, unsigned type) | ||
| 194 | { | 150 | { |
| 195 | struct pmic_gpio *pg = get_irq_chip_data(irq); | 151 | struct pmic_gpio *pg = irq_data_get_irq_chip_data(data); |
| 196 | u32 gpio = irq - pg->irq_base; | 152 | u32 gpio = data->irq - pg->irq_base; |
| 197 | unsigned long flags; | ||
| 198 | 153 | ||
| 199 | if (gpio >= pg->chip.ngpio) | 154 | if (gpio >= pg->chip.ngpio) |
| 200 | return -EINVAL; | 155 | return -EINVAL; |
| 201 | 156 | ||
| 202 | spin_lock_irqsave(&pg->irqtypes.lock, flags); | 157 | pg->trigger_type = type; |
| 203 | pg->irqtypes.trigger[gpio] = type; | 158 | pg->update_type = gpio | GPIO_UPDATE_TYPE; |
| 204 | pg->irqtypes.dirty |= (1 << gpio); | ||
| 205 | spin_unlock_irqrestore(&pg->irqtypes.lock, flags); | ||
| 206 | schedule_work(&pg->irqtypes.work); | ||
| 207 | return 0; | 159 | return 0; |
| 208 | } | 160 | } |
| 209 | 161 | ||
| 210 | |||
| 211 | |||
| 212 | static int pmic_gpio_to_irq(struct gpio_chip *chip, unsigned offset) | 162 | static int pmic_gpio_to_irq(struct gpio_chip *chip, unsigned offset) |
| 213 | { | 163 | { |
| 214 | struct pmic_gpio *pg = container_of(chip, struct pmic_gpio, chip); | 164 | struct pmic_gpio *pg = container_of(chip, struct pmic_gpio, chip); |
| @@ -217,38 +167,32 @@ static int pmic_gpio_to_irq(struct gpio_chip *chip, unsigned offset) | |||
| 217 | } | 167 | } |
| 218 | 168 | ||
| 219 | /* the gpiointr register is read-clear, so just do nothing. */ | 169 | /* the gpiointr register is read-clear, so just do nothing. */ |
| 220 | static void pmic_irq_unmask(unsigned irq) | 170 | static void pmic_irq_unmask(struct irq_data *data) { } |
| 221 | { | ||
| 222 | }; | ||
| 223 | 171 | ||
| 224 | static void pmic_irq_mask(unsigned irq) | 172 | static void pmic_irq_mask(struct irq_data *data) { } |
| 225 | { | ||
| 226 | }; | ||
| 227 | 173 | ||
| 228 | static struct irq_chip pmic_irqchip = { | 174 | static struct irq_chip pmic_irqchip = { |
| 229 | .name = "PMIC-GPIO", | 175 | .name = "PMIC-GPIO", |
| 230 | .mask = pmic_irq_mask, | 176 | .irq_mask = pmic_irq_mask, |
| 231 | .unmask = pmic_irq_unmask, | 177 | .irq_unmask = pmic_irq_unmask, |
| 232 | .set_type = pmic_irq_type, | 178 | .irq_set_type = pmic_irq_type, |
| 233 | }; | 179 | }; |
| 234 | 180 | ||
| 235 | static void pmic_irq_handler(unsigned irq, struct irq_desc *desc) | 181 | static irqreturn_t pmic_irq_handler(int irq, void *data) |
| 236 | { | 182 | { |
| 237 | struct pmic_gpio *pg = (struct pmic_gpio *)get_irq_data(irq); | 183 | struct pmic_gpio *pg = data; |
| 238 | u8 intsts = *((u8 *)pg->gpiointr + 4); | 184 | u8 intsts = *((u8 *)pg->gpiointr + 4); |
| 239 | int gpio; | 185 | int gpio; |
| 186 | irqreturn_t ret = IRQ_NONE; | ||
| 240 | 187 | ||
| 241 | for (gpio = 0; gpio < 8; gpio++) { | 188 | for (gpio = 0; gpio < 8; gpio++) { |
| 242 | if (intsts & (1 << gpio)) { | 189 | if (intsts & (1 << gpio)) { |
| 243 | pr_debug("pmic pin %d triggered\n", gpio); | 190 | pr_debug("pmic pin %d triggered\n", gpio); |
| 244 | generic_handle_irq(pg->irq_base + gpio); | 191 | generic_handle_irq(pg->irq_base + gpio); |
| 192 | ret = IRQ_HANDLED; | ||
| 245 | } | 193 | } |
| 246 | } | 194 | } |
| 247 | 195 | return ret; | |
| 248 | if (desc->chip->irq_eoi) | ||
| 249 | desc->chip->irq_eoi(irq_get_irq_data(irq)); | ||
| 250 | else | ||
| 251 | dev_warn(pg->chip.dev, "missing EOI handler for irq %d\n", irq); | ||
| 252 | } | 196 | } |
| 253 | 197 | ||
| 254 | static int __devinit platform_pmic_gpio_probe(struct platform_device *pdev) | 198 | static int __devinit platform_pmic_gpio_probe(struct platform_device *pdev) |
| @@ -297,8 +241,7 @@ static int __devinit platform_pmic_gpio_probe(struct platform_device *pdev) | |||
| 297 | pg->chip.can_sleep = 1; | 241 | pg->chip.can_sleep = 1; |
| 298 | pg->chip.dev = dev; | 242 | pg->chip.dev = dev; |
| 299 | 243 | ||
| 300 | INIT_WORK(&pg->irqtypes.work, pmic_irqtype_work); | 244 | mutex_init(&pg->buslock); |
| 301 | spin_lock_init(&pg->irqtypes.lock); | ||
| 302 | 245 | ||
| 303 | pg->chip.dev = dev; | 246 | pg->chip.dev = dev; |
| 304 | retval = gpiochip_add(&pg->chip); | 247 | retval = gpiochip_add(&pg->chip); |
| @@ -306,8 +249,13 @@ static int __devinit platform_pmic_gpio_probe(struct platform_device *pdev) | |||
| 306 | printk(KERN_ERR "%s: Can not add pmic gpio chip.\n", __func__); | 249 | printk(KERN_ERR "%s: Can not add pmic gpio chip.\n", __func__); |
| 307 | goto err; | 250 | goto err; |
| 308 | } | 251 | } |
| 309 | set_irq_data(pg->irq, pg); | 252 | |
| 310 | set_irq_chained_handler(pg->irq, pmic_irq_handler); | 253 | retval = request_irq(pg->irq, pmic_irq_handler, 0, "pmic", pg); |
| 254 | if (retval) { | ||
| 255 | printk(KERN_WARNING "pmic: Interrupt request failed\n"); | ||
| 256 | goto err; | ||
| 257 | } | ||
| 258 | |||
| 311 | for (i = 0; i < 8; i++) { | 259 | for (i = 0; i < 8; i++) { |
| 312 | set_irq_chip_and_handler_name(i + pg->irq_base, &pmic_irqchip, | 260 | set_irq_chip_and_handler_name(i + pg->irq_base, &pmic_irqchip, |
| 313 | handle_simple_irq, "demux"); | 261 | handle_simple_irq, "demux"); |
diff --git a/drivers/platform/x86/tc1100-wmi.c b/drivers/platform/x86/tc1100-wmi.c index 1fe0f1feff7..865ef78d6f1 100644 --- a/drivers/platform/x86/tc1100-wmi.c +++ b/drivers/platform/x86/tc1100-wmi.c | |||
| @@ -162,7 +162,7 @@ set_bool_##value(struct device *dev, struct device_attribute *attr, \ | |||
| 162 | return -EINVAL; \ | 162 | return -EINVAL; \ |
| 163 | return count; \ | 163 | return count; \ |
| 164 | } \ | 164 | } \ |
| 165 | static DEVICE_ATTR(value, S_IWUGO | S_IRUGO | S_IWUSR, \ | 165 | static DEVICE_ATTR(value, S_IRUGO | S_IWUSR, \ |
| 166 | show_bool_##value, set_bool_##value); | 166 | show_bool_##value, set_bool_##value); |
| 167 | 167 | ||
| 168 | show_set_bool(wireless, TC1100_INSTANCE_WIRELESS); | 168 | show_set_bool(wireless, TC1100_INSTANCE_WIRELESS); |
diff --git a/drivers/platform/x86/thinkpad_acpi.c b/drivers/platform/x86/thinkpad_acpi.c index dd599585c6a..eb9922385ef 100644 --- a/drivers/platform/x86/thinkpad_acpi.c +++ b/drivers/platform/x86/thinkpad_acpi.c | |||
| @@ -2275,16 +2275,12 @@ static void tpacpi_input_send_key(const unsigned int scancode) | |||
| 2275 | if (keycode != KEY_RESERVED) { | 2275 | if (keycode != KEY_RESERVED) { |
| 2276 | mutex_lock(&tpacpi_inputdev_send_mutex); | 2276 | mutex_lock(&tpacpi_inputdev_send_mutex); |
| 2277 | 2277 | ||
| 2278 | input_event(tpacpi_inputdev, EV_MSC, MSC_SCAN, scancode); | ||
| 2278 | input_report_key(tpacpi_inputdev, keycode, 1); | 2279 | input_report_key(tpacpi_inputdev, keycode, 1); |
| 2279 | if (keycode == KEY_UNKNOWN) | ||
| 2280 | input_event(tpacpi_inputdev, EV_MSC, MSC_SCAN, | ||
| 2281 | scancode); | ||
| 2282 | input_sync(tpacpi_inputdev); | 2280 | input_sync(tpacpi_inputdev); |
| 2283 | 2281 | ||
| 2282 | input_event(tpacpi_inputdev, EV_MSC, MSC_SCAN, scancode); | ||
| 2284 | input_report_key(tpacpi_inputdev, keycode, 0); | 2283 | input_report_key(tpacpi_inputdev, keycode, 0); |
| 2285 | if (keycode == KEY_UNKNOWN) | ||
| 2286 | input_event(tpacpi_inputdev, EV_MSC, MSC_SCAN, | ||
| 2287 | scancode); | ||
| 2288 | input_sync(tpacpi_inputdev); | 2284 | input_sync(tpacpi_inputdev); |
| 2289 | 2285 | ||
| 2290 | mutex_unlock(&tpacpi_inputdev_send_mutex); | 2286 | mutex_unlock(&tpacpi_inputdev_send_mutex); |
