ReactOS 0.4.17-dev-769-g1500a35
event.c File Reference
Include dependency graph for event.c:

Go to the source code of this file.

Classes

struct  fixed_event
 
struct  fixed_event_handler
 
struct  gpe_native_handler
 
struct  gpe_implicit_notify_handler
 
struct  gp_event
 
struct  gpe_register
 
struct  gpe_block
 
struct  gpe_interrupt_ctx
 
struct  gpe_match_ctx
 
struct  gpe_search_ctx
 
struct  do_for_all_gpes_ctx
 

Macros

#define UACPI_EVENT_DISABLED   0
 
#define UACPI_EVENT_ENABLED   1
 
#define EVENTS_PER_GPE_REGISTER   8
 
#define PM1_STATUS_BITS
 

Typedefs

typedef uacpi_iteration_decision(* gpe_block_iteration_callback) (struct gpe_block *, uacpi_handle)
 

Enumerations

enum  gpe_handler_type {
  GPE_HANDLER_TYPE_NONE = 0 , GPE_HANDLER_TYPE_AML_HANDLER = 1 , GPE_HANDLER_TYPE_NATIVE_HANDLER = 2 , GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW = 3 ,
  GPE_HANDLER_TYPE_IMPLICIT_NOTIFY = 4
}
 
enum  gpe_state { GPE_STATE_ENABLED , GPE_STATE_ENABLED_CONDITIONALLY , GPE_STATE_DISABLED }
 
enum  gpe_block_action { GPE_BLOCK_ACTION_DISABLE_ALL , GPE_BLOCK_ACTION_ENABLE_ALL_FOR_RUNTIME , GPE_BLOCK_ACTION_ENABLE_ALL_FOR_WAKE , GPE_BLOCK_ACTION_CLEAR_ALL }
 
enum  event_clear_if_first { EVENT_CLEAR_IF_FIRST_YES , EVENT_CLEAR_IF_FIRST_NO }
 

Functions

static uacpi_status initialize_fixed_events (void)
 
static uacpi_status set_event (uacpi_u8 event, uacpi_u8 value)
 
uacpi_status uacpi_enable_fixed_event (uacpi_fixed_event event)
 
uacpi_status uacpi_disable_fixed_event (uacpi_fixed_event event)
 
uacpi_status uacpi_clear_fixed_event (uacpi_fixed_event event)
 
static uacpi_interrupt_ret dispatch_fixed_event (const struct fixed_event *ev, uacpi_fixed_event event)
 
static uacpi_interrupt_ret handle_fixed_events (void)
 
static uacpi_u8 gpe_get_mask (struct gp_event *event)
 
static uacpi_status set_gpe_state (struct gp_event *event, enum gpe_state state)
 
static uacpi_status clear_gpe (struct gp_event *event)
 
static uacpi_status restore_gpe (struct gp_event *event)
 
static void async_restore_gpe (uacpi_handle opaque)
 
static void async_run_gpe_handler (uacpi_handle opaque)
 
static uacpi_interrupt_ret dispatch_gpe (uacpi_namespace_node *device_node, struct gp_event *event)
 
static uacpi_interrupt_ret detect_gpes (struct gpe_block *block)
 
static uacpi_status maybe_dispatch_gpe (uacpi_namespace_node *gpe_device, struct gp_event *event)
 
static uacpi_interrupt_ret handle_gpes (uacpi_handle opaque)
 
static uacpi_status find_or_create_gpe_interrupt_ctx (uacpi_u32 irq, struct gpe_interrupt_ctx **out_ctx)
 
static void gpe_release_implicit_notify_handlers (struct gp_event *event)
 
static uacpi_status gpe_block_apply_action (struct gpe_block *block, enum gpe_block_action action)
 
static void gpe_block_mask_safe (struct gpe_block *block)
 
static void uninstall_gpe_block (struct gpe_block *block)
 
static struct gp_eventgpe_from_block (struct gpe_block *block, uacpi_u16 idx)
 
static uacpi_iteration_decision do_match_gpe_methods (uacpi_handle opaque, uacpi_namespace_node *node, uacpi_u32 depth)
 
void uacpi_events_match_post_dynamic_table_load (void)
 
static uacpi_status create_gpe_block (uacpi_namespace_node *device_node, uacpi_u32 irq, uacpi_u16 base_idx, uacpi_u64 address, uacpi_u8 address_space_id, uacpi_u16 num_registers)
 
static void for_each_gpe_block (gpe_block_iteration_callback cb, uacpi_handle handle)
 
static uacpi_iteration_decision do_find_gpe (struct gpe_block *block, uacpi_handle opaque)
 
static struct gp_eventget_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
static void gp_event_toggle_masks (struct gp_event *event, uacpi_bool set_on)
 
static uacpi_status gpe_remove_user (struct gp_event *event)
 
static uacpi_status gpe_add_user (struct gp_event *event, enum event_clear_if_first clear_if_first)
 
const uacpi_charuacpi_gpe_triggering_to_string (uacpi_gpe_triggering triggering)
 
static uacpi_bool gpe_needs_polling (struct gp_event *event)
 
static uacpi_status gpe_mask_unmask (struct gp_event *event, uacpi_bool should_mask)
 
static uacpi_bool gpe_mask_safe (struct gp_event *event)
 
static uacpi_iteration_decision do_initialize_gpe_block (struct gpe_block *block, uacpi_handle opaque)
 
uacpi_status uacpi_finalize_gpe_initialization (void)
 
static uacpi_status sanitize_device_and_find_gpe (uacpi_namespace_node **gpe_device, uacpi_u16 idx, struct gp_event **out_event)
 
static uacpi_status do_install_gpe_handler (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_gpe_triggering triggering, enum gpe_handler_type type, uacpi_gpe_handler handler, uacpi_handle ctx)
 
uacpi_status uacpi_install_gpe_handler (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_gpe_triggering triggering, uacpi_gpe_handler handler, uacpi_handle ctx)
 
uacpi_status uacpi_install_gpe_handler_raw (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_gpe_triggering triggering, uacpi_gpe_handler handler, uacpi_handle ctx)
 
uacpi_status uacpi_uninstall_gpe_handler (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_gpe_handler handler)
 
uacpi_status uacpi_enable_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_disable_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_clear_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
static uacpi_status gpe_suspend_resume (uacpi_namespace_node *gpe_device, uacpi_u16 idx, enum gpe_state state)
 
uacpi_status uacpi_suspend_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_resume_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_finish_handling_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
static uacpi_status gpe_get_mask_unmask (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_bool should_mask)
 
uacpi_status uacpi_mask_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_unmask_gpe (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_setup_gpe_for_wake (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_namespace_node *wake_device)
 
static uacpi_status gpe_enable_disable_for_wake (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_bool enabled)
 
uacpi_status uacpi_enable_gpe_for_wake (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
uacpi_status uacpi_disable_gpe_for_wake (uacpi_namespace_node *gpe_device, uacpi_u16 idx)
 
static uacpi_iteration_decision do_for_all_gpes (struct gpe_block *block, uacpi_handle opaque)
 
static uacpi_status for_all_gpes_locked (struct do_for_all_gpes_ctx *ctx)
 
uacpi_status uacpi_disable_all_gpes (void)
 
uacpi_status uacpi_enable_all_runtime_gpes (void)
 
uacpi_status uacpi_enable_all_wake_gpes (void)
 
static uacpi_status initialize_gpes (void)
 
uacpi_status uacpi_install_gpe_block (uacpi_namespace_node *gpe_device, uacpi_u64 address, uacpi_address_space address_space, uacpi_u16 num_registers, uacpi_u32 irq)
 
uacpi_status uacpi_uninstall_gpe_block (uacpi_namespace_node *gpe_device)
 
static uacpi_interrupt_ret handle_global_lock (uacpi_handle ctx)
 
static uacpi_interrupt_ret handle_sci (uacpi_handle ctx)
 
uacpi_status uacpi_initialize_events_early (void)
 
uacpi_status uacpi_initialize_events (void)
 
void uacpi_deinitialize_events (void)
 
uacpi_status uacpi_install_fixed_event_handler (uacpi_fixed_event event, uacpi_interrupt_handler handler, uacpi_handle user)
 
uacpi_status uacpi_uninstall_fixed_event_handler (uacpi_fixed_event event)
 
uacpi_status uacpi_fixed_event_info (uacpi_fixed_event event, uacpi_event_info *out_info)
 
uacpi_status uacpi_gpe_info (uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_event_info *out_info)
 
uacpi_status uacpi_clear_all_events (void)
 

Variables

static uacpi_handle g_gpe_state_slock
 
static struct uacpi_recursive_lock g_event_lock
 
static uacpi_bool g_gpes_finalized
 
static const struct fixed_event fixed_events [UACPI_FIXED_EVENT_MAX+1]
 
static struct fixed_event_handler fixed_event_handlers [UACPI_FIXED_EVENT_MAX+1]
 
static struct gpe_interrupt_ctxg_gpe_interrupt_head
 

Macro Definition Documentation

◆ EVENTS_PER_GPE_REGISTER

#define EVENTS_PER_GPE_REGISTER   8

Definition at line 246 of file event.c.

◆ PM1_STATUS_BITS

#define PM1_STATUS_BITS
Value:
( \
)
#define ACPI_PM1_STS_WAKE_STS_MASK
Definition: acpi.h:876
#define ACPI_PM1_STS_PCIEXP_WAKE_STS_MASK
Definition: acpi.h:875
#define ACPI_PM1_STS_SLPBTN_STS_MASK
Definition: acpi.h:872
#define ACPI_PM1_STS_RTC_STS_MASK
Definition: acpi.h:873
#define ACPI_PM1_STS_BM_STS_MASK
Definition: acpi.h:869
#define ACPI_PM1_STS_TMR_STS_MASK
Definition: acpi.h:868
#define ACPI_PM1_STS_PWRBTN_STS_MASK
Definition: acpi.h:871
#define ACPI_PM1_STS_GBL_STS_MASK
Definition: acpi.h:870

Definition at line 2464 of file event.c.

◆ UACPI_EVENT_DISABLED

#define UACPI_EVENT_DISABLED   0

Definition at line 14 of file event.c.

◆ UACPI_EVENT_ENABLED

#define UACPI_EVENT_ENABLED   1

Definition at line 15 of file event.c.

Typedef Documentation

◆ gpe_block_iteration_callback

typedef uacpi_iteration_decision(* gpe_block_iteration_callback) (struct gpe_block *, uacpi_handle)

Definition at line 1113 of file event.c.

Enumeration Type Documentation

◆ event_clear_if_first

Enumerator
EVENT_CLEAR_IF_FIRST_YES 
EVENT_CLEAR_IF_FIRST_NO 

Definition at line 1213 of file event.c.

1213 {
1216};
@ EVENT_CLEAR_IF_FIRST_YES
Definition: event.c:1214
@ EVENT_CLEAR_IF_FIRST_NO
Definition: event.c:1215

◆ gpe_block_action

Enumerator
GPE_BLOCK_ACTION_DISABLE_ALL 
GPE_BLOCK_ACTION_ENABLE_ALL_FOR_RUNTIME 
GPE_BLOCK_ACTION_ENABLE_ALL_FOR_WAKE 
GPE_BLOCK_ACTION_CLEAR_ALL 

Definition at line 692 of file event.c.

693{
698};
@ GPE_BLOCK_ACTION_ENABLE_ALL_FOR_WAKE
Definition: event.c:696
@ GPE_BLOCK_ACTION_ENABLE_ALL_FOR_RUNTIME
Definition: event.c:695
@ GPE_BLOCK_ACTION_DISABLE_ALL
Definition: event.c:694
@ GPE_BLOCK_ACTION_CLEAR_ALL
Definition: event.c:697

◆ gpe_handler_type

Enumerator
GPE_HANDLER_TYPE_NONE 
GPE_HANDLER_TYPE_AML_HANDLER 
GPE_HANDLER_TYPE_NATIVE_HANDLER 
GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW 
GPE_HANDLER_TYPE_IMPLICIT_NOTIFY 

Definition at line 255 of file event.c.

255 {
261};
@ GPE_HANDLER_TYPE_NATIVE_HANDLER
Definition: event.c:258
@ GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW
Definition: event.c:259
@ GPE_HANDLER_TYPE_IMPLICIT_NOTIFY
Definition: event.c:260
@ GPE_HANDLER_TYPE_NONE
Definition: event.c:256
@ GPE_HANDLER_TYPE_AML_HANDLER
Definition: event.c:257

◆ gpe_state

Enumerator
GPE_STATE_ENABLED 
GPE_STATE_ENABLED_CONDITIONALLY 
GPE_STATE_DISABLED 

Definition at line 329 of file event.c.

329 {
333};
@ GPE_STATE_ENABLED
Definition: event.c:330
@ GPE_STATE_ENABLED_CONDITIONALLY
Definition: event.c:331
@ GPE_STATE_DISABLED
Definition: event.c:332

Function Documentation

◆ async_restore_gpe()

static void async_restore_gpe ( uacpi_handle  opaque)
static

Definition at line 401 of file event.c.

402{
404 struct gp_event *event = opaque;
405
408 uacpi_error("unable to restore GPE(%02X): %s",
410 }
411}
#define uacpi_error(...)
Definition: log.h:36
#define uacpi_unlikely_error(expr)
Definition: status.h:49
uacpi_status
Definition: status.h:10
const uacpi_char * uacpi_status_to_string(uacpi_status)
Definition: uacpi.c:60
static uacpi_status restore_gpe(struct gp_event *event)
Definition: event.c:385
return ret
Definition: mutex.c:147
struct _cl_event * event
Definition: glext.h:7739

Referenced by async_run_gpe_handler().

◆ async_run_gpe_handler()

static void async_run_gpe_handler ( uacpi_handle  opaque)
static

Definition at line 413 of file event.c.

414{
416 struct gp_event *event = opaque;
417
420 goto out_no_unlock;
421
422 switch (event->handler_type) {
424 uacpi_object *method_obj;
426
428 event->aml_handler, UACPI_OBJECT_METHOD_BIT
429 );
430 if (uacpi_unlikely(method_obj == UACPI_NULL)) {
431 uacpi_error("GPE(%02X) AML handler gone", event->idx);
432 break;
433 }
434
435 name = uacpi_namespace_node_name(event->aml_handler);
437 "executing GPE(%02X) handler %.4s",
438 event->idx, name.text
439 );
440
442 event->aml_handler, method_obj->method, UACPI_NULL, UACPI_NULL
443 );
446 "error while executing GPE(%02X) handler %.4s: %s",
447 event->idx, event->aml_handler->name.text,
449 );
450 }
451 break;
452 }
453
456
457 handler = event->implicit_handler;
458 while (handler) {
459 /*
460 * 2 - Device Wake. Used to notify OSPM that the device has signaled
461 * its wake event, and that OSPM needs to notify OSPM native device
462 * driver for the device.
463 */
464 uacpi_notify_all(handler->device, 2);
465 handler = handler->next;
466 }
467 break;
468 }
469
470 default:
471 break;
472 }
473
475
476out_no_unlock:
477 /*
478 * We schedule the work as NOTIFICATION to make sure all other notifications
479 * finish before this GPE is re-enabled.
480 */
483 );
485 uacpi_error("unable to schedule GPE(%02X) restore: %s",
488 }
489}
UINT(* handler)(MSIPACKAGE *)
Definition: action.c:7512
#define uacpi_trace(...)
Definition: log.h:33
uacpi_status uacpi_namespace_write_unlock(void)
Definition: namespace.c:51
uacpi_object * uacpi_namespace_node_get_object_typed(const uacpi_namespace_node *node, uacpi_object_type_bits type_mask)
Definition: namespace.c:654
uacpi_status uacpi_namespace_write_lock(void)
Definition: namespace.c:46
uacpi_object_name uacpi_namespace_node_name(const uacpi_namespace_node *node)
Definition: namespace.c:752
#define uacpi_unlikely(expr)
Definition: compiler.h:88
#define UACPI_NULL
Definition: types.h:33
@ UACPI_OBJECT_METHOD_BIT
Definition: types.h:142
static void async_restore_gpe(uacpi_handle opaque)
Definition: event.c:401
uacpi_status uacpi_notify_all(uacpi_namespace_node *node, uacpi_u64 value)
Definition: notify.c:69
uacpi_status uacpi_execute_control_method(uacpi_namespace_node *scope, uacpi_control_method *method, const uacpi_object_array *args, uacpi_object **ret)
Definition: interpreter.c:6150
uacpi_status uacpi_kernel_schedule_work(uacpi_work_type, uacpi_work_handler, uacpi_handle ctx)
Definition: uacpiosl.c:228
@ UACPI_WORK_NOTIFICATION
Definition: kernel_api.h:368
Definition: name.c:39
uacpi_control_method * method
Definition: types.h:257

Referenced by dispatch_gpe().

◆ clear_gpe()

static uacpi_status clear_gpe ( struct gp_event event)
static

Definition at line 378 of file event.c.

379{
380 struct gpe_register *reg = event->reg;
381
382 return uacpi_gas_write_mapped(&reg->status, gpe_get_mask(event));
383}
uacpi_status uacpi_gas_write_mapped(const uacpi_mapped_gas *gas, uacpi_u64 value)
Definition: io.c:885
static uacpi_u8 gpe_get_mask(struct gp_event *event)
Definition: event.c:324
static int reg
Definition: i386-dis.c:1290

Referenced by dispatch_gpe(), gpe_add_user(), restore_gpe(), and uacpi_clear_gpe().

◆ create_gpe_block()

static uacpi_status create_gpe_block ( uacpi_namespace_node device_node,
uacpi_u32  irq,
uacpi_u16  base_idx,
uacpi_u64  address,
uacpi_u8  address_space_id,
uacpi_u16  num_registers 
)
static

Definition at line 1012 of file event.c.

1016{
1018 struct gpe_match_ctx match_ctx = { 0 };
1019 struct gpe_block *block;
1020 struct gpe_register *reg;
1021 struct gp_event *event;
1022 struct acpi_gas tmp_gas = { 0 };
1023 uacpi_size i, j;
1024
1025 tmp_gas.address_space_id = address_space_id;
1026 tmp_gas.register_bit_width = 8;
1027
1030 return ret;
1031
1032 block->device_node = device_node;
1033 block->base_idx = base_idx;
1034
1035 block->num_registers = num_registers;
1036 block->registers = uacpi_kernel_alloc_zeroed(
1037 num_registers * sizeof(*block->registers)
1038 );
1039 if (uacpi_unlikely(block->registers == UACPI_NULL))
1040 goto error_out;
1041
1044 block->num_events * sizeof(*block->events)
1045 );
1046 if (uacpi_unlikely(block->events == UACPI_NULL))
1047 goto error_out;
1048
1049 for (reg = block->registers, event = block->events, i = 0;
1050 i < num_registers; ++i, ++reg) {
1051
1052 /*
1053 * Initialize this register pair as well as all the events within it.
1054 *
1055 * Each register has two sub registers: status & enable, 8 bits each.
1056 * Each bit corresponds to one event that we initialize below.
1057 */
1058 reg->base_idx = base_idx + (i * EVENTS_PER_GPE_REGISTER);
1059
1060
1061 tmp_gas.address = address + i;
1062 ret = uacpi_map_gas_noalloc(&tmp_gas, &reg->status);
1064 goto error_out;
1065
1066 tmp_gas.address += num_registers;
1067 ret = uacpi_map_gas_noalloc(&tmp_gas, &reg->enable);
1069 goto error_out;
1070
1071 for (j = 0; j < EVENTS_PER_GPE_REGISTER; ++j, ++event) {
1072 event->idx = reg->base_idx + j;
1073 event->reg = reg;
1074 }
1075
1076 /*
1077 * Disable all GPEs in this register & clear anything that might be
1078 * pending from earlier.
1079 */
1080 ret = uacpi_gas_write_mapped(&reg->enable, 0x00);
1082 goto error_out;
1083
1084 ret = uacpi_gas_write_mapped(&reg->status, 0xFF);
1086 goto error_out;
1087 }
1088
1091 goto error_out;
1092
1093 block->next = block->irq_ctx->gpe_head;
1094 block->irq_ctx->gpe_head = block;
1095 match_ctx.block = block;
1096
1098 device_node, do_match_gpe_methods, UACPI_NULL,
1101 );
1102
1103 uacpi_trace("initialized GPE block %.4s[%d->%d], %d AML handlers (IRQ %d)",
1104 device_node->name.text, base_idx, base_idx + block->num_events,
1105 match_ctx.matched_count, irq);
1106 return UACPI_STATUS_OK;
1107
1108error_out:
1110 return ret;
1111}
uacpi_u16 uacpi_gpe_triggering uacpi_gpe_handler uacpi_handle ctx uacpi_u16 uacpi_namespace_node *wake_device uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u64 uacpi_address_space uacpi_u16 num_registers
Definition: event.h:273
uacpi_status uacpi_map_gas_noalloc(const struct acpi_gas *gas, uacpi_mapped_gas *out_mapped)
Definition: io.c:927
uacpi_status uacpi_namespace_do_for_each_child(uacpi_namespace_node *parent, uacpi_iteration_callback descending_callback, uacpi_iteration_callback ascending_callback, uacpi_object_type_bits, uacpi_u32 max_depth, enum uacpi_should_lock, enum uacpi_permanent_only, void *user)
Definition: namespace.c:834
@ UACPI_PERMANENT_ONLY_YES
Definition: namespace.h:90
@ UACPI_SHOULD_LOCK_YES
Definition: namespace.h:95
#define uacpi_kernel_alloc_zeroed
Definition: stdlib.h:127
#define UACPI_MAX_DEPTH_ANY
Definition: namespace.h:102
size_t uacpi_size
Definition: types.h:37
@ UACPI_STATUS_OUT_OF_MEMORY
Definition: status.h:13
@ UACPI_STATUS_OK
Definition: status.h:11
static uacpi_status find_or_create_gpe_interrupt_ctx(uacpi_u32 irq, struct gpe_interrupt_ctx **out_ctx)
Definition: event.c:636
static uacpi_iteration_decision do_match_gpe_methods(uacpi_handle opaque, uacpi_namespace_node *node, uacpi_u32 depth)
Definition: event.c:891
static void uninstall_gpe_block(struct gpe_block *block)
Definition: event.c:778
#define EVENTS_PER_GPE_REGISTER
Definition: event.c:246
unsigned char irq
Definition: dsp.h:13
GLuint address
Definition: glext.h:9393
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
uacpi_u32 matched_count
Definition: event.c:887
struct gpe_block * block
Definition: event.c:886
uacpi_object_name name
Definition: namespace.h:29
uacpi_char text[4]
Definition: types.h:24
static unsigned int block
Definition: xmlmemory.c:101

Referenced by initialize_gpes(), and uacpi_install_gpe_block().

◆ detect_gpes()

static uacpi_interrupt_ret detect_gpes ( struct gpe_block block)
static

Definition at line 565 of file event.c.

566{
569 struct gpe_register *reg;
570 struct gp_event *event;
572 uacpi_size i, j;
573
574 while (block) {
575 for (i = 0; i < block->num_registers; ++i) {
576 reg = &block->registers[i];
577
578 if (!reg->runtime_mask && !reg->wake_mask)
579 continue;
580
581 ret = uacpi_gas_read_mapped(&reg->status, &status);
583 return int_ret;
584
585 ret = uacpi_gas_read_mapped(&reg->enable, &enable);
587 return int_ret;
588
589 if (status == 0)
590 continue;
591
592 for (j = 0; j < EVENTS_PER_GPE_REGISTER; ++j) {
593 if (!((status & enable) & (1ull << j)))
594 continue;
595
596 event = &block->events[j + i * EVENTS_PER_GPE_REGISTER];
597 int_ret |= dispatch_gpe(block->device_node, event);
598 }
599 }
600
601 block = block->next;
602 }
603
604 return int_ret;
605}
uacpi_status uacpi_gas_read_mapped(const uacpi_mapped_gas *gas, uacpi_u64 *value)
Definition: io.c:846
uint64_t uacpi_u64
Definition: types.h:22
uacpi_u32 uacpi_interrupt_ret
Definition: types.h:542
#define UACPI_INTERRUPT_NOT_HANDLED
Definition: types.h:540
static uacpi_interrupt_ret dispatch_gpe(uacpi_namespace_node *device_node, struct gp_event *event)
Definition: event.c:491
GLboolean enable
Definition: glext.h:11120
Definition: ps.c:97

Referenced by handle_gpes(), and uacpi_finalize_gpe_initialization().

◆ dispatch_fixed_event()

static uacpi_interrupt_ret dispatch_fixed_event ( const struct fixed_event ev,
uacpi_fixed_event  event 
)
static

Definition at line 175 of file event.c.

178{
181
185
186 if (uacpi_unlikely(evh->handler == UACPI_NULL)) {
188 "fixed event %d fired but no handler installed, disabling...",
189 event
190 );
193 }
194
195 return evh->handler(evh->ctx);
196}
#define ACPI_PM1_STS_CLEAR
Definition: acpi.h:878
#define uacpi_warn(...)
Definition: log.h:35
uacpi_status uacpi_write_register_field(uacpi_register_field, uacpi_u64)
Definition: registers.c:518
static struct fixed_event_handler fixed_event_handlers[UACPI_FIXED_EVENT_MAX+1]
Definition: event.c:68
#define UACPI_EVENT_DISABLED
Definition: event.c:14
uacpi_handle ctx
Definition: event.c:32
uacpi_interrupt_handler handler
Definition: event.c:31
uacpi_u8 enable_field
Definition: event.c:24
uacpi_u8 status_field
Definition: event.c:25

Referenced by handle_fixed_events().

◆ dispatch_gpe()

static uacpi_interrupt_ret dispatch_gpe ( uacpi_namespace_node device_node,
struct gp_event event 
)
static

Definition at line 491 of file event.c.

494{
497
498 /*
499 * For raw handlers we don't do any management whatsoever, we just let the
500 * handler know a GPE has triggered and let it handle disable/enable as
501 * well as clearing.
502 */
503 if (event->handler_type == GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW) {
504 return event->native_handler->cb(
505 event->native_handler->ctx, device_node, event->idx
506 );
507 }
508
511 uacpi_error("failed to disable GPE(%02X): %s",
513 return int_ret;
514 }
515
516 event->block_interrupts = UACPI_TRUE;
517
518 if (event->triggering == UACPI_GPE_TRIGGERING_EDGE) {
521 uacpi_error("unable to clear GPE(%02X): %s",
524 return int_ret;
525 }
526 }
527
528 switch (event->handler_type) {
530 int_ret = event->native_handler->cb(
531 event->native_handler->ctx, device_node, event->idx
532 );
533 if (!(int_ret & UACPI_GPE_REENABLE))
534 break;
535
538 uacpi_error("unable to restore GPE(%02X): %s",
540 }
541 break;
542
547 );
550 "unable to schedule GPE(%02X) for execution: %s",
552 );
553 }
554 break;
555
556 default:
557 uacpi_warn("GPE(%02X) fired but no handler, keeping disabled",
558 event->idx);
559 break;
560 }
561
563}
#define UACPI_GPE_REENABLE
Definition: event.h:77
@ UACPI_GPE_TRIGGERING_EDGE
Definition: event.h:85
#define UACPI_TRUE
Definition: types.h:29
#define UACPI_INTERRUPT_HANDLED
Definition: types.h:541
static uacpi_status set_gpe_state(struct gp_event *event, enum gpe_state state)
Definition: event.c:335
static void async_run_gpe_handler(uacpi_handle opaque)
Definition: event.c:413
static uacpi_status clear_gpe(struct gp_event *event)
Definition: event.c:378
@ UACPI_WORK_GPE_EXECUTION
Definition: kernel_api.h:362

Referenced by detect_gpes(), and maybe_dispatch_gpe().

◆ do_find_gpe()

static uacpi_iteration_decision do_find_gpe ( struct gpe_block block,
uacpi_handle  opaque 
)
static

Definition at line 1146 of file event.c.

1149{
1150 struct gpe_search_ctx *ctx = opaque;
1151
1152 if (block->device_node != ctx->gpe_device)
1154
1155 ctx->out_block = block;
1156 ctx->out_event = gpe_from_block(block, ctx->idx);
1157 if (ctx->out_event == UACPI_NULL)
1159
1161}
@ UACPI_ITERATION_DECISION_BREAK
Definition: types.h:30
@ UACPI_ITERATION_DECISION_CONTINUE
Definition: types.h:29
static struct gp_event * gpe_from_block(struct gpe_block *block, uacpi_u16 idx)
Definition: event.c:871

Referenced by get_gpe(), and uacpi_uninstall_gpe_block().

◆ do_for_all_gpes()

static uacpi_iteration_decision do_for_all_gpes ( struct gpe_block block,
uacpi_handle  opaque 
)
static

Definition at line 1950 of file event.c.

1953{
1954 struct do_for_all_gpes_ctx *ctx = opaque;
1955
1956 ctx->ret = gpe_block_apply_action(block, ctx->action);
1957 if (uacpi_unlikely_error(ctx->ret))
1959
1961}
static uacpi_status gpe_block_apply_action(struct gpe_block *block, enum gpe_block_action action)
Definition: event.c:700

Referenced by for_all_gpes_locked(), and uacpi_clear_all_events().

◆ do_initialize_gpe_block()

static uacpi_iteration_decision do_initialize_gpe_block ( struct gpe_block block,
uacpi_handle  opaque 
)
static

Definition at line 1328 of file event.c.

1331{
1333 uacpi_bool *poll_blocks = opaque;
1334 uacpi_size i, j, count_enabled = 0;
1335 struct gp_event *event;
1336
1337 for (i = 0; i < block->num_registers; ++i) {
1338 for (j = 0; j < EVENTS_PER_GPE_REGISTER; ++j) {
1339 event = &block->events[j + i * EVENTS_PER_GPE_REGISTER];
1340
1341 if (event->wake ||
1342 event->handler_type != GPE_HANDLER_TYPE_AML_HANDLER)
1343 continue;
1344
1347 uacpi_warn("failed to enable GPE(%02X): %s",
1349 continue;
1350 }
1351
1352 *poll_blocks |= gpe_needs_polling(event);
1353 count_enabled++;
1354 }
1355 }
1356
1357 if (count_enabled) {
1358 uacpi_info(
1359 "enabled %zu GPEs in block %.4s@[%d->%d]",
1360 count_enabled, block->device_node->name.text,
1361 block->base_idx, block->base_idx + block->num_events
1362 );
1363 }
1365}
#define uacpi_info(...)
Definition: log.h:34
bool uacpi_bool
Definition: types.h:31
static uacpi_status gpe_add_user(struct gp_event *event, enum event_clear_if_first clear_if_first)
Definition: event.c:1218
static uacpi_bool gpe_needs_polling(struct gp_event *event)
Definition: event.c:1257

Referenced by uacpi_finalize_gpe_initialization().

◆ do_install_gpe_handler()

static uacpi_status do_install_gpe_handler ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_gpe_triggering  triggering,
enum gpe_handler_type  type,
uacpi_gpe_handler  handler,
uacpi_handle  ctx 
)
static

Definition at line 1413 of file event.c.

1418{
1420 struct gp_event *event;
1421 struct gpe_native_handler *native_handler;
1422 uacpi_bool did_mask;
1423
1425
1428
1431
1434 return ret;
1435
1436 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1438 goto out;
1439
1440 if (event->handler_type == GPE_HANDLER_TYPE_NATIVE_HANDLER ||
1441 event->handler_type == GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW) {
1443 goto out;
1444 }
1445
1446 native_handler = uacpi_kernel_alloc(sizeof(*native_handler));
1447 if (uacpi_unlikely(native_handler == UACPI_NULL)) {
1449 goto out;
1450 }
1451
1452 native_handler->cb = handler;
1453 native_handler->ctx = ctx;
1454 native_handler->previous_handler = event->any_handler;
1455 native_handler->previous_handler_type = event->handler_type;
1456 native_handler->previous_triggering = event->triggering;
1457 native_handler->previously_enabled = UACPI_FALSE;
1458
1459 did_mask = gpe_mask_safe(event);
1460
1461 if ((event->handler_type == GPE_HANDLER_TYPE_AML_HANDLER ||
1462 event->handler_type == GPE_HANDLER_TYPE_IMPLICIT_NOTIFY) &&
1463 event->num_users != 0) {
1464 native_handler->previously_enabled = UACPI_TRUE;
1466
1467 if (uacpi_unlikely(event->triggering != triggering)) {
1468 uacpi_warn(
1469 "GPE(%02X) user handler claims %s triggering, originally "
1470 "configured as %s", idx,
1473 );
1474 }
1475 }
1476
1477 event->native_handler = native_handler;
1478 event->handler_type = type;
1479 event->triggering = triggering;
1480
1481 if (did_mask)
1483out:
1485 return ret;
1486}
uacpi_status uacpi_recursive_lock_acquire(struct uacpi_recursive_lock *lock)
Definition: mutex.c:288
uacpi_status uacpi_recursive_lock_release(struct uacpi_recursive_lock *lock)
Definition: mutex.c:308
unsigned int idx
Definition: utils.c:41
@ UACPI_GPE_TRIGGERING_MAX
Definition: event.h:86
uacpi_u16 uacpi_gpe_triggering triggering
Definition: event.h:117
#define UACPI_ENSURE_INIT_LEVEL_AT_LEAST(lvl)
Definition: context.h:127
static uacpi_bool uacpi_is_hardware_reduced(void)
Definition: context.h:100
#define UACPI_FALSE
Definition: types.h:30
@ UACPI_STATUS_INVALID_ARGUMENT
Definition: status.h:18
@ UACPI_STATUS_NOT_FOUND
Definition: status.h:17
@ UACPI_STATUS_ALREADY_EXISTS
Definition: status.h:20
@ UACPI_INIT_LEVEL_NAMESPACE_LOADED
Definition: types.h:78
const uacpi_char * uacpi_gpe_triggering_to_string(uacpi_gpe_triggering triggering)
Definition: event.c:1243
static struct uacpi_recursive_lock g_event_lock
Definition: event.c:20
static uacpi_status sanitize_device_and_find_gpe(uacpi_namespace_node **gpe_device, uacpi_u16 idx, struct gp_event **out_event)
Definition: event.c:1395
static uacpi_bool gpe_mask_safe(struct gp_event *event)
Definition: event.c:1318
static uacpi_status gpe_mask_unmask(struct gp_event *event, uacpi_bool should_mask)
Definition: event.c:1262
static uacpi_status gpe_remove_user(struct gp_event *event)
Definition: event.c:1193
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
void * uacpi_kernel_alloc(uacpi_size size)
Definition: uacpiosl.c:111
uacpi_gpe_handler cb
Definition: event.c:228
uacpi_u8 previously_enabled
Definition: event.c:238
uacpi_u8 previous_triggering
Definition: event.c:236
uacpi_handle ctx
Definition: event.c:229
uacpi_handle previous_handler
Definition: event.c:235
uacpi_u8 previous_handler_type
Definition: event.c:237
wchar_t tm const _CrtWcstime_Writes_and_advances_ptr_ count wchar_t ** out
Definition: wcsftime.cpp:383

Referenced by uacpi_install_gpe_handler(), and uacpi_install_gpe_handler_raw().

◆ do_match_gpe_methods()

static uacpi_iteration_decision do_match_gpe_methods ( uacpi_handle  opaque,
uacpi_namespace_node node,
uacpi_u32  depth 
)
static

Definition at line 891 of file event.c.

894{
896 struct gpe_match_ctx *ctx = opaque;
897 struct gp_event *event;
900
902
903 if (node->name.text[0] != '_')
905
906 switch (node->name.text[1]) {
907 case 'L':
909 break;
910 case 'E':
912 break;
913 default:
915 }
916
917 ret = uacpi_string_to_integer(&node->name.text[2], 2, UACPI_BASE_HEX, &idx);
919 uacpi_trace("invalid GPE method name %.4s, ignored", node->name.text);
921 }
922
923 event = gpe_from_block(ctx->block, idx);
924 if (event == UACPI_NULL)
926
927 switch (event->handler_type) {
928 /*
929 * This had implicit notify configured but this is no longer needed as we
930 * now have an actual AML handler. Free the implicit notify list and switch
931 * this handler to AML mode.
932 */
937 event->aml_handler = node;
938 event->handler_type = GPE_HANDLER_TYPE_AML_HANDLER;
939 break;
940
942 // This is okay, since we're re-running the detection code
943 if (!ctx->post_dynamic_table_load) {
945 "GPE(%02X) already matched %.4s, skipping %.4s",
946 (uacpi_u32)idx, event->aml_handler->name.text, node->name.text
947 );
948 }
950
954 "not assigning GPE(%02X) to %.4s, override "
955 "installed by user", (uacpi_u32)idx, node->name.text
956 );
958 default:
960 }
961
962 uacpi_trace("assigned GPE(%02X) -> %.4s",
963 (uacpi_u32)idx, node->name.text);
964 event->triggering = triggering;
965 ctx->matched_count++;
966
968}
@ UACPI_GPE_TRIGGERING_LEVEL
Definition: event.h:84
#define UACPI_UNUSED(x)
Definition: helpers.h:7
#define UACPI_FALLTHROUGH
Definition: compiler.h:100
uint32_t uacpi_u32
Definition: types.h:21
uint8_t uacpi_u8
Definition: types.h:19
static void gpe_release_implicit_notify_handlers(struct gp_event *event)
Definition: event.c:678
GLint GLint GLsizei GLsizei GLsizei depth
Definition: gl.h:1546
uacpi_status uacpi_string_to_integer(const uacpi_char *str, uacpi_size max_chars, enum uacpi_base base, uacpi_u64 *out_value)
Definition: utilities.c:233
@ UACPI_BASE_HEX
Definition: utilities.h:34
Definition: dlist.c:348

Referenced by create_gpe_block(), and uacpi_events_match_post_dynamic_table_load().

◆ find_or_create_gpe_interrupt_ctx()

static uacpi_status find_or_create_gpe_interrupt_ctx ( uacpi_u32  irq,
struct gpe_interrupt_ctx **  out_ctx 
)
static

Definition at line 636 of file event.c.

639{
642
643 while (entry) {
644 if (entry->irq == irq) {
645 *out_ctx = entry;
646 return UACPI_STATUS_OK;
647 }
648
649 entry = entry->next;
650 }
651
655
656 /*
657 * SCI interrupt is installed by other code and is responsible for more
658 * things than just the GPE handling. Don't install it here.
659 */
660 if (irq != g_uacpi_rt_ctx.fadt.sci_int) {
662 irq, handle_gpes, entry, &entry->irq_handle
663 );
665 uacpi_free(entry, sizeof(*entry));
666 return ret;
667 }
668 }
669
670 entry->irq = irq;
673
674 *out_ctx = entry;
675 return UACPI_STATUS_OK;
676}
struct uacpi_runtime_context g_uacpi_rt_ctx
Definition: uacpi.c:17
#define uacpi_free(mem, _)
Definition: stdlib.h:96
static struct gpe_interrupt_ctx * g_gpe_interrupt_head
Definition: event.c:322
static uacpi_interrupt_ret handle_gpes(uacpi_handle opaque)
Definition: event.c:626
uint32_t entry
Definition: isohybrid.c:63
uacpi_status uacpi_kernel_install_interrupt_handler(uacpi_u32 irq, uacpi_interrupt_handler, uacpi_handle ctx, uacpi_handle *out_irq_handle)
Definition: uacpiosl.c:212

Referenced by create_gpe_block().

◆ for_all_gpes_locked()

static uacpi_status for_all_gpes_locked ( struct do_for_all_gpes_ctx ctx)
static

Definition at line 1963 of file event.c.

1964{
1966
1968
1971
1974 return ret;
1975
1977
1979 return ctx->ret;
1980}
static void for_each_gpe_block(gpe_block_iteration_callback cb, uacpi_handle handle)
Definition: event.c:1116
static uacpi_iteration_decision do_for_all_gpes(struct gpe_block *block, uacpi_handle opaque)
Definition: event.c:1950

Referenced by uacpi_disable_all_gpes(), uacpi_enable_all_runtime_gpes(), and uacpi_enable_all_wake_gpes().

◆ for_each_gpe_block()

static void for_each_gpe_block ( gpe_block_iteration_callback  cb,
uacpi_handle  handle 
)
static

Definition at line 1116 of file event.c.

1119{
1120 uacpi_iteration_decision decision;
1121 struct gpe_interrupt_ctx *irq_ctx = g_gpe_interrupt_head;
1122 struct gpe_block *block;
1123
1124 while (irq_ctx) {
1125 block = irq_ctx->gpe_head;
1126
1127 while (block) {
1128 decision = cb(block, handle);
1129 if (decision == UACPI_ITERATION_DECISION_BREAK)
1130 return;
1131
1132 block = block->next;
1133 }
1134
1135 irq_ctx = irq_ctx->next;
1136 }
1137}
static MonoProfilerRuntimeShutdownBeginCallback cb
Definition: metahost.c:118
uacpi_iteration_decision
Definition: types.h:28
struct gpe_interrupt_ctx * irq_ctx
Definition: event.c:308

Referenced by for_all_gpes_locked(), get_gpe(), uacpi_clear_all_events(), uacpi_finalize_gpe_initialization(), and uacpi_uninstall_gpe_block().

◆ get_gpe()

static struct gp_event * get_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)
static

Definition at line 1163 of file event.c.

1166{
1167 struct gpe_search_ctx ctx = { 0 };
1168
1169 ctx.gpe_device = gpe_device;
1170 ctx.idx = idx;
1171
1173 return ctx.out_event;
1174}
static uacpi_iteration_decision do_find_gpe(struct gpe_block *block, uacpi_handle opaque)
Definition: event.c:1146
uacpi_namespace_node * gpe_device
Definition: event.c:1140

Referenced by sanitize_device_and_find_gpe(), uacpi_finish_handling_gpe(), and uacpi_install_gpe_block().

◆ gp_event_toggle_masks()

static void gp_event_toggle_masks ( struct gp_event event,
uacpi_bool  set_on 
)
static

Definition at line 1176 of file event.c.

1177{
1178 uacpi_u8 this_mask;
1179 struct gpe_register *reg = event->reg;
1180
1181 this_mask = gpe_get_mask(event);
1182
1183 if (set_on) {
1184 reg->runtime_mask |= this_mask;
1185 reg->current_mask = reg->runtime_mask;
1186 return;
1187 }
1188
1189 reg->runtime_mask &= ~this_mask;
1190 reg->current_mask = reg->runtime_mask;
1191}

Referenced by gpe_add_user(), and gpe_remove_user().

◆ gpe_add_user()

static uacpi_status gpe_add_user ( struct gp_event event,
enum event_clear_if_first  clear_if_first 
)
static

Definition at line 1218 of file event.c.

1221{
1223
1224 if (uacpi_unlikely(event->num_users == 0xFF))
1226
1227 if (++event->num_users == 1) {
1228 if (clear_if_first == EVENT_CLEAR_IF_FIRST_YES)
1230
1232
1236 event->num_users--;
1237 }
1238 }
1239
1240 return ret;
1241}
static void gp_event_toggle_masks(struct gp_event *event, uacpi_bool set_on)
Definition: event.c:1176

Referenced by do_initialize_gpe_block(), uacpi_enable_gpe(), and uacpi_uninstall_gpe_handler().

◆ gpe_block_apply_action()

static uacpi_status gpe_block_apply_action ( struct gpe_block block,
enum gpe_block_action  action 
)
static

Definition at line 700 of file event.c.

703{
707 struct gpe_register *reg;
708
709 for (i = 0; i < block->num_registers; ++i) {
710 reg = &block->registers[i];
711
712 switch (action) {
714 value = 0;
715 break;
717 value = reg->runtime_mask & ~reg->masked_mask;
718 break;
720 value = reg->wake_mask;
721 break;
723 ret = uacpi_gas_write_mapped(&reg->status, 0xFF);
725 return ret;
726 continue;
727 default:
729 }
730
731 reg->current_mask = value;
732 ret = uacpi_gas_write_mapped(&reg->enable, value);
734 return ret;
735 }
736
737 return UACPI_STATUS_OK;
738}
action
Definition: namespace.c:707
Definition: pdh_main.c:96

Referenced by do_for_all_gpes().

◆ gpe_block_mask_safe()

static void gpe_block_mask_safe ( struct gpe_block block)
static

Definition at line 740 of file event.c.

741{
743 struct gpe_register *reg;
744
745 for (i = 0; i < block->num_registers; ++i) {
746 reg = &block->registers[i];
747
748 // No need to flush or do anything if it's not currently enabled
749 if (!reg->current_mask)
750 continue;
751
752 // 1. Mask the GPEs, this makes sure their state is no longer modifyable
753 reg->masked_mask = 0xFF;
754
755 /*
756 * 2. Wait for in-flight work & IRQs to finish, these might already
757 * be past the respective "if (masked)" check and therefore may
758 * try to re-enable a masked GPE.
759 */
761
762 /*
763 * 3. Now that this GPE's state is unmodifyable and we know that
764 * currently in-flight IRQs will see the masked state, we can
765 * safely disable all events knowing they won't be re-enabled by
766 * a racing IRQ.
767 */
768 uacpi_gas_write_mapped(&reg->enable, 0x00);
769
770 /*
771 * 4. Wait for the last possible IRQ to finish, now that this event is
772 * disabled.
773 */
775 }
776}
uacpi_status uacpi_kernel_wait_for_work_completion(void)
Definition: uacpiosl.c:235

Referenced by uninstall_gpe_block().

◆ gpe_enable_disable_for_wake()

static uacpi_status gpe_enable_disable_for_wake ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_bool  enabled 
)
static

Definition at line 1891 of file event.c.

1894{
1896 struct gp_event *event;
1897 struct gpe_register *reg;
1898 uacpi_u8 mask;
1899
1901
1904
1907 return ret;
1908
1909 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1911 goto out;
1912
1913 if (!event->wake) {
1915 goto out;
1916 }
1917
1918 reg = event->reg;
1920
1921 if (enabled)
1922 reg->wake_mask |= mask;
1923 else
1924 reg->wake_mask &= mask;
1925
1926out:
1928 return ret;
1929}
GLenum GLenum GLsizei const GLuint GLboolean enabled
Definition: glext.h:7750
GLenum GLint GLuint mask
Definition: glext.h:6028

Referenced by uacpi_disable_gpe_for_wake(), and uacpi_enable_gpe_for_wake().

◆ gpe_from_block()

static struct gp_event * gpe_from_block ( struct gpe_block block,
uacpi_u16  idx 
)
static

Definition at line 871 of file event.c.

872{
874
875 if (idx < block->base_idx)
876 return UACPI_NULL;
877
878 offset = idx - block->base_idx;
879 if (offset > block->num_events)
880 return UACPI_NULL;
881
882 return &block->events[offset];
883}
uint16_t uacpi_u16
Definition: types.h:20
GLintptr offset
Definition: glext.h:5920

Referenced by do_find_gpe(), and do_match_gpe_methods().

◆ gpe_get_mask()

static uacpi_u8 gpe_get_mask ( struct gp_event event)
static

Definition at line 324 of file event.c.

325{
326 return 1 << (event->idx - event->reg->base_idx);
327}

Referenced by clear_gpe(), gp_event_toggle_masks(), gpe_enable_disable_for_wake(), gpe_mask_safe(), gpe_mask_unmask(), maybe_dispatch_gpe(), set_gpe_state(), and uacpi_gpe_info().

◆ gpe_get_mask_unmask()

static uacpi_status gpe_get_mask_unmask ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_bool  should_mask 
)
static

Definition at line 1734 of file event.c.

1737{
1739 struct gp_event *event;
1740
1742
1745
1748 return ret;
1749
1750 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1752 goto out;
1753
1754 ret = gpe_mask_unmask(event, should_mask);
1755
1756out:
1758 return ret;
1759}

Referenced by uacpi_mask_gpe(), and uacpi_unmask_gpe().

◆ gpe_mask_safe()

static uacpi_bool gpe_mask_safe ( struct gp_event event)
static

Definition at line 1318 of file event.c.

1319{
1320 // No need to flush or do anything if it's not currently enabled
1321 if (!(event->reg->current_mask & gpe_get_mask(event)))
1322 return UACPI_FALSE;
1323
1325 return UACPI_TRUE;
1326}

Referenced by do_install_gpe_handler(), uacpi_setup_gpe_for_wake(), and uacpi_uninstall_gpe_handler().

◆ gpe_mask_unmask()

static uacpi_status gpe_mask_unmask ( struct gp_event event,
uacpi_bool  should_mask 
)
static

Definition at line 1262 of file event.c.

1265{
1266 struct gpe_register *reg;
1267 uacpi_u8 mask;
1268
1269 reg = event->reg;
1271
1272 if (should_mask) {
1273 if (reg->masked_mask & mask)
1275
1276 // 1. Mask the GPE, this makes sure its state is no longer modifyable
1277 reg->masked_mask |= mask;
1278
1279 /*
1280 * 2. Wait for in-flight work & IRQs to finish, these might already
1281 * be past the respective "if (masked)" check and therefore may
1282 * try to re-enable a masked GPE.
1283 */
1285
1286 /*
1287 * 3. Now that this GPE's state is unmodifyable and we know that currently
1288 * in-flight IRQs will see the masked state, we can safely disable this
1289 * event knowing it won't be re-enabled by a racing IRQ.
1290 */
1292
1293 /*
1294 * 4. Wait for the last possible IRQ to finish, now that this event is
1295 * disabled.
1296 */
1298
1299 return UACPI_STATUS_OK;
1300 }
1301
1302 if (!(reg->masked_mask & mask))
1304
1305 reg->masked_mask &= ~mask;
1306 if (!event->block_interrupts && event->num_users)
1308
1309 return UACPI_STATUS_OK;
1310}

Referenced by do_install_gpe_handler(), gpe_get_mask_unmask(), gpe_mask_safe(), uacpi_setup_gpe_for_wake(), and uacpi_uninstall_gpe_handler().

◆ gpe_needs_polling()

static uacpi_bool gpe_needs_polling ( struct gp_event event)
static

Definition at line 1257 of file event.c.

1258{
1259 return event->num_users && event->triggering == UACPI_GPE_TRIGGERING_EDGE;
1260}

Referenced by do_initialize_gpe_block(), uacpi_enable_gpe(), and uacpi_uninstall_gpe_handler().

◆ gpe_release_implicit_notify_handlers()

static void gpe_release_implicit_notify_handlers ( struct gp_event event)
static

Definition at line 678 of file event.c.

679{
680 struct gpe_implicit_notify_handler *handler, *next_handler;
681
682 handler = event->implicit_handler;
683 while (handler) {
684 next_handler = handler->next;
685 uacpi_free(handler, sizeof(*handler));
686 handler = next_handler;
687 }
688
689 event->implicit_handler = UACPI_NULL;
690}

Referenced by do_match_gpe_methods(), and uninstall_gpe_block().

◆ gpe_remove_user()

static uacpi_status gpe_remove_user ( struct gp_event event)
static

Definition at line 1193 of file event.c.

1194{
1196
1197 if (uacpi_unlikely(event->num_users == 0))
1199
1200 if (--event->num_users == 0) {
1202
1206 event->num_users++;
1207 }
1208 }
1209
1210 return ret;
1211}

Referenced by do_install_gpe_handler(), uacpi_disable_gpe(), and uacpi_setup_gpe_for_wake().

◆ gpe_suspend_resume()

static uacpi_status gpe_suspend_resume ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
enum gpe_state  state 
)
static

Definition at line 1660 of file event.c.

1663{
1665 struct gp_event *event;
1666
1668
1671
1674 return ret;
1675
1676 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1678 goto out;
1679
1680 event->block_interrupts = state == GPE_STATE_DISABLED;
1682out:
1684 return ret;
1685}
static int state
Definition: maze.c:121

Referenced by uacpi_resume_gpe(), and uacpi_suspend_gpe().

◆ handle_fixed_events()

static uacpi_interrupt_ret handle_fixed_events ( void  )
static

Definition at line 198 of file event.c.

199{
202 uacpi_u64 enable_mask, status_mask;
204
207 return int_ret;
208
211 return int_ret;
212
213 for (i = 0; i < UACPI_FIXED_EVENT_MAX; ++i)
214 {
215 const struct fixed_event *ev = &fixed_events[i];
216
217 if (!(status_mask & ev->status_mask) ||
218 !(enable_mask & ev->enable_mask))
219 continue;
220
221 int_ret |= dispatch_fixed_event(ev, i);
222 }
223
224 return int_ret;
225}
@ UACPI_FIXED_EVENT_MAX
Definition: event.h:17
uacpi_status uacpi_read_register(uacpi_register, uacpi_u64 *)
Definition: registers.c:227
@ UACPI_REGISTER_PM1_EN
Definition: registers.h:18
@ UACPI_REGISTER_PM1_STS
Definition: registers.h:17
static const struct fixed_event fixed_events[UACPI_FIXED_EVENT_MAX+1]
Definition: event.c:35
static uacpi_interrupt_ret dispatch_fixed_event(const struct fixed_event *ev, uacpi_fixed_event event)
Definition: event.c:175
uacpi_u16 status_mask
Definition: event.c:27
uacpi_u16 enable_mask
Definition: event.c:26

Referenced by handle_sci().

◆ handle_global_lock()

static uacpi_interrupt_ret handle_global_lock ( uacpi_handle  ctx)
static

Definition at line 2136 of file event.c.

2137{
2140
2141 if (uacpi_unlikely(!g_uacpi_rt_ctx.has_global_lock)) {
2142 uacpi_warn("platform has no global lock but a release event "
2143 "was fired anyway?");
2145 }
2146
2147 flags = uacpi_kernel_lock_spinlock(g_uacpi_rt_ctx.global_lock_spinlock);
2148 if (!g_uacpi_rt_ctx.global_lock_pending) {
2149 uacpi_trace("spurious firmware global lock release notification");
2150 goto out;
2151 }
2152
2153 uacpi_trace("received a firmware global lock release notification");
2154
2155 uacpi_kernel_signal_event(g_uacpi_rt_ctx.global_lock_event);
2156 g_uacpi_rt_ctx.global_lock_pending = UACPI_FALSE;
2157
2158out:
2159 uacpi_kernel_unlock_spinlock(g_uacpi_rt_ctx.global_lock_spinlock, flags);
2161}
unsigned long uacpi_cpu_flags
Definition: arch_helpers.h:13
GLbitfield flags
Definition: glext.h:7161
void uacpi_kernel_signal_event(uacpi_handle)
Definition: uacpiosl.c:73
uacpi_cpu_flags uacpi_kernel_lock_spinlock(uacpi_handle)
Definition: uacpiosl.c:98
void uacpi_kernel_unlock_spinlock(uacpi_handle, uacpi_cpu_flags)
Definition: uacpiosl.c:105

Referenced by uacpi_initialize_events().

◆ handle_gpes()

static uacpi_interrupt_ret handle_gpes ( uacpi_handle  opaque)
static

Definition at line 626 of file event.c.

627{
628 struct gpe_interrupt_ctx *ctx = opaque;
629
632
633 return detect_gpes(ctx->gpe_head);
634}
static uacpi_interrupt_ret detect_gpes(struct gpe_block *block)
Definition: event.c:565

Referenced by find_or_create_gpe_interrupt_ctx(), handle_sci(), and uninstall_gpe_block().

◆ handle_sci()

static uacpi_interrupt_ret handle_sci ( uacpi_handle  ctx)
static

Definition at line 2163 of file event.c.

2164{
2166
2167 int_ret |= handle_fixed_events();
2168 int_ret |= handle_gpes(ctx);
2169
2170 return int_ret;
2171}
static uacpi_interrupt_ret handle_fixed_events(void)
Definition: event.c:198

Referenced by uacpi_deinitialize_events(), and uacpi_initialize_events().

◆ initialize_fixed_events()

static uacpi_status initialize_fixed_events ( void  )
static

Definition at line 71 of file event.c.

72{
74
75 for (i = 0; i < UACPI_FIXED_EVENT_MAX; ++i) {
78 );
79 }
80
81 return UACPI_STATUS_OK;
82}

Referenced by uacpi_initialize_events_early().

◆ initialize_gpes()

static uacpi_status initialize_gpes ( void  )
static

Definition at line 2006 of file event.c.

2007{
2009 uacpi_namespace_node *gpe_node;
2010 struct acpi_fadt *fadt = &g_uacpi_rt_ctx.fadt;
2011 uacpi_u8 gpe0_regs = 0, gpe1_regs = 0;
2012
2014
2015 if (fadt->x_gpe0_blk.address && fadt->gpe0_blk_len) {
2016 gpe0_regs = fadt->gpe0_blk_len / 2;
2017
2019 gpe_node, fadt->sci_int, 0, fadt->x_gpe0_blk.address,
2020 fadt->x_gpe0_blk.address_space_id, gpe0_regs
2021 );
2023 uacpi_error("unable to create FADT GPE block 0: %s",
2025 }
2026 }
2027
2028 if (fadt->x_gpe1_blk.address && fadt->gpe1_blk_len) {
2029 gpe1_regs = fadt->gpe1_blk_len / 2;
2030
2031 if (uacpi_unlikely((gpe0_regs * EVENTS_PER_GPE_REGISTER) >
2032 fadt->gpe1_base)) {
2034 "FADT GPE block 1 [%d->%d] collides with GPE block 0 "
2035 "[%d->%d], ignoring",
2036 0, gpe0_regs * EVENTS_PER_GPE_REGISTER, fadt->gpe1_base,
2037 gpe1_regs * EVENTS_PER_GPE_REGISTER
2038 );
2039 gpe1_regs = 0;
2040 goto out;
2041 }
2042
2044 gpe_node, fadt->sci_int, fadt->gpe1_base, fadt->x_gpe1_blk.address,
2045 fadt->x_gpe1_blk.address_space_id, gpe1_regs
2046 );
2048 uacpi_error("unable to create FADT GPE block 1: %s",
2050 }
2051 }
2052
2053 if (gpe0_regs == 0 && gpe1_regs == 0)
2054 uacpi_trace("platform has no FADT GPE events");
2055
2056out:
2057 return UACPI_STATUS_OK;
2058}
uacpi_namespace_node * uacpi_namespace_get_predefined(uacpi_predefined_namespace)
Definition: namespace.c:269
@ UACPI_PREDEFINED_NAMESPACE_GPE
Definition: namespace.h:18
static uacpi_status create_gpe_block(uacpi_namespace_node *device_node, uacpi_u32 irq, uacpi_u16 base_idx, uacpi_u64 address, uacpi_u8 address_space_id, uacpi_u16 num_registers)
Definition: event.c:1012

Referenced by uacpi_initialize_events().

◆ maybe_dispatch_gpe()

static uacpi_status maybe_dispatch_gpe ( uacpi_namespace_node gpe_device,
struct gp_event event 
)
static

Definition at line 607 of file event.c.

610{
612 struct gpe_register *reg = event->reg;
614
615 ret = uacpi_gas_read_mapped(&reg->status, &status);
617 return ret;
618
619 if (!(status & gpe_get_mask(event)))
620 return ret;
621
622 dispatch_gpe(gpe_device, event);
623 return ret;
624}
uacpi_mapped_gas status
Definition: event.c:284

Referenced by uacpi_enable_gpe(), and uacpi_uninstall_gpe_handler().

◆ restore_gpe()

static uacpi_status restore_gpe ( struct gp_event event)
static

Definition at line 385 of file event.c.

386{
388
389 if (event->triggering == UACPI_GPE_TRIGGERING_LEVEL) {
392 return ret;
393 }
394
396 event->block_interrupts = UACPI_FALSE;
397
398 return ret;
399}

Referenced by async_restore_gpe(), dispatch_gpe(), and uacpi_finish_handling_gpe().

◆ sanitize_device_and_find_gpe()

static uacpi_status sanitize_device_and_find_gpe ( uacpi_namespace_node **  gpe_device,
uacpi_u16  idx,
struct gp_event **  out_event 
)
static

Definition at line 1395 of file event.c.

1399{
1400 if (*gpe_device == UACPI_NULL) {
1401 *gpe_device = uacpi_namespace_get_predefined(
1403 );
1404 }
1405
1406 *out_event = get_gpe(*gpe_device, idx);
1407 if (*out_event == UACPI_NULL)
1409
1410 return UACPI_STATUS_OK;
1411}
static struct gp_event * get_gpe(uacpi_namespace_node *gpe_device, uacpi_u16 idx)
Definition: event.c:1163

Referenced by do_install_gpe_handler(), gpe_enable_disable_for_wake(), gpe_get_mask_unmask(), gpe_suspend_resume(), uacpi_clear_gpe(), uacpi_disable_gpe(), uacpi_enable_gpe(), uacpi_finish_handling_gpe(), uacpi_gpe_info(), uacpi_setup_gpe_for_wake(), and uacpi_uninstall_gpe_handler().

◆ set_event()

static uacpi_status set_event ( uacpi_u8  event,
uacpi_u8  value 
)
static

Definition at line 84 of file event.c.

85{
87 uacpi_u64 raw_value;
88 const struct fixed_event *ev = &fixed_events[event];
89
92 return ret;
93
96 return ret;
97
98 if (raw_value != value) {
99 uacpi_error("failed to %sable fixed event %d",
100 value ? "en" : "dis", event);
102 }
103
104 uacpi_trace("fixed event %d %sabled successfully",
105 event, value ? "en" : "dis");
106 return UACPI_STATUS_OK;
107}
uacpi_status uacpi_read_register_field(uacpi_register_field, uacpi_u64 *)
Definition: registers.c:487
@ UACPI_STATUS_HARDWARE_TIMEOUT
Definition: status.h:28

Referenced by fire_event(), queue_add_timer(), queue_move_timer(), uacpi_disable_fixed_event(), uacpi_enable_fixed_event(), uacpi_install_fixed_event_handler(), and uacpi_uninstall_fixed_event_handler().

◆ set_gpe_state()

static uacpi_status set_gpe_state ( struct gp_event event,
enum gpe_state  state 
)
static

Definition at line 335 of file event.c.

336{
338 struct gpe_register *reg = event->reg;
339 uacpi_u64 enable_mask;
340 uacpi_u8 event_bit;
342
343 event_bit = gpe_get_mask(event);
344 if (state != GPE_STATE_DISABLED && (reg->masked_mask & event_bit))
345 return UACPI_STATUS_OK;
346
348 if (!(reg->current_mask & event_bit))
349 return UACPI_STATUS_OK;
350
352 }
353
355
356 ret = uacpi_gas_read_mapped(&reg->enable, &enable_mask);
358 goto out;
359
360 switch (state) {
362 enable_mask |= event_bit;
363 break;
365 enable_mask &= ~event_bit;
366 break;
367 default:
369 goto out;
370 }
371
372 ret = uacpi_gas_write_mapped(&reg->enable, enable_mask);
373out:
375 return ret;
376}
static uacpi_handle g_gpe_state_slock
Definition: event.c:19

Referenced by dispatch_gpe(), gpe_add_user(), gpe_mask_unmask(), gpe_remove_user(), gpe_suspend_resume(), and restore_gpe().

◆ uacpi_clear_all_events()

uacpi_status uacpi_clear_all_events ( void  )

Definition at line 2475 of file event.c.

2476{
2478 struct do_for_all_gpes_ctx ctx = {
2480 };
2481
2483
2485 return UACPI_STATUS_OK;
2486
2489 return ret;
2490
2493 goto out;
2494
2496 ret = ctx.ret;
2497
2498out:
2500 return ret;
2501}
uacpi_status uacpi_write_register(uacpi_register, uacpi_u64)
Definition: registers.c:286
#define PM1_STATUS_BITS
Definition: event.c:2464

Referenced by enter_sleep_state_hw_full().

◆ uacpi_clear_fixed_event()

uacpi_status uacpi_clear_fixed_event ( uacpi_fixed_event  event)

Definition at line 161 of file event.c.

162{
164
165 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
168 return UACPI_STATUS_OK;
169
172 );
173}
@ UACPI_INIT_LEVEL_SUBSYSTEM_INITIALIZED
Definition: types.h:72

◆ uacpi_clear_gpe()

uacpi_status uacpi_clear_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1634 of file event.c.

1637{
1639 struct gp_event *event;
1640
1642
1645
1648 return ret;
1649
1650 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1652 goto out;
1653
1654 ret = clear_gpe(event);
1655out:
1657 return ret;
1658}

◆ uacpi_deinitialize_events()

void uacpi_deinitialize_events ( void  )

Definition at line 2246 of file event.c.

2247{
2248 struct gpe_interrupt_ctx *ctx, *next_ctx = g_gpe_interrupt_head;
2249 uacpi_size i;
2250
2252 return;
2253
2255
2256 if (g_uacpi_rt_ctx.sci_handle_valid) {
2258 handle_sci, g_uacpi_rt_ctx.sci_handle
2259 );
2260 g_uacpi_rt_ctx.sci_handle_valid = UACPI_FALSE;
2261 }
2262
2263 while (next_ctx) {
2264 struct gpe_block *block, *next_block;
2265
2266 ctx = next_ctx;
2267 next_ctx = ctx->next;
2268
2269 next_block = ctx->gpe_head;
2270 while (next_block) {
2271 block = next_block;
2272 next_block = block->next;
2274 }
2275 }
2276
2277 for (i = 0; i < UACPI_FIXED_EVENT_MAX; ++i) {
2280 }
2281
2285 }
2286
2288
2290}
uacpi_status uacpi_recursive_lock_deinit(struct uacpi_recursive_lock *lock)
Definition: mutex.c:268
static uacpi_interrupt_ret handle_sci(uacpi_handle ctx)
Definition: event.c:2163
uacpi_status uacpi_uninstall_fixed_event_handler(uacpi_fixed_event event)
Definition: event.c:2332
static uacpi_bool g_gpes_finalized
Definition: event.c:21
uacpi_status uacpi_kernel_uninstall_interrupt_handler(uacpi_interrupt_handler, uacpi_handle irq_handle)
Definition: uacpiosl.c:221
void uacpi_kernel_free_spinlock(uacpi_handle)
Definition: uacpiosl.c:92

Referenced by uacpi_state_reset().

◆ uacpi_disable_all_gpes()

uacpi_status uacpi_disable_all_gpes ( void  )

Definition at line 1982 of file event.c.

1983{
1984 struct do_for_all_gpes_ctx ctx = {
1986 };
1987 return for_all_gpes_locked(&ctx);
1988}
static uacpi_status for_all_gpes_locked(struct do_for_all_gpes_ctx *ctx)
Definition: event.c:1963

Referenced by enter_sleep_state_hw_full(), and wake_from_sleep_state_hw_full().

◆ uacpi_disable_fixed_event()

uacpi_status uacpi_disable_fixed_event ( uacpi_fixed_event  event)

Definition at line 140 of file event.c.

141{
143
145
146 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
149 return UACPI_STATUS_OK;
150
153 return ret;
154
156
158 return ret;
159}
static uacpi_status set_event(uacpi_u8 event, uacpi_u8 value)
Definition: event.c:84

◆ uacpi_disable_gpe()

uacpi_status uacpi_disable_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1608 of file event.c.

◆ uacpi_disable_gpe_for_wake()

uacpi_status uacpi_disable_gpe_for_wake ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1938 of file event.c.

1941{
1942 return gpe_enable_disable_for_wake(gpe_device, idx, UACPI_FALSE);
1943}
static uacpi_status gpe_enable_disable_for_wake(uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_bool enabled)
Definition: event.c:1891

◆ uacpi_enable_all_runtime_gpes()

uacpi_status uacpi_enable_all_runtime_gpes ( void  )

Definition at line 1990 of file event.c.

1991{
1992 struct do_for_all_gpes_ctx ctx = {
1994 };
1995 return for_all_gpes_locked(&ctx);
1996}

Referenced by wake_from_sleep_state_hw_full().

◆ uacpi_enable_all_wake_gpes()

uacpi_status uacpi_enable_all_wake_gpes ( void  )

Definition at line 1998 of file event.c.

1999{
2000 struct do_for_all_gpes_ctx ctx = {
2002 };
2003 return for_all_gpes_locked(&ctx);
2004}

Referenced by enter_sleep_state_hw_full().

◆ uacpi_enable_fixed_event()

uacpi_status uacpi_enable_fixed_event ( uacpi_fixed_event  event)

Definition at line 109 of file event.c.

110{
112
114
115 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
118 return UACPI_STATUS_OK;
119
122 return ret;
123
124 /*
125 * Attempting to enable an event that doesn't have a handler is most likely
126 * an error, don't allow it.
127 */
130 goto out;
131 }
132
134
135out:
137 return ret;
138}
@ UACPI_STATUS_NO_HANDLER
Definition: status.h:25
#define UACPI_EVENT_ENABLED
Definition: event.c:15

◆ uacpi_enable_gpe()

uacpi_status uacpi_enable_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1571 of file event.c.

1574{
1576 struct gp_event *event;
1577
1579
1582
1585 return ret;
1586
1587 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1589 goto out;
1590
1591 if (uacpi_unlikely(event->handler_type == GPE_HANDLER_TYPE_NONE)) {
1593 goto out;
1594 }
1595
1598 goto out;
1599
1601 maybe_dispatch_gpe(gpe_device, event);
1602
1603out:
1605 return ret;
1606}
static uacpi_status maybe_dispatch_gpe(uacpi_namespace_node *gpe_device, struct gp_event *event)
Definition: event.c:607

◆ uacpi_enable_gpe_for_wake()

uacpi_status uacpi_enable_gpe_for_wake ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1931 of file event.c.

1934{
1935 return gpe_enable_disable_for_wake(gpe_device, idx, UACPI_TRUE);
1936}

◆ uacpi_events_match_post_dynamic_table_load()

void uacpi_events_match_post_dynamic_table_load ( void  )

Definition at line 970 of file event.c.

971{
972 struct gpe_match_ctx match_ctx = {
974 };
975 struct gpe_interrupt_ctx *irq_ctx;
976
978 return;
979
981
983 goto out;
984
985 irq_ctx = g_gpe_interrupt_head;
986
987 while (irq_ctx) {
988 match_ctx.block = irq_ctx->gpe_head;
989
990 while (match_ctx.block) {
992 match_ctx.block->device_node, do_match_gpe_methods, UACPI_NULL,
995 );
996 match_ctx.block = match_ctx.block->next;
997 }
998
999 irq_ctx = irq_ctx->next;
1000 }
1001
1002 if (match_ctx.matched_count) {
1003 uacpi_info("matched %u additional GPEs post dynamic table load",
1004 match_ctx.matched_count);
1005 }
1006
1007out:
1010}
struct gpe_interrupt_ctx * next
Definition: event.c:316
struct gpe_block * gpe_head
Definition: event.c:318
uacpi_bool post_dynamic_table_load
Definition: event.c:888

Referenced by do_load_table(), handle_load(), and handle_load_table().

◆ uacpi_finalize_gpe_initialization()

uacpi_status uacpi_finalize_gpe_initialization ( void  )

Definition at line 1367 of file event.c.

1368{
1370 uacpi_bool poll_blocks = UACPI_FALSE;
1371
1373
1375 return UACPI_STATUS_OK;
1376
1379 return ret;
1380
1381 if (g_gpes_finalized)
1382 goto out;
1383
1385
1387 if (poll_blocks)
1389
1390out:
1392 return ret;
1393}
static uacpi_iteration_decision do_initialize_gpe_block(struct gpe_block *block, uacpi_handle opaque)
Definition: event.c:1328

◆ uacpi_finish_handling_gpe()

uacpi_status uacpi_finish_handling_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1701 of file event.c.

1704{
1706 struct gp_event *event;
1707
1709
1712
1715 return ret;
1716
1717 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1719 goto out;
1720
1721 event = get_gpe(gpe_device, idx);
1724 goto out;
1725 }
1726
1728out:
1730 return ret;
1731
1732}

◆ uacpi_fixed_event_info()

uacpi_status uacpi_fixed_event_info ( uacpi_fixed_event  event,
uacpi_event_info out_info 
)

Definition at line 2366 of file event.c.

2369{
2371 const struct fixed_event *ev;
2372 uacpi_u64 raw_value;
2374
2376
2377 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
2381
2384 return ret;
2385
2387 info |= UACPI_EVENT_INFO_HAS_HANDLER;
2388
2389 ev = &fixed_events[event];
2390
2391 ret = uacpi_read_register_field(ev->enable_field, &raw_value);
2393 goto out;
2394 if (raw_value)
2395 info |= UACPI_EVENT_INFO_ENABLED | UACPI_EVENT_INFO_HW_ENABLED;
2396
2397 ret = uacpi_read_register_field(ev->status_field, &raw_value);
2399 goto out;
2400 if (raw_value)
2401 info |= UACPI_EVENT_INFO_HW_STATUS;
2402
2403 *out_info = info;
2404out:
2406 return ret;
2407}
uacpi_event_info
Definition: event.h:63

◆ uacpi_gpe_info()

uacpi_status uacpi_gpe_info ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_event_info out_info 
)

Definition at line 2409 of file event.c.

2412{
2414 struct gp_event *event;
2415 struct gpe_register *reg;
2416 uacpi_u8 mask;
2417 uacpi_u64 raw_value;
2419
2421
2424
2427 return ret;
2428
2429 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
2431 goto out;
2432
2433 if (event->handler_type != GPE_HANDLER_TYPE_NONE)
2434 info |= UACPI_EVENT_INFO_HAS_HANDLER;
2435
2437 reg = event->reg;
2438
2439 if (reg->runtime_mask & mask)
2440 info |= UACPI_EVENT_INFO_ENABLED;
2441 if (reg->masked_mask & mask)
2442 info |= UACPI_EVENT_INFO_MASKED;
2443 if (reg->wake_mask & mask)
2444 info |= UACPI_EVENT_INFO_ENABLED_FOR_WAKE;
2445
2446 ret = uacpi_gas_read_mapped(&reg->enable, &raw_value);
2448 goto out;
2449 if (raw_value & mask)
2450 info |= UACPI_EVENT_INFO_HW_ENABLED;
2451
2452 ret = uacpi_gas_read_mapped(&reg->status, &raw_value);
2454 goto out;
2455 if (raw_value & mask)
2456 info |= UACPI_EVENT_INFO_HW_STATUS;
2457
2458 *out_info = info;
2459out:
2461 return ret;
2462}

◆ uacpi_gpe_triggering_to_string()

const uacpi_char * uacpi_gpe_triggering_to_string ( uacpi_gpe_triggering  triggering)

Definition at line 1243 of file event.c.

1246{
1247 switch (triggering) {
1249 return "edge";
1251 return "level";
1252 default:
1253 return "invalid";
1254 }
1255}

Referenced by do_install_gpe_handler().

◆ uacpi_initialize_events()

uacpi_status uacpi_initialize_events ( void  )

Definition at line 2195 of file event.c.

2196{
2198
2200 return UACPI_STATUS_OK;
2201
2202 ret = initialize_gpes();
2204 return ret;
2205
2208 &g_uacpi_rt_ctx.sci_handle
2209 );
2212 "unable to install SCI interrupt handler: %s",
2214 );
2215 return ret;
2216 }
2217 g_uacpi_rt_ctx.sci_handle_valid = UACPI_TRUE;
2218
2219 g_uacpi_rt_ctx.global_lock_event = uacpi_kernel_create_event();
2220 if (uacpi_unlikely(g_uacpi_rt_ctx.global_lock_event == UACPI_NULL))
2222
2223 g_uacpi_rt_ctx.global_lock_spinlock = uacpi_kernel_create_spinlock();
2224 if (uacpi_unlikely(g_uacpi_rt_ctx.global_lock_spinlock == UACPI_NULL))
2226
2229 );
2233 uacpi_warn("platform has global lock but no FACS was provided");
2234 return ret;
2235 }
2236 g_uacpi_rt_ctx.has_global_lock = UACPI_TRUE;
2237 } else if (ret == UACPI_STATUS_HARDWARE_TIMEOUT) {
2238 // has_global_lock remains set to false
2239 uacpi_trace("platform has no global lock");
2241 }
2242
2243 return ret;
2244}
#define UACPI_FIXED_EVENT_GLOBAL_LOCK
Definition: event.h:6
#define uacpi_likely_success(expr)
Definition: status.h:53
static uacpi_interrupt_ret handle_global_lock(uacpi_handle ctx)
Definition: event.c:2136
uacpi_status uacpi_install_fixed_event_handler(uacpi_fixed_event event, uacpi_interrupt_handler handler, uacpi_handle user)
Definition: event.c:2292
static uacpi_status initialize_gpes(void)
Definition: event.c:2006
uacpi_handle uacpi_kernel_create_event(void)
Definition: uacpiosl.c:53
uacpi_handle uacpi_kernel_create_spinlock(void)
Definition: uacpiosl.c:85

Referenced by uacpi_namespace_load().

◆ uacpi_initialize_events_early()

uacpi_status uacpi_initialize_events_early ( void  )

Definition at line 2173 of file event.c.

2174{
2176
2178 return UACPI_STATUS_OK;
2179
2183
2186 return ret;
2187
2190 return ret;
2191
2192 return UACPI_STATUS_OK;
2193}
uacpi_status uacpi_recursive_lock_init(struct uacpi_recursive_lock *lock)
Definition: mutex.c:256
static uacpi_status initialize_fixed_events(void)
Definition: event.c:71

Referenced by uacpi_initialize().

◆ uacpi_install_fixed_event_handler()

uacpi_status uacpi_install_fixed_event_handler ( uacpi_fixed_event  event,
uacpi_interrupt_handler  handler,
uacpi_handle  user 
)

Definition at line 2292 of file event.c.

2296{
2298 struct fixed_event_handler *ev;
2299
2301
2302 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
2305 return UACPI_STATUS_OK;
2306
2309 return ret;
2310
2312
2313 if (ev->handler != UACPI_NULL) {
2315 goto out;
2316 }
2317
2318 ev->handler = handler;
2319 ev->ctx = user;
2320
2323 ev->handler = UACPI_NULL;
2324 ev->ctx = UACPI_NULL;
2325 }
2326
2327out:
2329 return ret;
2330}
void user(int argc, const char *argv[])
Definition: cmds.c:1350

Referenced by uacpi_initialize_events().

◆ uacpi_install_gpe_block()

uacpi_status uacpi_install_gpe_block ( uacpi_namespace_node gpe_device,
uacpi_u64  address,
uacpi_address_space  address_space,
uacpi_u16  num_registers,
uacpi_u32  irq 
)

Definition at line 2060 of file event.c.

2064{
2066 uacpi_bool is_dev;
2067
2069
2072
2073 ret = uacpi_namespace_node_is(gpe_device, UACPI_OBJECT_DEVICE, &is_dev);
2075 return ret;
2076 if (!is_dev)
2078
2081 return ret;
2082
2083 if (uacpi_unlikely(get_gpe(gpe_device, 0) != UACPI_NULL)) {
2085 goto out;
2086 }
2087
2089 gpe_device, irq, 0, address, address_space, num_registers
2090 );
2091
2092out:
2094 return ret;
2095}
uacpi_u16 uacpi_gpe_triggering uacpi_gpe_handler uacpi_handle ctx uacpi_u16 uacpi_namespace_node *wake_device uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u16 idx uacpi_u64 uacpi_address_space address_space
Definition: event.h:273
uacpi_status uacpi_namespace_node_is(const uacpi_namespace_node *node, uacpi_object_type type, uacpi_bool *out)
Definition: namespace.c:825
@ UACPI_OBJECT_DEVICE
Definition: types.h:117

◆ uacpi_install_gpe_handler()

uacpi_status uacpi_install_gpe_handler ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_gpe_triggering  triggering,
uacpi_gpe_handler  handler,
uacpi_handle  ctx 
)

Definition at line 1488 of file event.c.

1493{
1496 handler, ctx
1497 );
1498}
static uacpi_status do_install_gpe_handler(uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_gpe_triggering triggering, enum gpe_handler_type type, uacpi_gpe_handler handler, uacpi_handle ctx)
Definition: event.c:1413

◆ uacpi_install_gpe_handler_raw()

uacpi_status uacpi_install_gpe_handler_raw ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_gpe_triggering  triggering,
uacpi_gpe_handler  handler,
uacpi_handle  ctx 
)

Definition at line 1500 of file event.c.

1505{
1508 handler, ctx
1509 );
1510}

◆ uacpi_mask_gpe()

uacpi_status uacpi_mask_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1761 of file event.c.

1764{
1765 return gpe_get_mask_unmask(gpe_device, idx, UACPI_TRUE);
1766}
static uacpi_status gpe_get_mask_unmask(uacpi_namespace_node *gpe_device, uacpi_u16 idx, uacpi_bool should_mask)
Definition: event.c:1734

◆ uacpi_resume_gpe()

uacpi_status uacpi_resume_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1694 of file event.c.

1697{
1698 return gpe_suspend_resume(gpe_device, idx, GPE_STATE_ENABLED);
1699}
static uacpi_status gpe_suspend_resume(uacpi_namespace_node *gpe_device, uacpi_u16 idx, enum gpe_state state)
Definition: event.c:1660

◆ uacpi_setup_gpe_for_wake()

uacpi_status uacpi_setup_gpe_for_wake ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_namespace_node wake_device 
)

Definition at line 1775 of file event.c.

1779{
1781 struct gp_event *event;
1782 uacpi_bool did_mask;
1783
1785
1788
1789 if (wake_device != UACPI_NULL) {
1790 uacpi_bool is_dev = wake_device == uacpi_namespace_root();
1791
1792 if (!is_dev) {
1793 ret = uacpi_namespace_node_is(wake_device, UACPI_OBJECT_DEVICE, &is_dev);
1795 return ret;
1796 }
1797
1798 if (!is_dev)
1800 }
1801
1804 return ret;
1805
1806 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1808 goto out;
1809
1810 did_mask = gpe_mask_safe(event);
1811
1812 if (wake_device != UACPI_NULL) {
1813 switch (event->handler_type) {
1815 event->handler_type = GPE_HANDLER_TYPE_IMPLICIT_NOTIFY;
1816 event->triggering = UACPI_GPE_TRIGGERING_LEVEL;
1817 break;
1818
1820 /*
1821 * An AML handler already exists, we expect it to call Notify() as
1822 * it sees fit. For now just make sure this event is disabled if it
1823 * had been enabled automatically previously during initialization.
1824 */
1826 break;
1827
1830 uacpi_warn(
1831 "not configuring implicit notify for GPE(%02X) -> %.4s: "
1832 " a user handler already installed", event->idx,
1833 wake_device->name.text
1834 );
1835 break;
1836
1837 // We will re-check this below
1839 break;
1840
1841 default:
1842 uacpi_warn("invalid GPE(%02X) handler type: %d",
1843 event->idx, event->handler_type);
1845 goto out_unmask;
1846 }
1847
1848 /*
1849 * This GPE has no known AML handler, so we configure it to receive
1850 * implicit notifications for wake devices when we get a corresponding
1851 * GPE triggered. Usually it's the job of a matching AML handler, but
1852 * we didn't find any.
1853 */
1854 if (event->handler_type == GPE_HANDLER_TYPE_IMPLICIT_NOTIFY) {
1855 struct gpe_implicit_notify_handler *implicit_handler;
1856
1857 implicit_handler = event->implicit_handler;
1858 while (implicit_handler) {
1859 if (implicit_handler->device == wake_device) {
1861 goto out_unmask;
1862 }
1863
1864 implicit_handler = implicit_handler->next;
1865 }
1866
1867 implicit_handler = uacpi_kernel_alloc(sizeof(*implicit_handler));
1868 if (uacpi_likely(implicit_handler != UACPI_NULL)) {
1869 implicit_handler->device = wake_device;
1870 implicit_handler->next = event->implicit_handler;
1871 event->implicit_handler = implicit_handler;
1872 } else {
1873 uacpi_warn(
1874 "unable to configure implicit wake for GPE(%02X) -> %.4s: "
1875 "out of memory", event->idx, wake_device->name.text
1876 );
1877 }
1878 }
1879 }
1880
1881 event->wake = UACPI_TRUE;
1882
1883out_unmask:
1884 if (did_mask)
1886out:
1888 return ret;
1889}
uacpi_namespace_node * uacpi_namespace_root(void)
Definition: namespace.c:264
#define uacpi_likely(expr)
Definition: compiler.h:89
@ UACPI_STATUS_INTERNAL_ERROR
Definition: status.h:21
uacpi_namespace_node * device
Definition: event.c:243
struct gpe_implicit_notify_handler * next
Definition: event.c:242

◆ uacpi_suspend_gpe()

uacpi_status uacpi_suspend_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1687 of file event.c.

1690{
1691 return gpe_suspend_resume(gpe_device, idx, GPE_STATE_DISABLED);
1692}

◆ uacpi_uninstall_fixed_event_handler()

uacpi_status uacpi_uninstall_fixed_event_handler ( uacpi_fixed_event  event)

Definition at line 2332 of file event.c.

2335{
2337 struct fixed_event_handler *ev;
2338
2340
2341 if (uacpi_unlikely(event < 0 || event > UACPI_FIXED_EVENT_MAX))
2344 return UACPI_STATUS_OK;
2345
2348 return ret;
2349
2351
2354 goto out;
2355
2357
2358 ev->handler = UACPI_NULL;
2359 ev->ctx = UACPI_NULL;
2360
2361out:
2363 return ret;
2364}

Referenced by uacpi_deinitialize_events(), and uacpi_initialize_events().

◆ uacpi_uninstall_gpe_block()

uacpi_status uacpi_uninstall_gpe_block ( uacpi_namespace_node gpe_device)

Definition at line 2097 of file event.c.

2100{
2102 uacpi_bool is_dev;
2103 struct gpe_search_ctx search_ctx = { 0 };
2104
2105 search_ctx.idx = 0;
2106 search_ctx.gpe_device = gpe_device;
2107
2109
2112
2115 return ret;
2116 if (!is_dev)
2118
2121 return ret;
2122
2123 for_each_gpe_block(do_find_gpe, &search_ctx);
2124 if (search_ctx.out_block == UACPI_NULL) {
2126 goto out;
2127 }
2128
2129 uninstall_gpe_block(search_ctx.out_block);
2130
2131out:
2133 return ret;
2134}
uacpi_u16 idx
Definition: event.c:1141
struct gpe_block * out_block
Definition: event.c:1142

◆ uacpi_uninstall_gpe_handler()

uacpi_status uacpi_uninstall_gpe_handler ( uacpi_namespace_node gpe_device,
uacpi_u16  idx,
uacpi_gpe_handler  handler 
)

Definition at line 1512 of file event.c.

1516{
1518 struct gp_event *event;
1519 struct gpe_native_handler *native_handler;
1520 uacpi_bool did_mask;
1521
1523
1526
1529 return ret;
1530
1531 ret = sanitize_device_and_find_gpe(&gpe_device, idx, &event);
1533 goto out;
1534
1535 if (event->handler_type != GPE_HANDLER_TYPE_NATIVE_HANDLER &&
1536 event->handler_type != GPE_HANDLER_TYPE_NATIVE_HANDLER_RAW) {
1538 goto out;
1539 }
1540
1541 native_handler = event->native_handler;
1542 if (uacpi_unlikely(native_handler->cb != handler)) {
1544 goto out;
1545 }
1546
1547 did_mask = gpe_mask_safe(event);
1548
1549 event->aml_handler = native_handler->previous_handler;
1550 event->triggering = native_handler->previous_triggering;
1551 event->handler_type = native_handler->previous_handler_type;
1552
1553 if ((event->handler_type == GPE_HANDLER_TYPE_AML_HANDLER ||
1554 event->handler_type == GPE_HANDLER_TYPE_IMPLICIT_NOTIFY) &&
1555 native_handler->previously_enabled) {
1557 }
1558
1559 uacpi_free(native_handler, sizeof(*native_handler));
1560
1561 if (did_mask)
1563
1565 maybe_dispatch_gpe(gpe_device, event);
1566out:
1568 return ret;
1569}

◆ uacpi_unmask_gpe()

uacpi_status uacpi_unmask_gpe ( uacpi_namespace_node gpe_device,
uacpi_u16  idx 
)

Definition at line 1768 of file event.c.

1771{
1772 return gpe_get_mask_unmask(gpe_device, idx, UACPI_FALSE);
1773}

◆ uninstall_gpe_block()

static void uninstall_gpe_block ( struct gpe_block block)
static

Definition at line 778 of file event.c.

779{
780 if (block->registers != UACPI_NULL) {
781 struct gpe_register *reg;
783
785
786 for (i = 0; i < block->num_registers; ++i) {
787 reg = &block->registers[i];
788
789 if (reg->enable.total_bit_width)
790 uacpi_unmap_gas_nofree(&reg->enable);
791 if (reg->status.total_bit_width)
792 uacpi_unmap_gas_nofree(&reg->status);
793 }
794 }
795
796 if (block->prev)
797 block->prev->next = block->next;
798
799 if (block->irq_ctx) {
800 struct gpe_interrupt_ctx *ctx = block->irq_ctx;
801
802 // Are we the first GPE block?
803 if (block == ctx->gpe_head) {
804 ctx->gpe_head = ctx->gpe_head->next;
805 } else {
806 struct gpe_block *prev_block = ctx->gpe_head;
807
808 // We're not, do a search
809 while (prev_block) {
810 if (prev_block->next == block) {
811 prev_block->next = block->next;
812 break;
813 }
814
815 prev_block = prev_block->next;
816 }
817 }
818
819 // This GPE block was the last user of this interrupt context, remove it
820 if (ctx->gpe_head == UACPI_NULL) {
821 if (ctx->prev)
822 ctx->prev->next = ctx->next;
823
824 if (ctx->irq != g_uacpi_rt_ctx.fadt.sci_int) {
826 handle_gpes, ctx->irq_handle
827 );
828 }
829
830 uacpi_free(block->irq_ctx, sizeof(*block->irq_ctx));
831 }
832 }
833
834 if (block->events != UACPI_NULL) {
836 struct gp_event *event;
837
838 for (i = 0; i < block->num_events; ++i) {
839 event = &block->events[i];
840
841 switch (event->handler_type) {
844 break;
845
848 uacpi_free(event->native_handler,
849 sizeof(*event->native_handler));
850 break;
851
854 break;
855 }
856
857 default:
858 break;
859 }
860 }
861
862 }
863
864 uacpi_free(block->registers,
865 sizeof(*block->registers) * block->num_registers);
866 uacpi_free(block->events,
867 sizeof(*block->events) * block->num_events);
868 uacpi_free(block, sizeof(*block));
869}
void uacpi_unmap_gas_nofree(uacpi_mapped_gas *gas)
Definition: io.c:984
static void gpe_block_mask_safe(struct gpe_block *block)
Definition: event.c:740
struct gpe_block * next
Definition: event.c:296

Referenced by create_gpe_block(), uacpi_deinitialize_events(), and uacpi_uninstall_gpe_block().

Variable Documentation

◆ fixed_event_handlers

◆ fixed_events

◆ g_event_lock

◆ g_gpe_interrupt_head

◆ g_gpe_state_slock

uacpi_handle g_gpe_state_slock
static

Definition at line 19 of file event.c.

Referenced by set_gpe_state(), uacpi_deinitialize_events(), and uacpi_initialize_events_early().

◆ g_gpes_finalized

uacpi_bool g_gpes_finalized
static

Definition at line 21 of file event.c.

Referenced by uacpi_deinitialize_events(), and uacpi_finalize_gpe_initialization().