intel-wmi-thunderbolt.c 2.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * WMI Thunderbolt driver
  4. *
  5. * Copyright (C) 2017 Dell Inc. All Rights Reserved.
  6. */
  7. #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  8. #include <linux/acpi.h>
  9. #include <linux/device.h>
  10. #include <linux/fs.h>
  11. #include <linux/kernel.h>
  12. #include <linux/module.h>
  13. #include <linux/string.h>
  14. #include <linux/sysfs.h>
  15. #include <linux/types.h>
  16. #include <linux/wmi.h>
  17. #define INTEL_WMI_THUNDERBOLT_GUID "86CCFD48-205E-4A77-9C48-2021CBEDE341"
  18. static ssize_t force_power_store(struct device *dev,
  19. struct device_attribute *attr,
  20. const char *buf, size_t count)
  21. {
  22. struct acpi_buffer input;
  23. acpi_status status;
  24. u8 mode;
  25. input.length = sizeof(u8);
  26. input.pointer = &mode;
  27. mode = hex_to_bin(buf[0]);
  28. dev_dbg(dev, "force_power: storing %#x\n", mode);
  29. if (mode == 0 || mode == 1) {
  30. status = wmi_evaluate_method(INTEL_WMI_THUNDERBOLT_GUID, 0, 1,
  31. &input, NULL);
  32. if (ACPI_FAILURE(status)) {
  33. dev_dbg(dev, "force_power: failed to evaluate ACPI method\n");
  34. return -ENODEV;
  35. }
  36. } else {
  37. dev_dbg(dev, "force_power: unsupported mode\n");
  38. return -EINVAL;
  39. }
  40. return count;
  41. }
  42. static DEVICE_ATTR_WO(force_power);
  43. static struct attribute *tbt_attrs[] = {
  44. &dev_attr_force_power.attr,
  45. NULL
  46. };
  47. static const struct attribute_group tbt_attribute_group = {
  48. .attrs = tbt_attrs,
  49. };
  50. static int intel_wmi_thunderbolt_probe(struct wmi_device *wdev)
  51. {
  52. int ret;
  53. ret = sysfs_create_group(&wdev->dev.kobj, &tbt_attribute_group);
  54. kobject_uevent(&wdev->dev.kobj, KOBJ_CHANGE);
  55. return ret;
  56. }
  57. static int intel_wmi_thunderbolt_remove(struct wmi_device *wdev)
  58. {
  59. sysfs_remove_group(&wdev->dev.kobj, &tbt_attribute_group);
  60. kobject_uevent(&wdev->dev.kobj, KOBJ_CHANGE);
  61. return 0;
  62. }
  63. static const struct wmi_device_id intel_wmi_thunderbolt_id_table[] = {
  64. { .guid_string = INTEL_WMI_THUNDERBOLT_GUID },
  65. { },
  66. };
  67. static struct wmi_driver intel_wmi_thunderbolt_driver = {
  68. .driver = {
  69. .name = "intel-wmi-thunderbolt",
  70. },
  71. .probe = intel_wmi_thunderbolt_probe,
  72. .remove = intel_wmi_thunderbolt_remove,
  73. .id_table = intel_wmi_thunderbolt_id_table,
  74. };
  75. module_wmi_driver(intel_wmi_thunderbolt_driver);
  76. MODULE_ALIAS("wmi:" INTEL_WMI_THUNDERBOLT_GUID);
  77. MODULE_AUTHOR("Mario Limonciello <mario.limonciello@dell.com>");
  78. MODULE_DESCRIPTION("Intel WMI Thunderbolt force power driver");
  79. MODULE_LICENSE("GPL v2");