diff options
author | Bob Moore <robert.moore@intel.com> | 2009-12-11 02:16:38 -0500 |
---|---|---|
committer | Len Brown <len.brown@intel.com> | 2009-12-15 17:29:36 -0500 |
commit | d97659112044c0c77b93c6199eee7ee884eb3cca (patch) | |
tree | cc1f8d167cdd2af02b6661bc326649732f611009 /drivers/acpi/acpica | |
parent | 90434c1c7c61ce7dd349f17f003b8813421aeadc (diff) |
ACPICA: Fix mutex errors when running _REG methods
Fixes a problem where mutex errors can occur when running a _REG
method that is in the same scope as a method-defined operation
region or an operation region under a module-level IF block.
This is rare, so the problem has not been seen before.
ACPICA BZ 826.
http://www.acpica.org/bugzilla/show_bug.cgi?id=826
Signed-off-by: Bob Moore <robert.moore@intel.com>
Signed-off-by: Lin Ming <ming.m.lin@intel.com>
Signed-off-by: Len Brown <len.brown@intel.com>
Diffstat (limited to 'drivers/acpi/acpica')
-rw-r--r-- | drivers/acpi/acpica/dswload.c | 31 |
1 files changed, 20 insertions, 11 deletions
diff --git a/drivers/acpi/acpica/dswload.c b/drivers/acpi/acpica/dswload.c index 9cc2289f872e..b40513dd6a6a 100644 --- a/drivers/acpi/acpica/dswload.c +++ b/drivers/acpi/acpica/dswload.c | |||
@@ -1052,9 +1052,22 @@ acpi_status acpi_ds_load2_end_op(struct acpi_walk_state *walk_state) | |||
1052 | } | 1052 | } |
1053 | 1053 | ||
1054 | /* | 1054 | /* |
1055 | * If we are executing a method, initialize the region | 1055 | * The op_region is not fully parsed at this time. The only valid |
1056 | * argument is the space_id. (We must save the address of the | ||
1057 | * AML of the address and length operands) | ||
1058 | * | ||
1059 | * If we have a valid region, initialize it. The namespace is | ||
1060 | * unlocked at this point. | ||
1061 | * | ||
1062 | * Need to unlock interpreter if it is locked (if we are running | ||
1063 | * a control method), in order to allow _REG methods to be run | ||
1064 | * during acpi_ev_initialize_region. | ||
1056 | */ | 1065 | */ |
1057 | if (walk_state->method_node) { | 1066 | if (walk_state->method_node) { |
1067 | /* | ||
1068 | * Executing a method: initialize the region and unlock | ||
1069 | * the interpreter | ||
1070 | */ | ||
1058 | status = | 1071 | status = |
1059 | acpi_ex_create_region(op->named.data, | 1072 | acpi_ex_create_region(op->named.data, |
1060 | op->named.length, | 1073 | op->named.length, |
@@ -1063,21 +1076,17 @@ acpi_status acpi_ds_load2_end_op(struct acpi_walk_state *walk_state) | |||
1063 | if (ACPI_FAILURE(status)) { | 1076 | if (ACPI_FAILURE(status)) { |
1064 | return (status); | 1077 | return (status); |
1065 | } | 1078 | } |
1066 | } | ||
1067 | 1079 | ||
1068 | /* | 1080 | acpi_ex_exit_interpreter(); |
1069 | * The op_region is not fully parsed at this time. Only valid | 1081 | } |
1070 | * argument is the space_id. (We must save the address of the | ||
1071 | * AML of the address and length operands) | ||
1072 | */ | ||
1073 | 1082 | ||
1074 | /* | ||
1075 | * If we have a valid region, initialize it | ||
1076 | * Namespace is NOT locked at this point. | ||
1077 | */ | ||
1078 | status = | 1083 | status = |
1079 | acpi_ev_initialize_region | 1084 | acpi_ev_initialize_region |
1080 | (acpi_ns_get_attached_object(node), FALSE); | 1085 | (acpi_ns_get_attached_object(node), FALSE); |
1086 | if (walk_state->method_node) { | ||
1087 | acpi_ex_enter_interpreter(); | ||
1088 | } | ||
1089 | |||
1081 | if (ACPI_FAILURE(status)) { | 1090 | if (ACPI_FAILURE(status)) { |
1082 | /* | 1091 | /* |
1083 | * If AE_NOT_EXIST is returned, it is not fatal | 1092 | * If AE_NOT_EXIST is returned, it is not fatal |