generic_event_device.h 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123
  1. /*
  2. *
  3. * Copyright (c) 2018 Intel Corporation
  4. * Copyright (c) 2019 Huawei Technologies R & D (UK) Ltd
  5. * Written by Samuel Ortiz, Shameer Kolothum
  6. *
  7. * This program is free software; you can redistribute it and/or modify it
  8. * under the terms and conditions of the GNU General Public License,
  9. * version 2 or later, as published by the Free Software Foundation.
  10. *
  11. * The ACPI Generic Event Device (GED) is a hardware-reduced specific
  12. * device[ACPI v6.1 Section 5.6.9] that handles all platform events,
  13. * including the hotplug ones. Generic Event Device allows platforms
  14. * to handle interrupts in ACPI ASL statements. It follows a very
  15. * similar approach like the _EVT method from GPIO events. All
  16. * interrupts are listed in _CRS and the handler is written in _EVT
  17. * method. Here, we use a single interrupt for the GED device, relying
  18. * on IO memory region to communicate the type of device affected by
  19. * the interrupt. This way, we can support up to 32 events with a
  20. * unique interrupt.
  21. *
  22. * Here is an example.
  23. *
  24. * Device (\_SB.GED)
  25. * {
  26. * Name (_HID, "ACPI0013")
  27. * Name (_UID, Zero)
  28. * Name (_CRS, ResourceTemplate ()
  29. * {
  30. * Interrupt (ResourceConsumer, Edge, ActiveHigh, Exclusive, ,, )
  31. * {
  32. * 0x00000029,
  33. * }
  34. * })
  35. * OperationRegion (EREG, SystemMemory, 0x09080000, 0x04)
  36. * Field (EREG, DWordAcc, NoLock, WriteAsZeros)
  37. * {
  38. * ESEL, 32
  39. * }
  40. *
  41. * Method (_EVT, 1, Serialized) // _EVT: Event
  42. * {
  43. * Local0 = ESEL // ESEL = IO memory region which specifies the
  44. * // device type.
  45. * If (((Local0 & One) == One))
  46. * {
  47. * MethodEvent1()
  48. * }
  49. * If ((Local0 & 0x2) == 0x2)
  50. * {
  51. * MethodEvent2()
  52. * }
  53. * ...
  54. * }
  55. * }
  56. *
  57. */
  58. #ifndef HW_ACPI_GENERIC_EVENT_DEVICE_H
  59. #define HW_ACPI_GENERIC_EVENT_DEVICE_H
  60. #include "hw/sysbus.h"
  61. #include "hw/acpi/memory_hotplug.h"
  62. #include "hw/acpi/ghes.h"
  63. #include "hw/acpi/cpu.h"
  64. #include "qom/object.h"
  65. #define ACPI_POWER_BUTTON_DEVICE "PWRB"
  66. #define TYPE_ACPI_GED "acpi-ged"
  67. OBJECT_DECLARE_SIMPLE_TYPE(AcpiGedState, ACPI_GED)
  68. #define ACPI_GED_EVT_SEL_OFFSET 0x0
  69. #define ACPI_GED_EVT_SEL_LEN 0x4
  70. #define ACPI_GED_REG_SLEEP_CTL 0x00
  71. #define ACPI_GED_REG_SLEEP_STS 0x01
  72. #define ACPI_GED_REG_RESET 0x02
  73. #define ACPI_GED_REG_COUNT 0x03
  74. /* ACPI_GED_REG_RESET value for reset*/
  75. #define ACPI_GED_RESET_VALUE 0x42
  76. /* ACPI_GED_REG_SLEEP_CTL.SLP_TYP value for S5 (aka poweroff) */
  77. #define ACPI_GED_SLP_TYP_S5 0x05
  78. #define GED_DEVICE "GED"
  79. #define AML_GED_EVT_REG "EREG"
  80. #define AML_GED_EVT_SEL "ESEL"
  81. /*
  82. * Platforms need to specify the GED event bitmap
  83. * to describe what kind of events they want to support
  84. * through GED.
  85. */
  86. #define ACPI_GED_MEM_HOTPLUG_EVT 0x1
  87. #define ACPI_GED_PWR_DOWN_EVT 0x2
  88. #define ACPI_GED_NVDIMM_HOTPLUG_EVT 0x4
  89. #define ACPI_GED_CPU_HOTPLUG_EVT 0x8
  90. typedef struct GEDState {
  91. MemoryRegion evt;
  92. MemoryRegion regs;
  93. uint32_t sel;
  94. } GEDState;
  95. struct AcpiGedState {
  96. SysBusDevice parent_obj;
  97. MemHotplugState memhp_state;
  98. MemoryRegion container_memhp;
  99. CPUHotplugState cpuhp_state;
  100. MemoryRegion container_cpuhp;
  101. GEDState ged_state;
  102. uint32_t ged_event_bitmap;
  103. qemu_irq irq;
  104. AcpiGhesState ghes_state;
  105. };
  106. void build_ged_aml(Aml *table, const char* name, HotplugHandler *hotplug_dev,
  107. uint32_t ged_irq, AmlRegionSpace rs, hwaddr ged_base);
  108. void acpi_dsdt_add_power_button(Aml *scope);
  109. #endif