summaryrefslogtreecommitdiffstats
path: root/drivers/acpi/executer
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/acpi/executer')
-rw-r--r--drivers/acpi/executer/exconfig.c105
-rw-r--r--drivers/acpi/executer/exconvrt.c2
-rw-r--r--drivers/acpi/executer/excreate.c117
-rw-r--r--drivers/acpi/executer/exdump.c69
-rw-r--r--drivers/acpi/executer/exfield.c63
-rw-r--r--drivers/acpi/executer/exfldio.c46
-rw-r--r--drivers/acpi/executer/exmisc.c2
-rw-r--r--drivers/acpi/executer/exmutex.c237
-rw-r--r--drivers/acpi/executer/exnames.c2
-rw-r--r--drivers/acpi/executer/exoparg1.c25
-rw-r--r--drivers/acpi/executer/exoparg2.c21
-rw-r--r--drivers/acpi/executer/exoparg3.c3
-rw-r--r--drivers/acpi/executer/exoparg6.c10
-rw-r--r--drivers/acpi/executer/exprep.c17
-rw-r--r--drivers/acpi/executer/exregion.c10
-rw-r--r--drivers/acpi/executer/exresnte.c12
-rw-r--r--drivers/acpi/executer/exresolv.c55
-rw-r--r--drivers/acpi/executer/exresop.c13
-rw-r--r--drivers/acpi/executer/exstore.c119
-rw-r--r--drivers/acpi/executer/exstoren.c2
-rw-r--r--drivers/acpi/executer/exstorob.c2
-rw-r--r--drivers/acpi/executer/exsystem.c3
-rw-r--r--drivers/acpi/executer/exutils.c67
23 files changed, 592 insertions, 410 deletions
diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c
index 25802f302ff..24da921d13e 100644
--- a/drivers/acpi/executer/exconfig.c
+++ b/drivers/acpi/executer/exconfig.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -45,7 +45,6 @@
#include <acpi/acinterp.h>
#include <acpi/amlcode.h>
#include <acpi/acnamesp.h>
-#include <acpi/acevents.h>
#include <acpi/actables.h>
#include <acpi/acdispat.h>
@@ -138,6 +137,14 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state,
ACPI_FUNCTION_TRACE(ex_load_table_op);
+ /* Validate lengths for the signature_string, OEMIDString, OEMtable_iD */
+
+ if ((operand[0]->string.length > ACPI_NAME_SIZE) ||
+ (operand[1]->string.length > ACPI_OEM_ID_SIZE) ||
+ (operand[2]->string.length > ACPI_OEM_TABLE_ID_SIZE)) {
+ return_ACPI_STATUS(AE_BAD_PARAMETER);
+ }
+
/* Find the ACPI table in the RSDT/XSDT */
status = acpi_tb_find_table(operand[0]->string.pointer,
@@ -229,11 +236,18 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state,
status = acpi_get_table_by_index(table_index, &table);
if (ACPI_SUCCESS(status)) {
ACPI_INFO((AE_INFO,
- "Dynamic OEM Table Load - [%4.4s] OemId [%6.6s] OemTableId [%8.8s]",
+ "Dynamic OEM Table Load - [%.4s] OemId [%.6s] OemTableId [%.8s]",
table->signature, table->oem_id,
table->oem_table_id));
}
+ /* Invoke table handler if present */
+
+ if (acpi_gbl_table_handler) {
+ (void)acpi_gbl_table_handler(ACPI_TABLE_EVENT_LOAD, table,
+ acpi_gbl_table_handler_context);
+ }
+
*return_desc = ddb_handle;
return_ACPI_STATUS(status);
}
@@ -268,6 +282,7 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
struct acpi_table_desc table_desc;
acpi_native_uint table_index;
acpi_status status;
+ u32 length;
ACPI_FUNCTION_TRACE(ex_load_op);
@@ -278,16 +293,16 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
switch (ACPI_GET_OBJECT_TYPE(obj_desc)) {
case ACPI_TYPE_REGION:
+ ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Load from Region %p %s\n",
+ obj_desc,
+ acpi_ut_get_object_type_name(obj_desc)));
+
/* Region must be system_memory (from ACPI spec) */
if (obj_desc->region.space_id != ACPI_ADR_SPACE_SYSTEM_MEMORY) {
return_ACPI_STATUS(AE_AML_OPERAND_TYPE);
}
- ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Load from Region %p %s\n",
- obj_desc,
- acpi_ut_get_object_type_name(obj_desc)));
-
/*
* If the Region Address and Length have not been previously evaluated,
* evaluate them now and save the results.
@@ -299,6 +314,11 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
}
}
+ /*
+ * We will simply map the memory region for the table. However, the
+ * memory region is technically not guaranteed to remain stable and
+ * we may eventually have to copy the table to a local buffer.
+ */
table_desc.address = obj_desc->region.address;
table_desc.length = obj_desc->region.length;
table_desc.flags = ACPI_TABLE_ORIGIN_MAPPED;
@@ -306,18 +326,41 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
case ACPI_TYPE_BUFFER: /* Buffer or resolved region_field */
- /* Simply extract the buffer from the buffer object */
-
ACPI_DEBUG_PRINT((ACPI_DB_EXEC,
"Load from Buffer or Field %p %s\n", obj_desc,
acpi_ut_get_object_type_name(obj_desc)));
- table_desc.pointer = ACPI_CAST_PTR(struct acpi_table_header,
- obj_desc->buffer.pointer);
- table_desc.length = table_desc.pointer->length;
- table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED;
+ length = obj_desc->buffer.length;
+
+ /* Must have at least an ACPI table header */
+
+ if (length < sizeof(struct acpi_table_header)) {
+ return_ACPI_STATUS(AE_INVALID_TABLE_LENGTH);
+ }
+
+ /* Validate checksum here. It won't get validated in tb_add_table */
- obj_desc->buffer.pointer = NULL;
+ status =
+ acpi_tb_verify_checksum(ACPI_CAST_PTR
+ (struct acpi_table_header,
+ obj_desc->buffer.pointer), length);
+ if (ACPI_FAILURE(status)) {
+ return_ACPI_STATUS(status);
+ }
+
+ /*
+ * We need to copy the buffer since the original buffer could be
+ * changed or deleted in the future
+ */
+ table_desc.pointer = ACPI_ALLOCATE(length);
+ if (!table_desc.pointer) {
+ return_ACPI_STATUS(AE_NO_MEMORY);
+ }
+
+ ACPI_MEMCPY(table_desc.pointer, obj_desc->buffer.pointer,
+ length);
+ table_desc.length = length;
+ table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED;
break;
default:
@@ -333,7 +376,8 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
}
status =
- acpi_ex_add_table(table_index, acpi_gbl_root_node, &ddb_handle);
+ acpi_ex_add_table(table_index, walk_state->scope_info->scope.node,
+ &ddb_handle);
if (ACPI_FAILURE(status)) {
/* On error, table_ptr was deallocated above */
@@ -349,11 +393,23 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
/* table_ptr was deallocated above */
+ acpi_ut_remove_reference(ddb_handle);
return_ACPI_STATUS(status);
}
+ /* Invoke table handler if present */
+
+ if (acpi_gbl_table_handler) {
+ (void)acpi_gbl_table_handler(ACPI_TABLE_EVENT_LOAD,
+ table_desc.pointer,
+ acpi_gbl_table_handler_context);
+ }
+
cleanup:
if (ACPI_FAILURE(status)) {
+
+ /* Delete allocated buffer or mapping */
+
acpi_tb_delete_table(&table_desc);
}
return_ACPI_STATUS(status);
@@ -376,6 +432,7 @@ acpi_status acpi_ex_unload_table(union acpi_operand_object *ddb_handle)
acpi_status status = AE_OK;
union acpi_operand_object *table_desc = ddb_handle;
acpi_native_uint table_index;
+ struct acpi_table_header *table;
ACPI_FUNCTION_TRACE(ex_unload_table);
@@ -395,17 +452,25 @@ acpi_status acpi_ex_unload_table(union acpi_operand_object *ddb_handle)
table_index = (acpi_native_uint) table_desc->reference.object;
+ /* Invoke table handler if present */
+
+ if (acpi_gbl_table_handler) {
+ status = acpi_get_table_by_index(table_index, &table);
+ if (ACPI_SUCCESS(status)) {
+ (void)acpi_gbl_table_handler(ACPI_TABLE_EVENT_UNLOAD,
+ table,
+ acpi_gbl_table_handler_context);
+ }
+ }
+
/*
* Delete the entire namespace under this table Node
* (Offset contains the table_id)
*/
acpi_tb_delete_namespace_by_owner(table_index);
- acpi_tb_release_owner_id(table_index);
+ (void)acpi_tb_release_owner_id(table_index);
acpi_tb_set_table_loaded_flag(table_index, FALSE);
- /* Delete the table descriptor (ddb_handle) */
-
- acpi_ut_remove_reference(table_desc);
- return_ACPI_STATUS(status);
+ return_ACPI_STATUS(AE_OK);
}
diff --git a/drivers/acpi/executer/exconvrt.c b/drivers/acpi/executer/exconvrt.c
index 79f2c0d42c0..fd954b4ed83 100644
--- a/drivers/acpi/executer/exconvrt.c
+++ b/drivers/acpi/executer/exconvrt.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
diff --git a/drivers/acpi/executer/excreate.c b/drivers/acpi/executer/excreate.c
index 6e9a23e47fe..60e62c4f057 100644
--- a/drivers/acpi/executer/excreate.c
+++ b/drivers/acpi/executer/excreate.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -96,6 +96,9 @@ acpi_status acpi_ex_create_alias(struct acpi_walk_state *walk_state)
* to the original Node.
*/
switch (target_node->type) {
+
+ /* For these types, the sub-object can change dynamically via a Store */
+
case ACPI_TYPE_INTEGER:
case ACPI_TYPE_STRING:
case ACPI_TYPE_BUFFER:
@@ -103,9 +106,18 @@ acpi_status acpi_ex_create_alias(struct acpi_walk_state *walk_state)
case ACPI_TYPE_BUFFER_FIELD:
/*
+ * These types open a new scope, so we need the NS node in order to access
+ * any children.
+ */
+ case ACPI_TYPE_DEVICE:
+ case ACPI_TYPE_POWER:
+ case ACPI_TYPE_PROCESSOR:
+ case ACPI_TYPE_THERMAL:
+ case ACPI_TYPE_LOCAL_SCOPE:
+
+ /*
* The new alias has the type ALIAS and points to the original
- * NS node, not the object itself. This is because for these
- * types, the object can change dynamically via a Store.
+ * NS node, not the object itself.
*/
alias_node->type = ACPI_TYPE_LOCAL_ALIAS;
alias_node->object =
@@ -115,9 +127,7 @@ acpi_status acpi_ex_create_alias(struct acpi_walk_state *walk_state)
case ACPI_TYPE_METHOD:
/*
- * The new alias has the type ALIAS and points to the original
- * NS node, not the object itself. This is because for these
- * types, the object can change dynamically via a Store.
+ * Control method aliases need to be differentiated
*/
alias_node->type = ACPI_TYPE_LOCAL_METHOD_ALIAS;
alias_node->object =
@@ -342,101 +352,6 @@ acpi_ex_create_region(u8 * aml_start,
/*******************************************************************************
*
- * FUNCTION: acpi_ex_create_table_region
- *
- * PARAMETERS: walk_state - Current state
- *
- * RETURN: Status
- *
- * DESCRIPTION: Create a new data_table_region object
- *
- ******************************************************************************/
-
-acpi_status acpi_ex_create_table_region(struct acpi_walk_state *walk_state)
-{
- acpi_status status;
- union acpi_operand_object **operand = &walk_state->operands[0];
- union acpi_operand_object *obj_desc;
- struct acpi_namespace_node *node;
- union acpi_operand_object *region_obj2;
- acpi_native_uint table_index;
- struct acpi_table_header *table;
-
- ACPI_FUNCTION_TRACE(ex_create_table_region);
-
- /* Get the Node from the object stack */
-
- node = walk_state->op->common.node;
-
- /*
- * If the region object is already attached to this node,
- * just return
- */
- if (acpi_ns_get_attached_object(node)) {
- return_ACPI_STATUS(AE_OK);
- }
-
- /* Find the ACPI table */
-
- status = acpi_tb_find_table(operand[1]->string.pointer,
- operand[2]->string.pointer,
- operand[3]->string.pointer, &table_index);
- if (ACPI_FAILURE(status)) {
- return_ACPI_STATUS(status);
- }
-
- /* Create the region descriptor */
-
- obj_desc = acpi_ut_create_internal_object(ACPI_TYPE_REGION);
- if (!obj_desc) {
- return_ACPI_STATUS(AE_NO_MEMORY);
- }
-
- region_obj2 = obj_desc->common.next_object;
- region_obj2->extra.region_context = NULL;
-
- status = acpi_get_table_by_index(table_index, &table);
- if (ACPI_FAILURE(status)) {
- return_ACPI_STATUS(status);
- }
-
- /* Init the region from the operands */
-
- obj_desc->region.space_id = REGION_DATA_TABLE;
- obj_desc->region.address =
- (acpi_physical_address) ACPI_TO_INTEGER(table);
- obj_desc->region.length = table->length;
- obj_desc->region.node = node;
- obj_desc->region.flags = AOPOBJ_DATA_VALID;
-
- /* Install the new region object in the parent Node */
-
- status = acpi_ns_attach_object(node, obj_desc, ACPI_TYPE_REGION);
- if (ACPI_FAILURE(status)) {
- goto cleanup;
- }
-
- status = acpi_ev_initialize_region(obj_desc, FALSE);
- if (ACPI_FAILURE(status)) {
- if (status == AE_NOT_EXIST) {
- status = AE_OK;
- } else {
- goto cleanup;
- }
- }
-
- obj_desc->region.flags |= AOPOBJ_SETUP_COMPLETE;
-
- cleanup:
-
- /* Remove local reference to the object */
-
- acpi_ut_remove_reference(obj_desc);
- return_ACPI_STATUS(status);
-}
-
-/*******************************************************************************
- *
* FUNCTION: acpi_ex_create_processor
*
* PARAMETERS: walk_state - Current state
diff --git a/drivers/acpi/executer/exdump.c b/drivers/acpi/executer/exdump.c
index 51c9c29987c..74f1b22601b 100644
--- a/drivers/acpi/executer/exdump.c
+++ b/drivers/acpi/executer/exdump.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -500,25 +500,28 @@ void acpi_ex_dump_operand(union acpi_operand_object *obj_desc, u32 depth)
acpi_os_printf("Reference: Debug\n");
break;
- case AML_NAME_OP:
+ case AML_INDEX_OP:
- ACPI_DUMP_PATHNAME(obj_desc->reference.object,
- "Reference: Name: ", ACPI_LV_INFO,
- _COMPONENT);
- ACPI_DUMP_ENTRY(obj_desc->reference.object,
- ACPI_LV_INFO);
+ acpi_os_printf("Reference: Index %p\n",
+ obj_desc->reference.object);
break;
- case AML_INDEX_OP:
+ case AML_LOAD_OP:
- acpi_os_printf("Reference: Index %p\n",
+ acpi_os_printf("Reference: [DdbHandle] TableIndex %p\n",
obj_desc->reference.object);
break;
case AML_REF_OF_OP:
- acpi_os_printf("Reference: (RefOf) %p\n",
- obj_desc->reference.object);
+ acpi_os_printf("Reference: (RefOf) %p [%s]\n",
+ obj_desc->reference.object,
+ acpi_ut_get_type_name(((union
+ acpi_operand_object
+ *)obj_desc->
+ reference.
+ object)->common.
+ type));
break;
case AML_ARG_OP:
@@ -559,8 +562,9 @@ void acpi_ex_dump_operand(union acpi_operand_object *obj_desc, u32 depth)
case AML_INT_NAMEPATH_OP:
- acpi_os_printf("Reference.Node->Name %X\n",
- obj_desc->reference.node->name.integer);
+ acpi_os_printf("Reference: Namepath %X [%4.4s]\n",
+ obj_desc->reference.node->name.integer,
+ obj_desc->reference.node->name.ascii);
break;
default:
@@ -640,8 +644,8 @@ void acpi_ex_dump_operand(union acpi_operand_object *obj_desc, u32 depth)
acpi_os_printf("\n");
} else {
acpi_os_printf(" base %8.8X%8.8X Length %X\n",
- ACPI_FORMAT_UINT64(obj_desc->region.
- address),
+ ACPI_FORMAT_NATIVE_UINT(obj_desc->region.
+ address),
obj_desc->region.length);
}
break;
@@ -877,20 +881,43 @@ static void acpi_ex_dump_reference_obj(union acpi_operand_object *obj_desc)
ret_buf.length = ACPI_ALLOCATE_LOCAL_BUFFER;
if (obj_desc->reference.opcode == AML_INT_NAMEPATH_OP) {
- acpi_os_printf("Named Object %p ", obj_desc->reference.node);
+ acpi_os_printf(" Named Object %p ", obj_desc->reference.node);
status =
acpi_ns_handle_to_pathname(obj_desc->reference.node,
&ret_buf);
if (ACPI_FAILURE(status)) {
- acpi_os_printf("Could not convert name to pathname\n");
+ acpi_os_printf(" Could not convert name to pathname\n");
} else {
acpi_os_printf("%s\n", (char *)ret_buf.pointer);
ACPI_FREE(ret_buf.pointer);
}
} else if (obj_desc->reference.object) {
- acpi_os_printf("\nReferenced Object: %p\n",
- obj_desc->reference.object);
+ if (ACPI_GET_DESCRIPTOR_TYPE(obj_desc) ==
+ ACPI_DESC_TYPE_OPERAND) {
+ acpi_os_printf(" Target: %p",
+ obj_desc->reference.object);
+ if (obj_desc->reference.opcode == AML_LOAD_OP) {
+ /*
+ * For DDBHandle reference,
+ * obj_desc->Reference.Object is the table index
+ */
+ acpi_os_printf(" [DDBHandle]\n");
+ } else {
+ acpi_os_printf(" [%s]\n",
+ acpi_ut_get_type_name(((union
+ acpi_operand_object
+ *)
+ obj_desc->
+ reference.
+ object)->
+ common.
+ type));
+ }
+ } else {
+ acpi_os_printf(" Target: %p\n",
+ obj_desc->reference.object);
+ }
}
}
@@ -976,7 +1003,9 @@ acpi_ex_dump_package_obj(union acpi_operand_object *obj_desc,
case ACPI_TYPE_LOCAL_REFERENCE:
- acpi_os_printf("[Object Reference] ");
+ acpi_os_printf("[Object Reference] %s",
+ (acpi_ps_get_opcode_info
+ (obj_desc->reference.opcode))->name);
acpi_ex_dump_reference_obj(obj_desc);
break;
diff --git a/drivers/acpi/executer/exfield.c b/drivers/acpi/executer/exfield.c
index 2d88a3d8d1a..3e440d84226 100644
--- a/drivers/acpi/executer/exfield.c
+++ b/drivers/acpi/executer/exfield.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -71,7 +71,6 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
union acpi_operand_object *buffer_desc;
acpi_size length;
void *buffer;
- u8 locked;
ACPI_FUNCTION_TRACE_PTR(ex_read_data_from_field, obj_desc);
@@ -111,9 +110,7 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
/* Lock entire transaction if requested */
- locked =
- acpi_ex_acquire_global_lock(obj_desc->common_field.
- field_flags);
+ acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
/*
* Perform the read.
@@ -125,7 +122,7 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
buffer.pointer),
ACPI_READ | (obj_desc->field.
attribute << 16));
- acpi_ex_release_global_lock(locked);
+ acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
goto exit;
}
@@ -175,13 +172,12 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
/* Lock entire transaction if requested */
- locked =
- acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
+ acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
/* Read from the field */
status = acpi_ex_extract_from_field(obj_desc, buffer, (u32) length);
- acpi_ex_release_global_lock(locked);
+ acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
exit:
if (ACPI_FAILURE(status)) {
@@ -214,10 +210,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
{
acpi_status status;
u32 length;
- u32 required_length;
void *buffer;
- void *new_buffer;
- u8 locked;
union acpi_operand_object *buffer_desc;
ACPI_FUNCTION_TRACE_PTR(ex_write_data_to_field, obj_desc);
@@ -278,9 +271,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
/* Lock entire transaction if requested */
- locked =
- acpi_ex_acquire_global_lock(obj_desc->common_field.
- field_flags);
+ acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
/*
* Perform the write (returns status and perhaps data in the
@@ -291,7 +282,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
(acpi_integer *) buffer,
ACPI_WRITE | (obj_desc->field.
attribute << 16));
- acpi_ex_release_global_lock(locked);
+ acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
*result_desc = buffer_desc;
return_ACPI_STATUS(status);
@@ -319,35 +310,6 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
return_ACPI_STATUS(AE_AML_OPERAND_TYPE);
}
- /*
- * We must have a buffer that is at least as long as the field
- * we are writing to. This is because individual fields are
- * indivisible and partial writes are not supported -- as per
- * the ACPI specification.
- */
- new_buffer = NULL;
- required_length =
- ACPI_ROUND_BITS_UP_TO_BYTES(obj_desc->common_field.bit_length);
-
- if (length < required_length) {
-
- /* We need to create a new buffer */
-
- new_buffer = ACPI_ALLOCATE_ZEROED(required_length);
- if (!new_buffer) {
- return_ACPI_STATUS(AE_NO_MEMORY);
- }
-
- /*
- * Copy the original data to the new buffer, starting
- * at Byte zero. All unused (upper) bytes of the
- * buffer will be 0.
- */
- ACPI_MEMCPY((char *)new_buffer, (char *)buffer, length);
- buffer = new_buffer;
- length = required_length;
- }
-
ACPI_DEBUG_PRINT((ACPI_DB_BFIELD,
"FieldWrite [FROM]: Obj %p (%s:%X), Buf %p, ByteLen %X\n",
source_desc,
@@ -366,19 +328,12 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
/* Lock entire transaction if requested */
- locked =
- acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
+ acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
/* Write to the field */
status = acpi_ex_insert_into_field(obj_desc, buffer, length);
- acpi_ex_release_global_lock(locked);
-
- /* Free temporary buffer if we used one */
-
- if (new_buffer) {
- ACPI_FREE(new_buffer);
- }
+ acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
return_ACPI_STATUS(status);
}
diff --git a/drivers/acpi/executer/exfldio.c b/drivers/acpi/executer/exfldio.c
index 65a48b6170e..e336b5dc7a5 100644
--- a/drivers/acpi/executer/exfldio.c
+++ b/drivers/acpi/executer/exfldio.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -263,7 +263,8 @@ acpi_ex_access_region(union acpi_operand_object *obj_desc,
rgn_desc->region.space_id,
obj_desc->common_field.access_byte_width,
obj_desc->common_field.base_byte_offset,
- field_datum_byte_offset, (void *)address));
+ field_datum_byte_offset, ACPI_CAST_PTR(void,
+ address)));
/* Invoke the appropriate address_space/op_region handler */
@@ -805,18 +806,39 @@ acpi_ex_insert_into_field(union acpi_operand_object *obj_desc,
u32 datum_count;
u32 field_datum_count;
u32 i;
+ u32 required_length;
+ void *new_buffer;
ACPI_FUNCTION_TRACE(ex_insert_into_field);
/* Validate input buffer */
- if (buffer_length <
- ACPI_ROUND_BITS_UP_TO_BYTES(obj_desc->common_field.bit_length)) {
- ACPI_ERROR((AE_INFO,
- "Field size %X (bits) is too large for buffer (%X)",
- obj_desc->common_field.bit_length, buffer_length));
+ new_buffer = NULL;
+ required_length =
+ ACPI_ROUND_BITS_UP_TO_BYTES(obj_desc->common_field.bit_length);
+ /*
+ * We must have a buffer that is at least as long as the field
+ * we are writing to. This is because individual fields are
+ * indivisible and partial writes are not supported -- as per
+ * the ACPI specification.
+ */
+ if (buffer_length < required_length) {
- return_ACPI_STATUS(AE_BUFFER_OVERFLOW);
+ /* We need to create a new buffer */
+
+ new_buffer = ACPI_ALLOCATE_ZEROED(required_length);
+ if (!new_buffer) {
+ return_ACPI_STATUS(AE_NO_MEMORY);
+ }
+
+ /*
+ * Copy the original data to the new buffer, starting
+ * at Byte zero. All unused (upper) bytes of the
+ * buffer will be 0.
+ */
+ ACPI_MEMCPY((char *)new_buffer, (char *)buffer, buffer_length);
+ buffer = new_buffer;
+ buffer_length = required_length;
}
/*
@@ -866,7 +888,7 @@ acpi_ex_insert_into_field(union acpi_operand_object *obj_desc,
merged_datum,
field_offset);
if (ACPI_FAILURE(status)) {
- return_ACPI_STATUS(status);
+ goto exit;
}
field_offset += obj_desc->common_field.access_byte_width;
@@ -924,5 +946,11 @@ acpi_ex_insert_into_field(union acpi_operand_object *obj_desc,
mask, merged_datum,
field_offset);
+ exit:
+ /* Free temporary buffer if we used one */
+
+ if (new_buffer) {
+ ACPI_FREE(new_buffer);
+ }
return_ACPI_STATUS(status);
}
diff --git a/drivers/acpi/executer/exmisc.c b/drivers/acpi/executer/exmisc.c
index f13d1cec2d6..cc956a5b526 100644
--- a/drivers/acpi/executer/exmisc.c
+++ b/drivers/acpi/executer/exmisc.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
diff --git a/drivers/acpi/executer/exmutex.c b/drivers/acpi/executer/exmutex.c
index 6748e3ef099..c873ab40cd0 100644
--- a/drivers/acpi/executer/exmutex.c
+++ b/drivers/acpi/executer/exmutex.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -126,6 +126,79 @@ acpi_ex_link_mutex(union acpi_operand_object *obj_desc,
/*******************************************************************************
*
+ * FUNCTION: acpi_ex_acquire_mutex_object
+ *
+ * PARAMETERS: time_desc - Timeout in milliseconds
+ * obj_desc - Mutex object
+ * Thread - Current thread state
+ *
+ * RETURN: Status
+ *
+ * DESCRIPTION: Acquire an AML mutex, low-level interface. Provides a common
+ * path that supports multiple acquires by the same thread.
+ *
+ * MUTEX: Interpreter must be locked
+ *
+ * NOTE: This interface is called from three places:
+ * 1) From acpi_ex_acquire_mutex, via an AML Acquire() operator
+ * 2) From acpi_ex_acquire_global_lock when an AML Field access requires the
+ * global lock
+ * 3) From the external interface, acpi_acquire_global_lock
+ *
+ ******************************************************************************/
+
+acpi_status
+acpi_ex_acquire_mutex_object(u16 timeout,
+ union acpi_operand_object *obj_desc,
+ acpi_thread_id thread_id)
+{
+ acpi_status status;
+
+ ACPI_FUNCTION_TRACE_PTR(ex_acquire_mutex_object, obj_desc);
+
+ if (!obj_desc) {
+ return_ACPI_STATUS(AE_BAD_PARAMETER);
+ }
+
+ /* Support for multiple acquires by the owning thread */
+
+ if (obj_desc->mutex.thread_id == thread_id) {
+ /*
+ * The mutex is already owned by this thread, just increment the
+ * acquisition depth
+ */
+ obj_desc->mutex.acquisition_depth++;
+ return_ACPI_STATUS(AE_OK);
+ }
+
+ /* Acquire the mutex, wait if necessary. Special case for Global Lock */
+
+ if (obj_desc == acpi_gbl_global_lock_mutex) {
+ status = acpi_ev_acquire_global_lock(timeout);
+ } else {
+ status = acpi_ex_system_wait_mutex(obj_desc->mutex.os_mutex,
+ timeout);
+ }
+
+ if (ACPI_FAILURE(status)) {
+
+ /* Includes failure from a timeout on time_desc */
+
+ return_ACPI_STATUS(status);
+ }
+
+ /* Acquired the mutex: update mutex object */
+
+ obj_desc->mutex.thread_id = thread_id;
+ obj_desc->mutex.acquisition_depth = 1;
+ obj_desc->mutex.original_sync_level = 0;
+ obj_desc->mutex.owner_thread = NULL; /* Used only for AML Acquire() */
+
+ return_ACPI_STATUS(AE_OK);
+}
+
+/*******************************************************************************
+ *
* FUNCTION: acpi_ex_acquire_mutex
*
* PARAMETERS: time_desc - Timeout integer
@@ -151,7 +224,7 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc,
return_ACPI_STATUS(AE_BAD_PARAMETER);
}
- /* Sanity check: we must have a valid thread ID */
+ /* Must have a valid thread ID */
if (!walk_state->thread) {
ACPI_ERROR((AE_INFO,
@@ -161,7 +234,7 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc,
}
/*
- * Current Sync must be less than or equal to the sync level of the
+ * Current sync level must be less than or equal to the sync level of the
* mutex. This mechanism provides some deadlock prevention
*/
if (walk_state->thread->current_sync_level > obj_desc->mutex.sync_level) {
@@ -172,51 +245,89 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc,
return_ACPI_STATUS(AE_AML_MUTEX_ORDER);
}
- /* Support for multiple acquires by the owning thread */
+ status = acpi_ex_acquire_mutex_object((u16) time_desc->integer.value,
+ obj_desc,
+ walk_state->thread->thread_id);
+ if (ACPI_SUCCESS(status) && obj_desc->mutex.acquisition_depth == 1) {
- if (obj_desc->mutex.owner_thread) {
- if (obj_desc->mutex.owner_thread->thread_id ==
- walk_state->thread->thread_id) {
- /*
- * The mutex is already owned by this thread, just increment the
- * acquisition depth
- */
- obj_desc->mutex.acquisition_depth++;
- return_ACPI_STATUS(AE_OK);
- }
+ /* Save Thread object, original/current sync levels */
+
+ obj_desc->mutex.owner_thread = walk_state->thread;
+ obj_desc->mutex.original_sync_level =
+ walk_state->thread->current_sync_level;
+ walk_state->thread->current_sync_level =
+ obj_desc->mutex.sync_level;
+
+ /* Link the mutex to the current thread for force-unlock at method exit */
+
+ acpi_ex_link_mutex(obj_desc, walk_state->thread);
}
- /* Acquire the mutex, wait if necessary. Special case for Global Lock */
+ return_ACPI_STATUS(status);
+}
- if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) {
- status =
- acpi_ev_acquire_global_lock((u16) time_desc->integer.value);
- } else {
- status = acpi_ex_system_wait_mutex(obj_desc->mutex.os_mutex,
- (u16) time_desc->integer.
- value);
+/*******************************************************************************
+ *
+ * FUNCTION: acpi_ex_release_mutex_object
+ *
+ * PARAMETERS: obj_desc - The object descriptor for this op
+ *
+ * RETURN: Status
+ *
+ * DESCRIPTION: Release a previously acquired Mutex, low level interface.
+ * Provides a common path that supports multiple releases (after
+ * previous multiple acquires) by the same thread.
+ *
+ * MUTEX: Interpreter must be locked
+ *
+ * NOTE: This interface is called from three places:
+ * 1) From acpi_ex_release_mutex, via an AML Acquire() operator
+ * 2) From acpi_ex_release_global_lock when an AML Field access requires the
+ * global lock
+ * 3) From the external interface, acpi_release_global_lock
+ *
+ ******************************************************************************/
+
+acpi_status acpi_ex_release_mutex_object(union acpi_operand_object *obj_desc)
+{
+ acpi_status status = AE_OK;
+
+ ACPI_FUNCTION_TRACE(ex_release_mutex_object);
+
+ if (obj_desc->mutex.acquisition_depth == 0) {
+ return (AE_NOT_ACQUIRED);
}
- if (ACPI_FAILURE(status)) {
+ /* Match multiple Acquires with multiple Releases */
- /* Includes failure from a timeout on time_desc */
+ obj_desc->mutex.acquisition_depth--;
+ if (obj_desc->mutex.acquisition_depth != 0) {
- return_ACPI_STATUS(status);
+ /* Just decrement the depth and return */
+
+ return_ACPI_STATUS(AE_OK);
}
- /* Have the mutex: update mutex and walk info and save the sync_level */
+ if (obj_desc->mutex.owner_thread) {
- obj_desc->mutex.owner_thread = walk_state->thread;
- obj_desc->mutex.acquisition_depth = 1;
- obj_desc->mutex.original_sync_level =
- walk_state->thread->current_sync_level;
+ /* Unlink the mutex from the owner's list */
- walk_state->thread->current_sync_level = obj_desc->mutex.sync_level;
+ acpi_ex_unlink_mutex(obj_desc);
+ obj_desc->mutex.owner_thread = NULL;
+ }
- /* Link the mutex to the current thread for force-unlock at method exit */
+ /* Release the mutex, special case for Global Lock */
- acpi_ex_link_mutex(obj_desc, walk_state->thread);
- return_ACPI_STATUS(AE_OK);
+ if (obj_desc == acpi_gbl_global_lock_mutex) {
+ status = acpi_ev_release_global_lock();
+ } else {
+ acpi_os_release_mutex(obj_desc->mutex.os_mutex);
+ }
+
+ /* Clear mutex info */
+
+ obj_desc->mutex.thread_id = 0;
+ return_ACPI_STATUS(status);
}
/*******************************************************************************
@@ -253,22 +364,13 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc,
return_ACPI_STATUS(AE_AML_MUTEX_NOT_ACQUIRED);
}
- /* Sanity check: we must have a valid thread ID */
-
- if (!walk_state->thread) {
- ACPI_ERROR((AE_INFO,
- "Cannot release Mutex [%4.4s], null thread info",
- acpi_ut_get_node_name(obj_desc->mutex.node)));
- return_ACPI_STATUS(AE_AML_INTERNAL);
- }
-
/*
* The Mutex is owned, but this thread must be the owner.
* Special case for Global Lock, any thread can release
*/
if ((obj_desc->mutex.owner_thread->thread_id !=
walk_state->thread->thread_id)
- && (obj_desc->mutex.os_mutex != acpi_gbl_global_lock_mutex)) {
+ && (obj_desc != acpi_gbl_global_lock_mutex)) {
ACPI_ERROR((AE_INFO,
"Thread %lX cannot release Mutex [%4.4s] acquired by thread %lX",
(unsigned long)walk_state->thread->thread_id,
@@ -278,45 +380,37 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc,
return_ACPI_STATUS(AE_AML_NOT_OWNER);
}
+ /* Must have a valid thread ID */
+
+ if (!walk_state->thread) {
+ ACPI_ERROR((AE_INFO,
+ "Cannot release Mutex [%4.4s], null thread info",
+ acpi_ut_get_node_name(obj_desc->mutex.node)));
+ return_ACPI_STATUS(AE_AML_INTERNAL);
+ }
+
/*
* The sync level of the mutex must be less than or equal to the current
* sync level
*/
if (obj_desc->mutex.sync_level > walk_state->thread->current_sync_level) {
ACPI_ERROR((AE_INFO,
- "Cannot release Mutex [%4.4s], incorrect SyncLevel",
- acpi_ut_get_node_name(obj_desc->mutex.node)));
+ "Cannot release Mutex [%4.4s], SyncLevel mismatch: mutex %d current %d",
+ acpi_ut_get_node_name(obj_desc->mutex.node),
+ obj_desc->mutex.sync_level,
+ walk_state->thread->current_sync_level));
return_ACPI_STATUS(AE_AML_MUTEX_ORDER);
}
- /* Match multiple Acquires with multiple Releases */
-
- obj_desc->mutex.acquisition_depth--;
- if (obj_desc->mutex.acquisition_depth != 0) {
-
- /* Just decrement the depth and return */
-
- return_ACPI_STATUS(AE_OK);
- }
-
- /* Unlink the mutex from the owner's list */
+ status = acpi_ex_release_mutex_object(obj_desc);
- acpi_ex_unlink_mutex(obj_desc);
+ if (obj_desc->mutex.acquisition_depth == 0) {
- /* Release the mutex, special case for Global Lock */
+ /* Restore the original sync_level */
- if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) {
- status = acpi_ev_release_global_lock();
- } else {
- acpi_os_release_mutex(obj_desc->mutex.os_mutex);
+ walk_state->thread->current_sync_level =
+ obj_desc->mutex.original_sync_level;
}
-
- /* Update the mutex and restore sync_level */
-
- obj_desc->mutex.owner_thread = NULL;
- walk_state->thread->current_sync_level =
- obj_desc->mutex.original_sync_level;
-
return_ACPI_STATUS(status);
}
@@ -357,7 +451,7 @@ void acpi_ex_release_all_mutexes(struct acpi_thread_state *thread)
/* Release the mutex, special case for Global Lock */
- if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) {
+ if (obj_desc == acpi_gbl_global_lock_mutex) {
/* Ignore errors */
@@ -369,6 +463,7 @@ void acpi_ex_release_all_mutexes(struct acpi_thread_state *thread)
/* Mark mutex unowned */
obj_desc->mutex.owner_thread = NULL;
+ obj_desc->mutex.thread_id = 0;
/* Update Thread sync_level (Last mutex is the important one) */
diff --git a/drivers/acpi/executer/exnames.c b/drivers/acpi/executer/exnames.c
index 308eae52dc0..817e67be369 100644
--- a/drivers/acpi/executer/exnames.c
+++ b/drivers/acpi/executer/exnames.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
diff --git a/drivers/acpi/executer/exoparg1.c b/drivers/acpi/executer/exoparg1.c
index 252f10acbbc..7c3bea575e0 100644
--- a/drivers/acpi/executer/exoparg1.c
+++ b/drivers/acpi/executer/exoparg1.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -121,6 +121,7 @@ acpi_status acpi_ex_opcode_0A_0T_1R(struct acpi_walk_state *walk_state)
if ((ACPI_FAILURE(status)) || walk_state->result_obj) {
acpi_ut_remove_reference(return_desc);
+ walk_state->result_obj = NULL;
} else {
/* Save the return value */
@@ -739,26 +740,38 @@ acpi_status acpi_ex_opcode_1A_0T_1R(struct acpi_walk_state *walk_state)
value = acpi_gbl_integer_byte_width;
break;
- case ACPI_TYPE_BUFFER:
- value = temp_desc->buffer.length;
- break;
-
case ACPI_TYPE_STRING:
value = temp_desc->string.length;
break;
+ case ACPI_TYPE_BUFFER:
+
+ /* Buffer arguments may not be evaluated at this point */
+
+ status = acpi_ds_get_buffer_arguments(temp_desc);
+ value = temp_desc->buffer.length;
+ break;
+
case ACPI_TYPE_PACKAGE:
+
+ /* Package arguments may not be evaluated at this point */
+
+ status = acpi_ds_get_package_arguments(temp_desc);
value = temp_desc->package.count;
break;
default:
ACPI_ERROR((AE_INFO,
- "Operand is not Buf/Int/Str/Pkg - found type %s",
+ "Operand must be Buffer/Integer/String/Package - found type %s",
acpi_ut_get_type_name(type)));
status = AE_AML_OPERAND_TYPE;
goto cleanup;
}
+ if (ACPI_FAILURE(status)) {
+ goto cleanup;
+ }
+
/*
* Now that we have the size of the object, create a result
* object to hold the value
diff --git a/drivers/acpi/executer/exoparg2.c b/drivers/acpi/executer/exoparg2.c
index 17e652e6537..8e8bbb6cceb 100644
--- a/drivers/acpi/executer/exoparg2.c
+++ b/drivers/acpi/executer/exoparg2.c
@@ -5,7 +5,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -241,10 +241,6 @@ acpi_status acpi_ex_opcode_2A_2T_1R(struct acpi_walk_state *walk_state)
goto cleanup;
}
- /* Return the remainder */
-
- walk_state->result_obj = return_desc1;
-
cleanup:
/*
* Since the remainder is not returned indirectly, remove a reference to
@@ -259,6 +255,12 @@ acpi_status acpi_ex_opcode_2A_2T_1R(struct acpi_walk_state *walk_state)
acpi_ut_remove_reference(return_desc1);
}
+ /* Save return object (the remainder) on success */
+
+ else {
+ walk_state->result_obj = return_desc1;
+ }
+
return_ACPI_STATUS(status);
}
@@ -490,6 +492,7 @@ acpi_status acpi_ex_opcode_2A_1T_1R(struct acpi_walk_state *walk_state)
if (ACPI_FAILURE(status)) {
acpi_ut_remove_reference(return_desc);
+ walk_state->result_obj = NULL;
}
return_ACPI_STATUS(status);
@@ -583,8 +586,6 @@ acpi_status acpi_ex_opcode_2A_0T_1R(struct acpi_walk_state *walk_state)
return_desc->integer.value = ACPI_INTEGER_MAX;
}
- walk_state->result_obj = return_desc;
-
cleanup:
/* Delete return object on error */
@@ -593,5 +594,11 @@ acpi_status acpi_ex_opcode_2A_0T_1R(struct acpi_walk_state *walk_state)
acpi_ut_remove_reference(return_desc);
}
+ /* Save return object on success */
+
+ else {
+ walk_state->result_obj = return_desc;
+ }
+
return_ACPI_STATUS(status);
}
diff --git a/drivers/acpi/executer/exoparg3.c b/drivers/acpi/executer/exoparg3.c
index 7fe67cf82ce..9cb4197681a 100644
--- a/drivers/acpi/executer/exoparg3.c
+++ b/drivers/acpi/executer/exoparg3.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -260,6 +260,7 @@ acpi_status acpi_ex_opcode_3A_1T_1R(struct acpi_walk_state *walk_state)
if (ACPI_FAILURE(status) || walk_state->result_obj) {
acpi_ut_remove_reference(return_desc);
+ walk_state->result_obj = NULL;
}
/* Set the return object and exit */
diff --git a/drivers/acpi/executer/exoparg6.c b/drivers/acpi/executer/exoparg6.c
index bd80a9cb3d6..67d48737af5 100644
--- a/drivers/acpi/executer/exoparg6.c
+++ b/drivers/acpi/executer/exoparg6.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -322,8 +322,6 @@ acpi_status acpi_ex_opcode_6A_0T_1R(struct acpi_walk_state * walk_state)
goto cleanup;
}
- walk_state->result_obj = return_desc;
-
cleanup:
/* Delete return object on error */
@@ -332,5 +330,11 @@ acpi_status acpi_ex_opcode_6A_0T_1R(struct acpi_walk_state * walk_state)
acpi_ut_remove_reference(return_desc);
}
+ /* Save return object on success */
+
+ else {
+ walk_state->result_obj = return_desc;
+ }
+
return_ACPI_STATUS(status);
}
diff --git a/drivers/acpi/executer/exprep.c b/drivers/acpi/executer/exprep.c
index efe5d4b461a..3a2f8cd4c62 100644
--- a/drivers/acpi/executer/exprep.c
+++ b/drivers/acpi/executer/exprep.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -412,6 +412,7 @@ acpi_ex_prep_common_field_object(union acpi_operand_object *obj_desc,
acpi_status acpi_ex_prep_field_value(struct acpi_create_field_info *info)
{
union acpi_operand_object *obj_desc;
+ union acpi_operand_object *second_desc = NULL;
u32 type;
acpi_status status;
@@ -494,6 +495,20 @@ acpi_status acpi_ex_prep_field_value(struct acpi_create_field_info *info)
obj_desc->field.access_byte_width,
obj_desc->bank_field.region_obj,
obj_desc->bank_field.bank_obj));
+
+ /*
+ * Remember location in AML stream of the field unit
+ * opcode and operands -- since the bank_value
+ * operands must be evaluated.
+ */
+ second_desc = obj_desc->common.next_object;
+ second_desc->extra.aml_start =
+ ((union acpi_parse_object *)(info->data_register_node))->
+ named.data;
+ second_desc->extra.aml_length =
+ ((union acpi_parse_object *)(info->data_register_node))->
+ named.length;
+
break;
case ACPI_TYPE_LOCAL_INDEX_FIELD:
diff --git a/drivers/acpi/executer/exregion.c b/drivers/acpi/executer/exregion.c
index 3f51b7e84a1..7cd8bb54fa0 100644
--- a/drivers/acpi/executer/exregion.c
+++ b/drivers/acpi/executer/exregion.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -160,7 +160,7 @@ acpi_ex_system_memory_space_handler(u32 function,
if (!mem_info->mapped_logical_address) {
ACPI_ERROR((AE_INFO,
"Could not map memory at %8.8X%8.8X, size %X",
- ACPI_FORMAT_UINT64(address),
+ ACPI_FORMAT_NATIVE_UINT(address),
(u32) window_size));
mem_info->mapped_length = 0;
return_ACPI_STATUS(AE_NO_MEMORY);
@@ -182,7 +182,8 @@ acpi_ex_system_memory_space_handler(u32 function,
ACPI_DEBUG_PRINT((ACPI_DB_INFO,
"System-Memory (width %d) R/W %d Address=%8.8X%8.8X\n",
- bit_width, function, ACPI_FORMAT_UINT64(address)));
+ bit_width, function,
+ ACPI_FORMAT_NATIVE_UINT(address)));
/*
* Perform the memory read or write
@@ -284,7 +285,8 @@ acpi_ex_system_io_space_handler(u32 function,
ACPI_DEBUG_PRINT((ACPI_DB_INFO,
"System-IO (width %d) R/W %d Address=%8.8X%8.8X\n",
- bit_width, function, ACPI_FORMAT_UINT64(address)));
+ bit_width, function,
+ ACPI_FORMAT_NATIVE_UINT(address)));
/* Decode the function parameter */
diff --git a/drivers/acpi/executer/exresnte.c b/drivers/acpi/executer/exresnte.c
index 2b3a01cc492..5596f42c967 100644
--- a/drivers/acpi/executer/exresnte.c
+++ b/drivers/acpi/executer/exresnte.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -116,9 +116,11 @@ acpi_ex_resolve_node_to_value(struct acpi_namespace_node **object_ptr,
* Several object types require no further processing:
* 1) Device/Thermal objects don't have a "real" subobject, return the Node
* 2) Method locals and arguments have a pseudo-Node
+ * 3) 10/2007: Added method type to assist with Package construction.
*/
if ((entry_type == ACPI_TYPE_DEVICE) ||
(entry_type == ACPI_TYPE_THERMAL) ||
+ (entry_type == ACPI_TYPE_METHOD) ||
(node->flags & (ANOBJ_METHOD_ARG | ANOBJ_METHOD_LOCAL))) {
return_ACPI_STATUS(AE_OK);
}
@@ -214,7 +216,6 @@ acpi_ex_resolve_node_to_value(struct acpi_namespace_node **object_ptr,
/* For these objects, just return the object attached to the Node */
case ACPI_TYPE_MUTEX:
- case ACPI_TYPE_METHOD:
case ACPI_TYPE_POWER:
case ACPI_TYPE_PROCESSOR:
case ACPI_TYPE_EVENT:
@@ -238,13 +239,12 @@ acpi_ex_resolve_node_to_value(struct acpi_namespace_node **object_ptr,
case ACPI_TYPE_LOCAL_REFERENCE:
switch (source_desc->reference.opcode) {
- case AML_LOAD_OP:
+ case AML_LOAD_OP: /* This is a ddb_handle */
+ case AML_REF_OF_OP:
+ case AML_INDEX_OP:
- /* This is a ddb_handle */
/* Return an additional reference to the object */
- case AML_REF_OF_OP:
-
obj_desc = source_desc;
acpi_ut_add_reference(obj_desc);
break;
diff --git a/drivers/acpi/executer/exresolv.c b/drivers/acpi/executer/exresolv.c
index 6c64e55dab0..b35f7c817ac 100644
--- a/drivers/acpi/executer/exresolv.c
+++ b/drivers/acpi/executer/exresolv.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -140,7 +140,6 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
{
acpi_status status = AE_OK;
union acpi_operand_object *stack_desc;
- void *temp_node;
union acpi_operand_object *obj_desc = NULL;
u16 opcode;
@@ -156,23 +155,6 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
opcode = stack_desc->reference.opcode;
switch (opcode) {
- case AML_NAME_OP:
-
- /*
- * Convert name reference to a namespace node
- * Then, acpi_ex_resolve_node_to_value can be used to get the value
- */
- temp_node = stack_desc->reference.object;
-
- /* Delete the Reference Object */
-
- acpi_ut_remove_reference(stack_desc);
-
- /* Return the namespace node */
-
- (*stack_ptr) = temp_node;
- break;
-
case AML_LOCAL_OP:
case AML_ARG_OP:
@@ -207,15 +189,25 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
switch (stack_desc->reference.target_type) {
case ACPI_TYPE_BUFFER_FIELD:
- /* Just return - leave the Reference on the stack */
+ /* Just return - do not dereference */
break;
case ACPI_TYPE_PACKAGE:
+ /* If method call or copy_object - do not dereference */
+
+ if ((walk_state->opcode ==
+ AML_INT_METHODCALL_OP)
+ || (walk_state->opcode == AML_COPY_OP)) {
+ break;
+ }
+
+ /* Otherwise, dereference the package_index to a package element */
+
obj_desc = *stack_desc->reference.where;
if (obj_desc) {
/*
- * Valid obj descriptor, copy pointer to return value
+ * Valid object descriptor, copy pointer to return value
* (i.e., dereference the package index)
* Delete the ref object, increment the returned object
*/
@@ -224,11 +216,11 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
*stack_ptr = obj_desc;
} else {
/*
- * A NULL object descriptor means an unitialized element of
+ * A NULL object descriptor means an uninitialized element of
* the package, can't dereference it
*/
ACPI_ERROR((AE_INFO,
- "Attempt to deref an Index to NULL pkg element Idx=%p",
+ "Attempt to dereference an Index to NULL package element Idx=%p",
stack_desc));
status = AE_AML_UNINITIALIZED_ELEMENT;
}
@@ -239,7 +231,7 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
/* Invalid reference object */
ACPI_ERROR((AE_INFO,
- "Unknown TargetType %X in Index/Reference obj %p",
+ "Unknown TargetType %X in Index/Reference object %p",
stack_desc->reference.target_type,
stack_desc));
status = AE_AML_INTERNAL;
@@ -251,7 +243,7 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr,
case AML_DEBUG_OP:
case AML_LOAD_OP:
- /* Just leave the object as-is */
+ /* Just leave the object as-is, do not dereference */
break;
@@ -390,10 +382,10 @@ acpi_ex_resolve_multiple(struct acpi_walk_state *walk_state,
}
/*
- * For reference objects created via the ref_of or Index operators,
- * we need to get to the base object (as per the ACPI specification
- * of the object_type and size_of operators). This means traversing
- * the list of possibly many nested references.
+ * For reference objects created via the ref_of, Index, or Load/load_table
+ * operators, we need to get to the base object (as per the ACPI
+ * specification of the object_type and size_of operators). This means
+ * traversing the list of possibly many nested references.
*/
while (ACPI_GET_OBJECT_TYPE(obj_desc) == ACPI_TYPE_LOCAL_REFERENCE) {
switch (obj_desc->reference.opcode) {
@@ -463,6 +455,11 @@ acpi_ex_resolve_multiple(struct acpi_walk_state *walk_state,
}
break;
+ case AML_LOAD_OP:
+
+ type = ACPI_TYPE_DDB_HANDLE;
+ goto exit;
+
case AML_LOCAL_OP:
case AML_ARG_OP:
diff --git a/drivers/acpi/executer/exresop.c b/drivers/acpi/executer/exresop.c
index 09d897b3f6d..73e29e566a7 100644
--- a/drivers/acpi/executer/exresop.c
+++ b/drivers/acpi/executer/exresop.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -137,7 +137,6 @@ acpi_ex_resolve_operands(u16 opcode,
union acpi_operand_object *obj_desc;
acpi_status status = AE_OK;
u8 object_type;
- void *temp_node;
u32 arg_types;
const struct acpi_opcode_info *op_info;
u32 this_arg_type;
@@ -239,7 +238,6 @@ acpi_ex_resolve_operands(u16 opcode,
/*lint -fallthrough */
- case AML_NAME_OP:
case AML_INDEX_OP:
case AML_REF_OF_OP:
case AML_ARG_OP:
@@ -332,15 +330,6 @@ acpi_ex_resolve_operands(u16 opcode,
if (ACPI_FAILURE(status)) {
return_ACPI_STATUS(status);
}
-
- if (obj_desc->reference.opcode == AML_NAME_OP) {
-
- /* Convert a named reference to the actual named object */
-
- temp_node = obj_desc->reference.object;
- acpi_ut_remove_reference(obj_desc);
- (*stack_ptr) = temp_node;
- }
goto next_operand;
case ARGI_DATAREFOBJ: /* Store operator only */
diff --git a/drivers/acpi/executer/exstore.c b/drivers/acpi/executer/exstore.c
index f4b69a63782..76c875bc315 100644
--- a/drivers/acpi/executer/exstore.c
+++ b/drivers/acpi/executer/exstore.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -84,8 +84,12 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
ACPI_FUNCTION_TRACE_PTR(ex_do_debug_object, source_desc);
- ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "[ACPI Debug] %*s",
- level, " "));
+ /* Print line header as long as we are not in the middle of an object display */
+
+ if (!((level > 0) && index == 0)) {
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "[ACPI Debug] %*s",
+ level, " "));
+ }
/* Display index for package output only */
@@ -95,12 +99,12 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
}
if (!source_desc) {
- ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "<Null Object>\n"));
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "[Null Object]\n"));
return_VOID;
}
if (ACPI_GET_DESCRIPTOR_TYPE(source_desc) == ACPI_DESC_TYPE_OPERAND) {
- ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "%s: ",
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "%s ",
acpi_ut_get_object_type_name
(source_desc)));
@@ -123,6 +127,8 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
return_VOID;
}
+ /* source_desc is of type ACPI_DESC_TYPE_OPERAND */
+
switch (ACPI_GET_OBJECT_TYPE(source_desc)) {
case ACPI_TYPE_INTEGER:
@@ -147,7 +153,7 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
(u32) source_desc->buffer.length));
ACPI_DUMP_BUFFER(source_desc->buffer.pointer,
(source_desc->buffer.length <
- 32) ? source_desc->buffer.length : 32);
+ 256) ? source_desc->buffer.length : 256);
break;
case ACPI_TYPE_STRING:
@@ -160,7 +166,7 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
case ACPI_TYPE_PACKAGE:
ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT,
- "[0x%.2X Elements]\n",
+ "[Contains 0x%.2X Elements]\n",
source_desc->package.count));
/* Output the entire contents of the package */
@@ -180,12 +186,59 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
(source_desc->reference.opcode),
source_desc->reference.offset));
} else {
- ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "[%s]\n",
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "[%s]",
acpi_ps_get_opcode_name
(source_desc->reference.opcode)));
}
- if (source_desc->reference.object) {
+ if (source_desc->reference.opcode == AML_LOAD_OP) { /* Load and load_table */
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT,
+ " Table OwnerId %p\n",
+ source_desc->reference.object));
+ break;
+ }
+
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, " "));
+
+ /* Check for valid node first, then valid object */
+
+ if (source_desc->reference.node) {
+ if (ACPI_GET_DESCRIPTOR_TYPE
+ (source_desc->reference.node) !=
+ ACPI_DESC_TYPE_NAMED) {
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT,
+ " %p - Not a valid namespace node\n",
+ source_desc->reference.
+ node));
+ } else {
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT,
+ "Node %p [%4.4s] ",
+ source_desc->reference.
+ node,
+ (source_desc->reference.
+ node)->name.ascii));
+
+ switch ((source_desc->reference.node)->type) {
+
+ /* These types have no attached object */
+
+ case ACPI_TYPE_DEVICE:
+ acpi_os_printf("Device\n");
+ break;
+
+ case ACPI_TYPE_THERMAL:
+ acpi_os_printf("Thermal Zone\n");
+ break;
+
+ default:
+ acpi_ex_do_debug_object((source_desc->
+ reference.
+ node)->object,
+ level + 4, 0);
+ break;
+ }
+ }
+ } else if (source_desc->reference.object) {
if (ACPI_GET_DESCRIPTOR_TYPE
(source_desc->reference.object) ==
ACPI_DESC_TYPE_NAMED) {
@@ -198,18 +251,13 @@ acpi_ex_do_debug_object(union acpi_operand_object *source_desc,
acpi_ex_do_debug_object(source_desc->reference.
object, level + 4, 0);
}
- } else if (source_desc->reference.node) {
- acpi_ex_do_debug_object((source_desc->reference.node)->
- object, level + 4, 0);
}
break;
default:
- ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "%p %s\n",
- source_desc,
- acpi_ut_get_object_type_name
- (source_desc)));
+ ACPI_DEBUG_PRINT_RAW((ACPI_DB_DEBUG_OBJECT, "%p\n",
+ source_desc));
break;
}
@@ -313,7 +361,6 @@ acpi_ex_store(union acpi_operand_object *source_desc,
* 4) Store to the debug object
*/
switch (ref_desc->reference.opcode) {
- case AML_NAME_OP:
case AML_REF_OF_OP:
/* Storing an object into a Name "container" */
@@ -415,11 +462,24 @@ acpi_ex_store_object_to_index(union acpi_operand_object *source_desc,
*/
obj_desc = *(index_desc->reference.where);
- status =
- acpi_ut_copy_iobject_to_iobject(source_desc, &new_desc,
- walk_state);
- if (ACPI_FAILURE(status)) {
- return_ACPI_STATUS(status);
+ if (ACPI_GET_OBJECT_TYPE(source_desc) ==
+ ACPI_TYPE_LOCAL_REFERENCE
+ && source_desc->reference.opcode == AML_LOAD_OP) {
+
+ /* This is a DDBHandle, just add a reference to it */
+
+ acpi_ut_add_reference(source_desc);
+ new_desc = source_desc;
+ } else {
+ /* Normal object, copy it */
+
+ status =
+ acpi_ut_copy_iobject_to_iobject(source_desc,
+ &new_desc,
+ walk_state);
+ if (ACPI_FAILURE(status)) {
+ return_ACPI_STATUS(status);
+ }
}
if (obj_desc) {
@@ -571,10 +631,17 @@ acpi_ex_store_object_to_node(union acpi_operand_object *source_desc,
/* If no implicit conversion, drop into the default case below */
- if ((!implicit_conversion) || (walk_state->opcode == AML_COPY_OP)) {
-
- /* Force execution of default (no implicit conversion) */
-
+ if ((!implicit_conversion) ||
+ ((walk_state->opcode == AML_COPY_OP) &&
+ (target_type != ACPI_TYPE_LOCAL_REGION_FIELD) &&
+ (target_type != ACPI_TYPE_LOCAL_BANK_FIELD) &&
+ (target_type != ACPI_TYPE_LOCAL_INDEX_FIELD))) {
+ /*
+ * Force execution of default (no implicit conversion). Note:
+ * copy_object does not perform an implicit conversion, as per the ACPI
+ * spec -- except in case of region/bank/index fields -- because these
+ * objects must retain their original type permanently.
+ */
target_type = ACPI_TYPE_ANY;
}
diff --git a/drivers/acpi/executer/exstoren.c b/drivers/acpi/executer/exstoren.c
index 1d622c625c6..a6d2168b81f 100644
--- a/drivers/acpi/executer/exstoren.c
+++ b/drivers/acpi/executer/exstoren.c
@@ -7,7 +7,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
diff --git a/drivers/acpi/executer/exstorob.c b/drivers/acpi/executer/exstorob.c
index 8233d40178e..9a75ff09fb0 100644
--- a/drivers/acpi/executer/exstorob.c
+++ b/drivers/acpi/executer/exstorob.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
diff --git a/drivers/acpi/executer/exsystem.c b/drivers/acpi/executer/exsystem.c
index 9460baff303..68990f1df37 100644
--- a/drivers/acpi/executer/exsystem.c
+++ b/drivers/acpi/executer/exsystem.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -44,7 +44,6 @@
#include <acpi/acpi.h>
#include <acpi/acinterp.h>
-#include <acpi/acevents.h>
#define _COMPONENT ACPI_EXECUTER
ACPI_MODULE_NAME("exsystem")
diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c
index 6b0aeccbb69..86c03880b52 100644
--- a/drivers/acpi/executer/exutils.c
+++ b/drivers/acpi/executer/exutils.c
@@ -6,7 +6,7 @@
*****************************************************************************/
/*
- * Copyright (C) 2000 - 2007, R. Byron Moore
+ * Copyright (C) 2000 - 2008, Intel Corp.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -61,7 +61,6 @@
#include <acpi/acpi.h>
#include <acpi/acinterp.h>
#include <acpi/amlcode.h>
-#include <acpi/acevents.h>
#define _COMPONENT ACPI_EXECUTER
ACPI_MODULE_NAME("exutils")
@@ -217,9 +216,10 @@ void acpi_ex_truncate_for32bit_table(union acpi_operand_object *obj_desc)
/*
* Object must be a valid number and we must be executing
- * a control method
+ * a control method. NS node could be there for AML_INT_NAMEPATH_OP.
*/
if ((!obj_desc) ||
+ (ACPI_GET_DESCRIPTOR_TYPE(obj_desc) != ACPI_DESC_TYPE_OPERAND) ||
(ACPI_GET_OBJECT_TYPE(obj_desc) != ACPI_TYPE_INTEGER)) {
return;
}
@@ -240,72 +240,73 @@ void acpi_ex_truncate_for32bit_table(union acpi_operand_object *obj_desc)
* PARAMETERS: field_flags - Flags with Lock rule:
* always_lock or never_lock
*
- * RETURN: TRUE/FALSE indicating whether the lock was actually acquired
+ * RETURN: None
*
- * DESCRIPTION: Obtain the global lock and keep track of this fact via two
- * methods. A global variable keeps the state of the lock, and
- * the state is returned to the caller.
+ * DESCRIPTION: Obtain the ACPI hardware Global Lock, only if the field
+ * flags specifiy that it is to be obtained before field access.
*
******************************************************************************/
-u8 acpi_ex_acquire_global_lock(u32 field_flags)
+void acpi_ex_acquire_global_lock(u32 field_flags)
{
- u8 locked = FALSE;
acpi_status status;
ACPI_FUNCTION_TRACE(ex_acquire_global_lock);
- /* Only attempt lock if the always_lock bit is set */
+ /* Only use the lock if the always_lock bit is set */
+
+ if (!(field_flags & AML_FIELD_LOCK_RULE_MASK)) {
+ return_VOID;
+ }
- if (field_flags & AML_FIELD_LOCK_RULE_MASK) {
+ /* Attempt to get the global lock, wait forever */
- /* We should attempt to get the lock, wait forever */
+ status = acpi_ex_acquire_mutex_object(ACPI_WAIT_FOREVER,
+ acpi_gbl_global_lock_mutex,
+ acpi_os_get_thread_id());
- status = acpi_ev_acquire_global_lock(ACPI_WAIT_FOREVER);
- if (ACPI_SUCCESS(status)) {
- locked = TRUE;
- } else {
- ACPI_EXCEPTION((AE_INFO, status,
- "Could not acquire Global Lock"));
- }
+ if (ACPI_FAILURE(status)) {
+ ACPI_EXCEPTION((AE_INFO, status,
+ "Could not acquire Global Lock"));
}
- return_UINT8(locked);
+ return_VOID;
}
/*******************************************************************************
*
* FUNCTION: acpi_ex_release_global_lock
*
- * PARAMETERS: locked_by_me - Return value from corresponding call to
- * acquire_global_lock.
+ * PARAMETERS: field_flags - Flags with Lock rule:
+ * always_lock or never_lock
*
* RETURN: None
*
- * DESCRIPTION: Release the global lock if it is locked.
+ * DESCRIPTION: Release the ACPI hardware Global Lock
*
******************************************************************************/
-void acpi_ex_release_global_lock(u8 locked_by_me)
+void acpi_ex_release_global_lock(u32 field_flags)
{
acpi_status status;
ACPI_FUNCTION_TRACE(ex_release_global_lock);
- /* Only attempt unlock if the caller locked it */
+ /* Only use the lock if the always_lock bit is set */
- if (locked_by_me) {
+ if (!(field_flags & AML_FIELD_LOCK_RULE_MASK)) {
+ return_VOID;
+ }
- /* OK, now release the lock */
+ /* Release the global lock */
- status = acpi_ev_release_global_lock();
- if (ACPI_FAILURE(status)) {
+ status = acpi_ex_release_mutex_object(acpi_gbl_global_lock_mutex);
+ if (ACPI_FAILURE(status)) {
- /* Report the error, but there isn't much else we can do */
+ /* Report the error, but there isn't much else we can do */
- ACPI_EXCEPTION((AE_INFO, status,
- "Could not release ACPI Global Lock"));
- }
+ ACPI_EXCEPTION((AE_INFO, status,
+ "Could not release Global Lock"));
}
return_VOID;