diff options
author | Len Brown <len.brown@intel.com> | 2005-08-04 18:09:09 -0400 |
---|---|---|
committer | Len Brown <len.brown@intel.com> | 2005-08-04 18:09:09 -0400 |
commit | 5d2a22079c825669d91a3a200332f1053b4b61b0 (patch) | |
tree | 2e6e88bbcc3e17535fdf3103540b246b3658e20b /drivers/acpi | |
parent | 1c5ad84516ae7ea4ec868436a910a6bd8d20215a (diff) | |
parent | bd6dbdf3c7b9784fbf5d8500e427a954e27a976a (diff) |
/home/lenb/src/to-akpm branch 'acpi-2.6.12'
Diffstat (limited to 'drivers/acpi')
61 files changed, 3409 insertions, 2698 deletions
diff --git a/drivers/acpi/dispatcher/dsinit.c b/drivers/acpi/dispatcher/dsinit.c index d7790db50178..bcd1d472b90f 100644 --- a/drivers/acpi/dispatcher/dsinit.c +++ b/drivers/acpi/dispatcher/dsinit.c | |||
@@ -86,20 +86,20 @@ acpi_ds_init_one_object ( | |||
86 | void *context, | 86 | void *context, |
87 | void **return_value) | 87 | void **return_value) |
88 | { | 88 | { |
89 | struct acpi_init_walk_info *info = (struct acpi_init_walk_info *) context; | ||
90 | struct acpi_namespace_node *node = (struct acpi_namespace_node *) obj_handle; | ||
89 | acpi_object_type type; | 91 | acpi_object_type type; |
90 | acpi_status status; | 92 | acpi_status status; |
91 | struct acpi_init_walk_info *info = (struct acpi_init_walk_info *) context; | ||
92 | 93 | ||
93 | 94 | ||
94 | ACPI_FUNCTION_NAME ("ds_init_one_object"); | 95 | ACPI_FUNCTION_NAME ("ds_init_one_object"); |
95 | 96 | ||
96 | 97 | ||
97 | /* | 98 | /* |
98 | * We are only interested in objects owned by the table that | 99 | * We are only interested in NS nodes owned by the table that |
99 | * was just loaded | 100 | * was just loaded |
100 | */ | 101 | */ |
101 | if (((struct acpi_namespace_node *) obj_handle)->owner_id != | 102 | if (node->owner_id != info->table_desc->owner_id) { |
102 | info->table_desc->table_id) { | ||
103 | return (AE_OK); | 103 | return (AE_OK); |
104 | } | 104 | } |
105 | 105 | ||
@@ -126,8 +126,6 @@ acpi_ds_init_one_object ( | |||
126 | 126 | ||
127 | case ACPI_TYPE_METHOD: | 127 | case ACPI_TYPE_METHOD: |
128 | 128 | ||
129 | info->method_count++; | ||
130 | |||
131 | /* | 129 | /* |
132 | * Print a dot for each method unless we are going to print | 130 | * Print a dot for each method unless we are going to print |
133 | * the entire pathname | 131 | * the entire pathname |
@@ -143,7 +141,7 @@ acpi_ds_init_one_object ( | |||
143 | * on a per-table basis. Currently, we just use a global for the width. | 141 | * on a per-table basis. Currently, we just use a global for the width. |
144 | */ | 142 | */ |
145 | if (info->table_desc->pointer->revision == 1) { | 143 | if (info->table_desc->pointer->revision == 1) { |
146 | ((struct acpi_namespace_node *) obj_handle)->flags |= ANOBJ_DATA_WIDTH_32; | 144 | node->flags |= ANOBJ_DATA_WIDTH_32; |
147 | } | 145 | } |
148 | 146 | ||
149 | /* | 147 | /* |
@@ -153,22 +151,14 @@ acpi_ds_init_one_object ( | |||
153 | status = acpi_ds_parse_method (obj_handle); | 151 | status = acpi_ds_parse_method (obj_handle); |
154 | if (ACPI_FAILURE (status)) { | 152 | if (ACPI_FAILURE (status)) { |
155 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | 153 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, |
156 | "Method %p [%4.4s] - parse failure, %s\n", | 154 | "\n+Method %p [%4.4s] - parse failure, %s\n", |
157 | obj_handle, acpi_ut_get_node_name (obj_handle), | 155 | obj_handle, acpi_ut_get_node_name (obj_handle), |
158 | acpi_format_exception (status))); | 156 | acpi_format_exception (status))); |
159 | 157 | ||
160 | /* This parse failed, but we will continue parsing more methods */ | 158 | /* This parse failed, but we will continue parsing more methods */ |
161 | |||
162 | break; | ||
163 | } | 159 | } |
164 | 160 | ||
165 | /* | 161 | info->method_count++; |
166 | * Delete the parse tree. We simply re-parse the method | ||
167 | * for every execution since there isn't much overhead | ||
168 | */ | ||
169 | acpi_ns_delete_namespace_subtree (obj_handle); | ||
170 | acpi_ns_delete_namespace_by_owner ( | ||
171 | ((struct acpi_namespace_node *) obj_handle)->object->method.owning_id); | ||
172 | break; | 162 | break; |
173 | 163 | ||
174 | 164 | ||
@@ -237,7 +227,7 @@ acpi_ds_initialize_objects ( | |||
237 | 227 | ||
238 | ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INIT, | 228 | ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INIT, |
239 | "\nTable [%4.4s](id %4.4X) - %hd Objects with %hd Devices %hd Methods %hd Regions\n", | 229 | "\nTable [%4.4s](id %4.4X) - %hd Objects with %hd Devices %hd Methods %hd Regions\n", |
240 | table_desc->pointer->signature, table_desc->table_id, info.object_count, | 230 | table_desc->pointer->signature, table_desc->owner_id, info.object_count, |
241 | info.device_count, info.method_count, info.op_region_count)); | 231 | info.device_count, info.method_count, info.op_region_count)); |
242 | 232 | ||
243 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, | 233 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, |
diff --git a/drivers/acpi/dispatcher/dsmethod.c b/drivers/acpi/dispatcher/dsmethod.c index 9fc3f4c033eb..e344c06ed33f 100644 --- a/drivers/acpi/dispatcher/dsmethod.c +++ b/drivers/acpi/dispatcher/dsmethod.c | |||
@@ -58,12 +58,11 @@ | |||
58 | * | 58 | * |
59 | * FUNCTION: acpi_ds_parse_method | 59 | * FUNCTION: acpi_ds_parse_method |
60 | * | 60 | * |
61 | * PARAMETERS: obj_handle - Method node | 61 | * PARAMETERS: Node - Method node |
62 | * | 62 | * |
63 | * RETURN: Status | 63 | * RETURN: Status |
64 | * | 64 | * |
65 | * DESCRIPTION: Call the parser and parse the AML that is associated with the | 65 | * DESCRIPTION: Parse the AML that is associated with the method. |
66 | * method. | ||
67 | * | 66 | * |
68 | * MUTEX: Assumes parser is locked | 67 | * MUTEX: Assumes parser is locked |
69 | * | 68 | * |
@@ -71,31 +70,28 @@ | |||
71 | 70 | ||
72 | acpi_status | 71 | acpi_status |
73 | acpi_ds_parse_method ( | 72 | acpi_ds_parse_method ( |
74 | acpi_handle obj_handle) | 73 | struct acpi_namespace_node *node) |
75 | { | 74 | { |
76 | acpi_status status; | 75 | acpi_status status; |
77 | union acpi_operand_object *obj_desc; | 76 | union acpi_operand_object *obj_desc; |
78 | union acpi_parse_object *op; | 77 | union acpi_parse_object *op; |
79 | struct acpi_namespace_node *node; | ||
80 | acpi_owner_id owner_id; | ||
81 | struct acpi_walk_state *walk_state; | 78 | struct acpi_walk_state *walk_state; |
82 | 79 | ||
83 | 80 | ||
84 | ACPI_FUNCTION_TRACE_PTR ("ds_parse_method", obj_handle); | 81 | ACPI_FUNCTION_TRACE_PTR ("ds_parse_method", node); |
85 | 82 | ||
86 | 83 | ||
87 | /* Parameter Validation */ | 84 | /* Parameter Validation */ |
88 | 85 | ||
89 | if (!obj_handle) { | 86 | if (!node) { |
90 | return_ACPI_STATUS (AE_NULL_ENTRY); | 87 | return_ACPI_STATUS (AE_NULL_ENTRY); |
91 | } | 88 | } |
92 | 89 | ||
93 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "**** Parsing [%4.4s] **** named_obj=%p\n", | 90 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "**** Parsing [%4.4s] **** named_obj=%p\n", |
94 | acpi_ut_get_node_name (obj_handle), obj_handle)); | 91 | acpi_ut_get_node_name (node), node)); |
95 | 92 | ||
96 | /* Extract the method object from the method Node */ | 93 | /* Extract the method object from the method Node */ |
97 | 94 | ||
98 | node = (struct acpi_namespace_node *) obj_handle; | ||
99 | obj_desc = acpi_ns_get_attached_object (node); | 95 | obj_desc = acpi_ns_get_attached_object (node); |
100 | if (!obj_desc) { | 96 | if (!obj_desc) { |
101 | return_ACPI_STATUS (AE_NULL_OBJECT); | 97 | return_ACPI_STATUS (AE_NULL_OBJECT); |
@@ -132,14 +128,18 @@ acpi_ds_parse_method ( | |||
132 | * objects (such as Operation Regions) can be created during the | 128 | * objects (such as Operation Regions) can be created during the |
133 | * first pass parse. | 129 | * first pass parse. |
134 | */ | 130 | */ |
135 | owner_id = acpi_ut_allocate_owner_id (ACPI_OWNER_TYPE_METHOD); | 131 | status = acpi_ut_allocate_owner_id (&obj_desc->method.owner_id); |
136 | obj_desc->method.owning_id = owner_id; | 132 | if (ACPI_FAILURE (status)) { |
133 | goto cleanup; | ||
134 | } | ||
137 | 135 | ||
138 | /* Create and initialize a new walk state */ | 136 | /* Create and initialize a new walk state */ |
139 | 137 | ||
140 | walk_state = acpi_ds_create_walk_state (owner_id, NULL, NULL, NULL); | 138 | walk_state = acpi_ds_create_walk_state ( |
139 | obj_desc->method.owner_id, NULL, NULL, NULL); | ||
141 | if (!walk_state) { | 140 | if (!walk_state) { |
142 | return_ACPI_STATUS (AE_NO_MEMORY); | 141 | status = AE_NO_MEMORY; |
142 | goto cleanup2; | ||
143 | } | 143 | } |
144 | 144 | ||
145 | status = acpi_ds_init_aml_walk (walk_state, op, node, | 145 | status = acpi_ds_init_aml_walk (walk_state, op, node, |
@@ -147,7 +147,7 @@ acpi_ds_parse_method ( | |||
147 | obj_desc->method.aml_length, NULL, 1); | 147 | obj_desc->method.aml_length, NULL, 1); |
148 | if (ACPI_FAILURE (status)) { | 148 | if (ACPI_FAILURE (status)) { |
149 | acpi_ds_delete_walk_state (walk_state); | 149 | acpi_ds_delete_walk_state (walk_state); |
150 | return_ACPI_STATUS (status); | 150 | goto cleanup2; |
151 | } | 151 | } |
152 | 152 | ||
153 | /* | 153 | /* |
@@ -161,13 +161,25 @@ acpi_ds_parse_method ( | |||
161 | */ | 161 | */ |
162 | status = acpi_ps_parse_aml (walk_state); | 162 | status = acpi_ps_parse_aml (walk_state); |
163 | if (ACPI_FAILURE (status)) { | 163 | if (ACPI_FAILURE (status)) { |
164 | return_ACPI_STATUS (status); | 164 | goto cleanup2; |
165 | } | 165 | } |
166 | 166 | ||
167 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | 167 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, |
168 | "**** [%4.4s] Parsed **** named_obj=%p Op=%p\n", | 168 | "**** [%4.4s] Parsed **** named_obj=%p Op=%p\n", |
169 | acpi_ut_get_node_name (obj_handle), obj_handle, op)); | 169 | acpi_ut_get_node_name (node), node, op)); |
170 | |||
171 | /* | ||
172 | * Delete the parse tree. We simply re-parse the method for every | ||
173 | * execution since there isn't much overhead (compared to keeping lots | ||
174 | * of parse trees around) | ||
175 | */ | ||
176 | acpi_ns_delete_namespace_subtree (node); | ||
177 | acpi_ns_delete_namespace_by_owner (obj_desc->method.owner_id); | ||
178 | |||
179 | cleanup2: | ||
180 | acpi_ut_release_owner_id (&obj_desc->method.owner_id); | ||
170 | 181 | ||
182 | cleanup: | ||
171 | acpi_ps_delete_parse_tree (op); | 183 | acpi_ps_delete_parse_tree (op); |
172 | return_ACPI_STATUS (status); | 184 | return_ACPI_STATUS (status); |
173 | } | 185 | } |
@@ -263,7 +275,7 @@ acpi_ds_call_control_method ( | |||
263 | { | 275 | { |
264 | acpi_status status; | 276 | acpi_status status; |
265 | struct acpi_namespace_node *method_node; | 277 | struct acpi_namespace_node *method_node; |
266 | struct acpi_walk_state *next_walk_state; | 278 | struct acpi_walk_state *next_walk_state = NULL; |
267 | union acpi_operand_object *obj_desc; | 279 | union acpi_operand_object *obj_desc; |
268 | struct acpi_parameter_info info; | 280 | struct acpi_parameter_info info; |
269 | u32 i; | 281 | u32 i; |
@@ -287,20 +299,23 @@ acpi_ds_call_control_method ( | |||
287 | return_ACPI_STATUS (AE_NULL_OBJECT); | 299 | return_ACPI_STATUS (AE_NULL_OBJECT); |
288 | } | 300 | } |
289 | 301 | ||
290 | obj_desc->method.owning_id = acpi_ut_allocate_owner_id (ACPI_OWNER_TYPE_METHOD); | 302 | status = acpi_ut_allocate_owner_id (&obj_desc->method.owner_id); |
303 | if (ACPI_FAILURE (status)) { | ||
304 | return_ACPI_STATUS (status); | ||
305 | } | ||
291 | 306 | ||
292 | /* Init for new method, wait on concurrency semaphore */ | 307 | /* Init for new method, wait on concurrency semaphore */ |
293 | 308 | ||
294 | status = acpi_ds_begin_method_execution (method_node, obj_desc, | 309 | status = acpi_ds_begin_method_execution (method_node, obj_desc, |
295 | this_walk_state->method_node); | 310 | this_walk_state->method_node); |
296 | if (ACPI_FAILURE (status)) { | 311 | if (ACPI_FAILURE (status)) { |
297 | return_ACPI_STATUS (status); | 312 | goto cleanup; |
298 | } | 313 | } |
299 | 314 | ||
300 | if (!(obj_desc->method.method_flags & AML_METHOD_INTERNAL_ONLY)) { | 315 | if (!(obj_desc->method.method_flags & AML_METHOD_INTERNAL_ONLY)) { |
301 | /* 1) Parse: Create a new walk state for the preempting walk */ | 316 | /* 1) Parse: Create a new walk state for the preempting walk */ |
302 | 317 | ||
303 | next_walk_state = acpi_ds_create_walk_state (obj_desc->method.owning_id, | 318 | next_walk_state = acpi_ds_create_walk_state (obj_desc->method.owner_id, |
304 | op, obj_desc, NULL); | 319 | op, obj_desc, NULL); |
305 | if (!next_walk_state) { | 320 | if (!next_walk_state) { |
306 | return_ACPI_STATUS (AE_NO_MEMORY); | 321 | return_ACPI_STATUS (AE_NO_MEMORY); |
@@ -330,7 +345,7 @@ acpi_ds_call_control_method ( | |||
330 | 345 | ||
331 | /* 2) Execute: Create a new state for the preempting walk */ | 346 | /* 2) Execute: Create a new state for the preempting walk */ |
332 | 347 | ||
333 | next_walk_state = acpi_ds_create_walk_state (obj_desc->method.owning_id, | 348 | next_walk_state = acpi_ds_create_walk_state (obj_desc->method.owner_id, |
334 | NULL, obj_desc, thread); | 349 | NULL, obj_desc, thread); |
335 | if (!next_walk_state) { | 350 | if (!next_walk_state) { |
336 | status = AE_NO_MEMORY; | 351 | status = AE_NO_MEMORY; |
@@ -381,6 +396,7 @@ acpi_ds_call_control_method ( | |||
381 | /* On error, we must delete the new walk state */ | 396 | /* On error, we must delete the new walk state */ |
382 | 397 | ||
383 | cleanup: | 398 | cleanup: |
399 | acpi_ut_release_owner_id (&obj_desc->method.owner_id); | ||
384 | if (next_walk_state && (next_walk_state->method_desc)) { | 400 | if (next_walk_state && (next_walk_state->method_desc)) { |
385 | /* Decrement the thread count on the method parse tree */ | 401 | /* Decrement the thread count on the method parse tree */ |
386 | 402 | ||
@@ -552,8 +568,7 @@ acpi_ds_terminate_control_method ( | |||
552 | */ | 568 | */ |
553 | if ((walk_state->method_desc->method.concurrency == 1) && | 569 | if ((walk_state->method_desc->method.concurrency == 1) && |
554 | (!walk_state->method_desc->method.semaphore)) { | 570 | (!walk_state->method_desc->method.semaphore)) { |
555 | status = acpi_os_create_semaphore (1, | 571 | status = acpi_os_create_semaphore (1, 1, |
556 | 1, | ||
557 | &walk_state->method_desc->method.semaphore); | 572 | &walk_state->method_desc->method.semaphore); |
558 | } | 573 | } |
559 | 574 | ||
@@ -582,8 +597,10 @@ acpi_ds_terminate_control_method ( | |||
582 | * Delete any namespace entries created anywhere else within | 597 | * Delete any namespace entries created anywhere else within |
583 | * the namespace | 598 | * the namespace |
584 | */ | 599 | */ |
585 | acpi_ns_delete_namespace_by_owner (walk_state->method_desc->method.owning_id); | 600 | acpi_ns_delete_namespace_by_owner (walk_state->method_desc->method.owner_id); |
586 | status = acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); | 601 | status = acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); |
602 | acpi_ut_release_owner_id (&walk_state->method_desc->method.owner_id); | ||
603 | |||
587 | if (ACPI_FAILURE (status)) { | 604 | if (ACPI_FAILURE (status)) { |
588 | return_ACPI_STATUS (status); | 605 | return_ACPI_STATUS (status); |
589 | } | 606 | } |
diff --git a/drivers/acpi/dispatcher/dsmthdat.c b/drivers/acpi/dispatcher/dsmthdat.c index f7998306f756..c83d53fd6398 100644 --- a/drivers/acpi/dispatcher/dsmthdat.c +++ b/drivers/acpi/dispatcher/dsmthdat.c | |||
@@ -633,22 +633,11 @@ acpi_ds_store_object_to_local ( | |||
633 | */ | 633 | */ |
634 | if (opcode == AML_ARG_OP) { | 634 | if (opcode == AML_ARG_OP) { |
635 | /* | 635 | /* |
636 | * Make sure that the object is the correct type. This may be | ||
637 | * overkill, butit is here because references were NS nodes in | ||
638 | * the past. Now they are operand objects of type Reference. | ||
639 | */ | ||
640 | if (ACPI_GET_DESCRIPTOR_TYPE (current_obj_desc) != ACPI_DESC_TYPE_OPERAND) { | ||
641 | ACPI_REPORT_ERROR (( | ||
642 | "Invalid descriptor type while storing to method arg: [%s]\n", | ||
643 | acpi_ut_get_descriptor_name (current_obj_desc))); | ||
644 | return_ACPI_STATUS (AE_AML_INTERNAL); | ||
645 | } | ||
646 | |||
647 | /* | ||
648 | * If we have a valid reference object that came from ref_of(), | 636 | * If we have a valid reference object that came from ref_of(), |
649 | * do the indirect store | 637 | * do the indirect store |
650 | */ | 638 | */ |
651 | if ((current_obj_desc->common.type == ACPI_TYPE_LOCAL_REFERENCE) && | 639 | if ((ACPI_GET_DESCRIPTOR_TYPE (current_obj_desc) == ACPI_DESC_TYPE_OPERAND) && |
640 | (current_obj_desc->common.type == ACPI_TYPE_LOCAL_REFERENCE) && | ||
652 | (current_obj_desc->reference.opcode == AML_REF_OF_OP)) { | 641 | (current_obj_desc->reference.opcode == AML_REF_OF_OP)) { |
653 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, | 642 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, |
654 | "Arg (%p) is an obj_ref(Node), storing in node %p\n", | 643 | "Arg (%p) is an obj_ref(Node), storing in node %p\n", |
diff --git a/drivers/acpi/dispatcher/dsobject.c b/drivers/acpi/dispatcher/dsobject.c index bfbae4e4c667..1eee2d54180f 100644 --- a/drivers/acpi/dispatcher/dsobject.c +++ b/drivers/acpi/dispatcher/dsobject.c | |||
@@ -547,6 +547,9 @@ acpi_ds_init_object_from_op ( | |||
547 | case AML_TYPE_LITERAL: | 547 | case AML_TYPE_LITERAL: |
548 | 548 | ||
549 | obj_desc->integer.value = op->common.value.integer; | 549 | obj_desc->integer.value = op->common.value.integer; |
550 | #ifndef ACPI_NO_METHOD_EXECUTION | ||
551 | acpi_ex_truncate_for32bit_table (obj_desc); | ||
552 | #endif | ||
550 | break; | 553 | break; |
551 | 554 | ||
552 | 555 | ||
diff --git a/drivers/acpi/dispatcher/dsopcode.c b/drivers/acpi/dispatcher/dsopcode.c index ba13bca28bee..750bdb1ac344 100644 --- a/drivers/acpi/dispatcher/dsopcode.c +++ b/drivers/acpi/dispatcher/dsopcode.c | |||
@@ -119,14 +119,15 @@ acpi_ds_execute_arguments ( | |||
119 | 119 | ||
120 | walk_state = acpi_ds_create_walk_state (0, NULL, NULL, NULL); | 120 | walk_state = acpi_ds_create_walk_state (0, NULL, NULL, NULL); |
121 | if (!walk_state) { | 121 | if (!walk_state) { |
122 | return_ACPI_STATUS (AE_NO_MEMORY); | 122 | status = AE_NO_MEMORY; |
123 | goto cleanup; | ||
123 | } | 124 | } |
124 | 125 | ||
125 | status = acpi_ds_init_aml_walk (walk_state, op, NULL, aml_start, | 126 | status = acpi_ds_init_aml_walk (walk_state, op, NULL, aml_start, |
126 | aml_length, NULL, 1); | 127 | aml_length, NULL, 1); |
127 | if (ACPI_FAILURE (status)) { | 128 | if (ACPI_FAILURE (status)) { |
128 | acpi_ds_delete_walk_state (walk_state); | 129 | acpi_ds_delete_walk_state (walk_state); |
129 | return_ACPI_STATUS (status); | 130 | goto cleanup; |
130 | } | 131 | } |
131 | 132 | ||
132 | /* Mark this parse as a deferred opcode */ | 133 | /* Mark this parse as a deferred opcode */ |
@@ -138,8 +139,7 @@ acpi_ds_execute_arguments ( | |||
138 | 139 | ||
139 | status = acpi_ps_parse_aml (walk_state); | 140 | status = acpi_ps_parse_aml (walk_state); |
140 | if (ACPI_FAILURE (status)) { | 141 | if (ACPI_FAILURE (status)) { |
141 | acpi_ps_delete_parse_tree (op); | 142 | goto cleanup; |
142 | return_ACPI_STATUS (status); | ||
143 | } | 143 | } |
144 | 144 | ||
145 | /* Get and init the Op created above */ | 145 | /* Get and init the Op created above */ |
@@ -160,7 +160,8 @@ acpi_ds_execute_arguments ( | |||
160 | 160 | ||
161 | walk_state = acpi_ds_create_walk_state (0, NULL, NULL, NULL); | 161 | walk_state = acpi_ds_create_walk_state (0, NULL, NULL, NULL); |
162 | if (!walk_state) { | 162 | if (!walk_state) { |
163 | return_ACPI_STATUS (AE_NO_MEMORY); | 163 | status = AE_NO_MEMORY; |
164 | goto cleanup; | ||
164 | } | 165 | } |
165 | 166 | ||
166 | /* Execute the opcode and arguments */ | 167 | /* Execute the opcode and arguments */ |
@@ -169,13 +170,15 @@ acpi_ds_execute_arguments ( | |||
169 | aml_length, NULL, 3); | 170 | aml_length, NULL, 3); |
170 | if (ACPI_FAILURE (status)) { | 171 | if (ACPI_FAILURE (status)) { |
171 | acpi_ds_delete_walk_state (walk_state); | 172 | acpi_ds_delete_walk_state (walk_state); |
172 | return_ACPI_STATUS (status); | 173 | goto cleanup; |
173 | } | 174 | } |
174 | 175 | ||
175 | /* Mark this execution as a deferred opcode */ | 176 | /* Mark this execution as a deferred opcode */ |
176 | 177 | ||
177 | walk_state->deferred_node = node; | 178 | walk_state->deferred_node = node; |
178 | status = acpi_ps_parse_aml (walk_state); | 179 | status = acpi_ps_parse_aml (walk_state); |
180 | |||
181 | cleanup: | ||
179 | acpi_ps_delete_parse_tree (op); | 182 | acpi_ps_delete_parse_tree (op); |
180 | return_ACPI_STATUS (status); | 183 | return_ACPI_STATUS (status); |
181 | } | 184 | } |
diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index d11620018421..9100c0bda470 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c | |||
@@ -50,7 +50,7 @@ | |||
50 | #include <acpi/acnamesp.h> | 50 | #include <acpi/acnamesp.h> |
51 | #include <acpi/acevents.h> | 51 | #include <acpi/acevents.h> |
52 | 52 | ||
53 | #ifdef _ACPI_ASL_COMPILER | 53 | #ifdef ACPI_ASL_COMPILER |
54 | #include <acpi/acdisasm.h> | 54 | #include <acpi/acdisasm.h> |
55 | #endif | 55 | #endif |
56 | 56 | ||
@@ -145,15 +145,6 @@ acpi_ds_load1_begin_op ( | |||
145 | 145 | ||
146 | if (op) { | 146 | if (op) { |
147 | if (!(walk_state->op_info->flags & AML_NAMED)) { | 147 | if (!(walk_state->op_info->flags & AML_NAMED)) { |
148 | #if 0 | ||
149 | if ((walk_state->op_info->class == AML_CLASS_EXECUTE) || | ||
150 | (walk_state->op_info->class == AML_CLASS_CONTROL)) { | ||
151 | acpi_os_printf ("\n\n***EXECUTABLE OPCODE %s***\n\n", | ||
152 | walk_state->op_info->name); | ||
153 | *out_op = op; | ||
154 | return (AE_CTRL_SKIP); | ||
155 | } | ||
156 | #endif | ||
157 | *out_op = op; | 148 | *out_op = op; |
158 | return (AE_OK); | 149 | return (AE_OK); |
159 | } | 150 | } |
@@ -185,7 +176,7 @@ acpi_ds_load1_begin_op ( | |||
185 | */ | 176 | */ |
186 | status = acpi_ns_lookup (walk_state->scope_info, path, object_type, | 177 | status = acpi_ns_lookup (walk_state->scope_info, path, object_type, |
187 | ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT, walk_state, &(node)); | 178 | ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT, walk_state, &(node)); |
188 | #ifdef _ACPI_ASL_COMPILER | 179 | #ifdef ACPI_ASL_COMPILER |
189 | if (status == AE_NOT_FOUND) { | 180 | if (status == AE_NOT_FOUND) { |
190 | /* | 181 | /* |
191 | * Table disassembly: | 182 | * Table disassembly: |
@@ -486,11 +477,31 @@ acpi_ds_load2_begin_op ( | |||
486 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Op=%p State=%p\n", op, walk_state)); | 477 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Op=%p State=%p\n", op, walk_state)); |
487 | 478 | ||
488 | if (op) { | 479 | if (op) { |
480 | if ((walk_state->control_state) && | ||
481 | (walk_state->control_state->common.state == | ||
482 | ACPI_CONTROL_CONDITIONAL_EXECUTING)) { | ||
483 | /* We are executing a while loop outside of a method */ | ||
484 | |||
485 | status = acpi_ds_exec_begin_op (walk_state, out_op); | ||
486 | return_ACPI_STATUS (status); | ||
487 | } | ||
488 | |||
489 | /* We only care about Namespace opcodes here */ | 489 | /* We only care about Namespace opcodes here */ |
490 | 490 | ||
491 | if ((!(walk_state->op_info->flags & AML_NSOPCODE) && | 491 | if ((!(walk_state->op_info->flags & AML_NSOPCODE) && |
492 | (walk_state->opcode != AML_INT_NAMEPATH_OP)) || | 492 | (walk_state->opcode != AML_INT_NAMEPATH_OP)) || |
493 | (!(walk_state->op_info->flags & AML_NAMED))) { | 493 | (!(walk_state->op_info->flags & AML_NAMED))) { |
494 | if ((walk_state->op_info->class == AML_CLASS_EXECUTE) || | ||
495 | (walk_state->op_info->class == AML_CLASS_CONTROL)) { | ||
496 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, | ||
497 | "Begin/EXEC: %s (fl %8.8X)\n", walk_state->op_info->name, | ||
498 | walk_state->op_info->flags)); | ||
499 | |||
500 | /* Executing a type1 or type2 opcode outside of a method */ | ||
501 | |||
502 | status = acpi_ds_exec_begin_op (walk_state, out_op); | ||
503 | return_ACPI_STATUS (status); | ||
504 | } | ||
494 | return_ACPI_STATUS (AE_OK); | 505 | return_ACPI_STATUS (AE_OK); |
495 | } | 506 | } |
496 | 507 | ||
@@ -558,7 +569,7 @@ acpi_ds_load2_begin_op ( | |||
558 | ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT, | 569 | ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT, |
559 | walk_state, &(node)); | 570 | walk_state, &(node)); |
560 | if (ACPI_FAILURE (status)) { | 571 | if (ACPI_FAILURE (status)) { |
561 | #ifdef _ACPI_ASL_COMPILER | 572 | #ifdef ACPI_ASL_COMPILER |
562 | if (status == AE_NOT_FOUND) { | 573 | if (status == AE_NOT_FOUND) { |
563 | status = AE_OK; | 574 | status = AE_OK; |
564 | } | 575 | } |
@@ -651,8 +662,10 @@ acpi_ds_load2_begin_op ( | |||
651 | break; | 662 | break; |
652 | } | 663 | } |
653 | 664 | ||
665 | /* Add new entry into namespace */ | ||
666 | |||
654 | status = acpi_ns_lookup (walk_state->scope_info, buffer_ptr, object_type, | 667 | status = acpi_ns_lookup (walk_state->scope_info, buffer_ptr, object_type, |
655 | ACPI_IMODE_EXECUTE, ACPI_NS_NO_UPSEARCH, | 668 | ACPI_IMODE_LOAD_PASS2, ACPI_NS_NO_UPSEARCH, |
656 | walk_state, &(node)); | 669 | walk_state, &(node)); |
657 | break; | 670 | break; |
658 | } | 671 | } |
@@ -662,7 +675,6 @@ acpi_ds_load2_begin_op ( | |||
662 | return_ACPI_STATUS (status); | 675 | return_ACPI_STATUS (status); |
663 | } | 676 | } |
664 | 677 | ||
665 | |||
666 | if (!op) { | 678 | if (!op) { |
667 | /* Create a new op */ | 679 | /* Create a new op */ |
668 | 680 | ||
@@ -676,9 +688,7 @@ acpi_ds_load2_begin_op ( | |||
676 | if (node) { | 688 | if (node) { |
677 | op->named.name = node->name.integer; | 689 | op->named.name = node->name.integer; |
678 | } | 690 | } |
679 | if (out_op) { | 691 | *out_op = op; |
680 | *out_op = op; | ||
681 | } | ||
682 | } | 692 | } |
683 | 693 | ||
684 | /* | 694 | /* |
@@ -725,9 +735,24 @@ acpi_ds_load2_end_op ( | |||
725 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Opcode [%s] Op %p State %p\n", | 735 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Opcode [%s] Op %p State %p\n", |
726 | walk_state->op_info->name, op, walk_state)); | 736 | walk_state->op_info->name, op, walk_state)); |
727 | 737 | ||
728 | /* Only interested in opcodes that have namespace objects */ | 738 | /* Check if opcode had an associated namespace object */ |
729 | 739 | ||
730 | if (!(walk_state->op_info->flags & AML_NSOBJECT)) { | 740 | if (!(walk_state->op_info->flags & AML_NSOBJECT)) { |
741 | #ifndef ACPI_NO_METHOD_EXECUTION | ||
742 | /* No namespace object. Executable opcode? */ | ||
743 | |||
744 | if ((walk_state->op_info->class == AML_CLASS_EXECUTE) || | ||
745 | (walk_state->op_info->class == AML_CLASS_CONTROL)) { | ||
746 | ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, | ||
747 | "End/EXEC: %s (fl %8.8X)\n", walk_state->op_info->name, | ||
748 | walk_state->op_info->flags)); | ||
749 | |||
750 | /* Executing a type1 or type2 opcode outside of a method */ | ||
751 | |||
752 | status = acpi_ds_exec_end_op (walk_state); | ||
753 | return_ACPI_STATUS (status); | ||
754 | } | ||
755 | #endif | ||
731 | return_ACPI_STATUS (AE_OK); | 756 | return_ACPI_STATUS (AE_OK); |
732 | } | 757 | } |
733 | 758 | ||
@@ -736,7 +761,6 @@ acpi_ds_load2_end_op ( | |||
736 | "Ending scope Op=%p State=%p\n", op, walk_state)); | 761 | "Ending scope Op=%p State=%p\n", op, walk_state)); |
737 | } | 762 | } |
738 | 763 | ||
739 | |||
740 | object_type = walk_state->op_info->object_type; | 764 | object_type = walk_state->op_info->object_type; |
741 | 765 | ||
742 | /* | 766 | /* |
@@ -959,6 +983,7 @@ acpi_ds_load2_end_op ( | |||
959 | ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, | 983 | ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, |
960 | walk_state, &(new_node)); | 984 | walk_state, &(new_node)); |
961 | if (ACPI_SUCCESS (status)) { | 985 | if (ACPI_SUCCESS (status)) { |
986 | |||
962 | /* | 987 | /* |
963 | * Make sure that what we found is indeed a method | 988 | * Make sure that what we found is indeed a method |
964 | * We didn't search for a method on purpose, to see if the name | 989 | * We didn't search for a method on purpose, to see if the name |
diff --git a/drivers/acpi/dispatcher/dswstate.c b/drivers/acpi/dispatcher/dswstate.c index 9cd3db652b31..5621665991b5 100644 --- a/drivers/acpi/dispatcher/dswstate.c +++ b/drivers/acpi/dispatcher/dswstate.c | |||
@@ -261,12 +261,12 @@ acpi_ds_result_pop_from_bottom ( | |||
261 | 261 | ||
262 | if (!*object) { | 262 | if (!*object) { |
263 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | 263 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, |
264 | "Null operand! State=%p #Ops=%X, Index=%X\n", | 264 | "Null operand! State=%p #Ops=%X Index=%X\n", |
265 | walk_state, state->results.num_results, (u32) index)); | 265 | walk_state, state->results.num_results, (u32) index)); |
266 | return (AE_AML_NO_RETURN_VALUE); | 266 | return (AE_AML_NO_RETURN_VALUE); |
267 | } | 267 | } |
268 | 268 | ||
269 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s], Results=%p State=%p\n", | 269 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s] Results=%p State=%p\n", |
270 | *object, (*object) ? acpi_ut_get_object_type_name (*object) : "NULL", | 270 | *object, (*object) ? acpi_ut_get_object_type_name (*object) : "NULL", |
271 | state, walk_state)); | 271 | state, walk_state)); |
272 | 272 | ||
@@ -681,7 +681,7 @@ acpi_ds_create_walk_state ( | |||
681 | ACPI_FUNCTION_TRACE ("ds_create_walk_state"); | 681 | ACPI_FUNCTION_TRACE ("ds_create_walk_state"); |
682 | 682 | ||
683 | 683 | ||
684 | walk_state = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_WALK); | 684 | walk_state = ACPI_MEM_CALLOCATE (sizeof (struct acpi_walk_state)); |
685 | if (!walk_state) { | 685 | if (!walk_state) { |
686 | return_PTR (NULL); | 686 | return_PTR (NULL); |
687 | } | 687 | } |
@@ -704,7 +704,7 @@ acpi_ds_create_walk_state ( | |||
704 | 704 | ||
705 | status = acpi_ds_result_stack_push (walk_state); | 705 | status = acpi_ds_result_stack_push (walk_state); |
706 | if (ACPI_FAILURE (status)) { | 706 | if (ACPI_FAILURE (status)) { |
707 | acpi_ut_release_to_cache (ACPI_MEM_LIST_WALK, walk_state); | 707 | ACPI_MEM_FREE (walk_state); |
708 | return_PTR (NULL); | 708 | return_PTR (NULL); |
709 | } | 709 | } |
710 | 710 | ||
@@ -744,7 +744,7 @@ acpi_ds_init_aml_walk ( | |||
744 | u8 *aml_start, | 744 | u8 *aml_start, |
745 | u32 aml_length, | 745 | u32 aml_length, |
746 | struct acpi_parameter_info *info, | 746 | struct acpi_parameter_info *info, |
747 | u32 pass_number) | 747 | u8 pass_number) |
748 | { | 748 | { |
749 | acpi_status status; | 749 | acpi_status status; |
750 | struct acpi_parse_state *parser_state = &walk_state->parser_state; | 750 | struct acpi_parse_state *parser_state = &walk_state->parser_state; |
@@ -762,6 +762,7 @@ acpi_ds_init_aml_walk ( | |||
762 | /* The next_op of the next_walk will be the beginning of the method */ | 762 | /* The next_op of the next_walk will be the beginning of the method */ |
763 | 763 | ||
764 | walk_state->next_op = NULL; | 764 | walk_state->next_op = NULL; |
765 | walk_state->pass_number = pass_number; | ||
765 | 766 | ||
766 | if (info) { | 767 | if (info) { |
767 | if (info->parameter_type == ACPI_PARAM_GPE) { | 768 | if (info->parameter_type == ACPI_PARAM_GPE) { |
@@ -899,38 +900,11 @@ acpi_ds_delete_walk_state ( | |||
899 | acpi_ut_delete_generic_state (state); | 900 | acpi_ut_delete_generic_state (state); |
900 | } | 901 | } |
901 | 902 | ||
902 | acpi_ut_release_to_cache (ACPI_MEM_LIST_WALK, walk_state); | 903 | ACPI_MEM_FREE (walk_state); |
903 | return_VOID; | 904 | return_VOID; |
904 | } | 905 | } |
905 | 906 | ||
906 | 907 | ||
907 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
908 | /****************************************************************************** | ||
909 | * | ||
910 | * FUNCTION: acpi_ds_delete_walk_state_cache | ||
911 | * | ||
912 | * PARAMETERS: None | ||
913 | * | ||
914 | * RETURN: None | ||
915 | * | ||
916 | * DESCRIPTION: Purge the global state object cache. Used during subsystem | ||
917 | * termination. | ||
918 | * | ||
919 | ******************************************************************************/ | ||
920 | |||
921 | void | ||
922 | acpi_ds_delete_walk_state_cache ( | ||
923 | void) | ||
924 | { | ||
925 | ACPI_FUNCTION_TRACE ("ds_delete_walk_state_cache"); | ||
926 | |||
927 | |||
928 | acpi_ut_delete_generic_cache (ACPI_MEM_LIST_WALK); | ||
929 | return_VOID; | ||
930 | } | ||
931 | #endif | ||
932 | |||
933 | |||
934 | #ifdef ACPI_OBSOLETE_FUNCTIONS | 908 | #ifdef ACPI_OBSOLETE_FUNCTIONS |
935 | /******************************************************************************* | 909 | /******************************************************************************* |
936 | * | 910 | * |
diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index 081120b109ba..ede834df4f69 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c | |||
@@ -396,6 +396,7 @@ acpi_ev_gpe_detect ( | |||
396 | struct acpi_gpe_register_info *gpe_register_info; | 396 | struct acpi_gpe_register_info *gpe_register_info; |
397 | u32 status_reg; | 397 | u32 status_reg; |
398 | u32 enable_reg; | 398 | u32 enable_reg; |
399 | u32 flags; | ||
399 | acpi_status status; | 400 | acpi_status status; |
400 | struct acpi_gpe_block_info *gpe_block; | 401 | struct acpi_gpe_block_info *gpe_block; |
401 | acpi_native_uint i; | 402 | acpi_native_uint i; |
@@ -412,7 +413,7 @@ acpi_ev_gpe_detect ( | |||
412 | 413 | ||
413 | /* Examine all GPE blocks attached to this interrupt level */ | 414 | /* Examine all GPE blocks attached to this interrupt level */ |
414 | 415 | ||
415 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_ISR); | 416 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
416 | gpe_block = gpe_xrupt_list->gpe_block_list_head; | 417 | gpe_block = gpe_xrupt_list->gpe_block_list_head; |
417 | while (gpe_block) { | 418 | while (gpe_block) { |
418 | /* | 419 | /* |
@@ -476,7 +477,7 @@ acpi_ev_gpe_detect ( | |||
476 | 477 | ||
477 | unlock_and_exit: | 478 | unlock_and_exit: |
478 | 479 | ||
479 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_ISR); | 480 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
480 | return (int_status); | 481 | return (int_status); |
481 | } | 482 | } |
482 | 483 | ||
diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c index 84186a7d17b2..dfc54692b127 100644 --- a/drivers/acpi/events/evgpeblk.c +++ b/drivers/acpi/events/evgpeblk.c | |||
@@ -66,7 +66,7 @@ acpi_ev_match_prw_and_gpe ( | |||
66 | 66 | ||
67 | static struct acpi_gpe_xrupt_info * | 67 | static struct acpi_gpe_xrupt_info * |
68 | acpi_ev_get_gpe_xrupt_block ( | 68 | acpi_ev_get_gpe_xrupt_block ( |
69 | u32 interrupt_level); | 69 | u32 interrupt_number); |
70 | 70 | ||
71 | static acpi_status | 71 | static acpi_status |
72 | acpi_ev_delete_gpe_xrupt ( | 72 | acpi_ev_delete_gpe_xrupt ( |
@@ -75,7 +75,7 @@ acpi_ev_delete_gpe_xrupt ( | |||
75 | static acpi_status | 75 | static acpi_status |
76 | acpi_ev_install_gpe_block ( | 76 | acpi_ev_install_gpe_block ( |
77 | struct acpi_gpe_block_info *gpe_block, | 77 | struct acpi_gpe_block_info *gpe_block, |
78 | u32 interrupt_level); | 78 | u32 interrupt_number); |
79 | 79 | ||
80 | static acpi_status | 80 | static acpi_status |
81 | acpi_ev_create_gpe_info_blocks ( | 81 | acpi_ev_create_gpe_info_blocks ( |
@@ -138,7 +138,6 @@ acpi_ev_valid_gpe_event ( | |||
138 | * FUNCTION: acpi_ev_walk_gpe_list | 138 | * FUNCTION: acpi_ev_walk_gpe_list |
139 | * | 139 | * |
140 | * PARAMETERS: gpe_walk_callback - Routine called for each GPE block | 140 | * PARAMETERS: gpe_walk_callback - Routine called for each GPE block |
141 | * Flags - ACPI_NOT_ISR or ACPI_ISR | ||
142 | * | 141 | * |
143 | * RETURN: Status | 142 | * RETURN: Status |
144 | * | 143 | * |
@@ -148,18 +147,18 @@ acpi_ev_valid_gpe_event ( | |||
148 | 147 | ||
149 | acpi_status | 148 | acpi_status |
150 | acpi_ev_walk_gpe_list ( | 149 | acpi_ev_walk_gpe_list ( |
151 | ACPI_GPE_CALLBACK gpe_walk_callback, | 150 | ACPI_GPE_CALLBACK gpe_walk_callback) |
152 | u32 flags) | ||
153 | { | 151 | { |
154 | struct acpi_gpe_block_info *gpe_block; | 152 | struct acpi_gpe_block_info *gpe_block; |
155 | struct acpi_gpe_xrupt_info *gpe_xrupt_info; | 153 | struct acpi_gpe_xrupt_info *gpe_xrupt_info; |
156 | acpi_status status = AE_OK; | 154 | acpi_status status = AE_OK; |
155 | u32 flags; | ||
157 | 156 | ||
158 | 157 | ||
159 | ACPI_FUNCTION_TRACE ("ev_walk_gpe_list"); | 158 | ACPI_FUNCTION_TRACE ("ev_walk_gpe_list"); |
160 | 159 | ||
161 | 160 | ||
162 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, flags); | 161 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
163 | 162 | ||
164 | /* Walk the interrupt level descriptor list */ | 163 | /* Walk the interrupt level descriptor list */ |
165 | 164 | ||
@@ -482,7 +481,7 @@ cleanup: | |||
482 | * | 481 | * |
483 | * FUNCTION: acpi_ev_get_gpe_xrupt_block | 482 | * FUNCTION: acpi_ev_get_gpe_xrupt_block |
484 | * | 483 | * |
485 | * PARAMETERS: interrupt_level - Interrupt for a GPE block | 484 | * PARAMETERS: interrupt_number - Interrupt for a GPE block |
486 | * | 485 | * |
487 | * RETURN: A GPE interrupt block | 486 | * RETURN: A GPE interrupt block |
488 | * | 487 | * |
@@ -495,11 +494,12 @@ cleanup: | |||
495 | 494 | ||
496 | static struct acpi_gpe_xrupt_info * | 495 | static struct acpi_gpe_xrupt_info * |
497 | acpi_ev_get_gpe_xrupt_block ( | 496 | acpi_ev_get_gpe_xrupt_block ( |
498 | u32 interrupt_level) | 497 | u32 interrupt_number) |
499 | { | 498 | { |
500 | struct acpi_gpe_xrupt_info *next_gpe_xrupt; | 499 | struct acpi_gpe_xrupt_info *next_gpe_xrupt; |
501 | struct acpi_gpe_xrupt_info *gpe_xrupt; | 500 | struct acpi_gpe_xrupt_info *gpe_xrupt; |
502 | acpi_status status; | 501 | acpi_status status; |
502 | u32 flags; | ||
503 | 503 | ||
504 | 504 | ||
505 | ACPI_FUNCTION_TRACE ("ev_get_gpe_xrupt_block"); | 505 | ACPI_FUNCTION_TRACE ("ev_get_gpe_xrupt_block"); |
@@ -509,7 +509,7 @@ acpi_ev_get_gpe_xrupt_block ( | |||
509 | 509 | ||
510 | next_gpe_xrupt = acpi_gbl_gpe_xrupt_list_head; | 510 | next_gpe_xrupt = acpi_gbl_gpe_xrupt_list_head; |
511 | while (next_gpe_xrupt) { | 511 | while (next_gpe_xrupt) { |
512 | if (next_gpe_xrupt->interrupt_level == interrupt_level) { | 512 | if (next_gpe_xrupt->interrupt_number == interrupt_number) { |
513 | return_PTR (next_gpe_xrupt); | 513 | return_PTR (next_gpe_xrupt); |
514 | } | 514 | } |
515 | 515 | ||
@@ -523,11 +523,11 @@ acpi_ev_get_gpe_xrupt_block ( | |||
523 | return_PTR (NULL); | 523 | return_PTR (NULL); |
524 | } | 524 | } |
525 | 525 | ||
526 | gpe_xrupt->interrupt_level = interrupt_level; | 526 | gpe_xrupt->interrupt_number = interrupt_number; |
527 | 527 | ||
528 | /* Install new interrupt descriptor with spin lock */ | 528 | /* Install new interrupt descriptor with spin lock */ |
529 | 529 | ||
530 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 530 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
531 | if (acpi_gbl_gpe_xrupt_list_head) { | 531 | if (acpi_gbl_gpe_xrupt_list_head) { |
532 | next_gpe_xrupt = acpi_gbl_gpe_xrupt_list_head; | 532 | next_gpe_xrupt = acpi_gbl_gpe_xrupt_list_head; |
533 | while (next_gpe_xrupt->next) { | 533 | while (next_gpe_xrupt->next) { |
@@ -540,17 +540,17 @@ acpi_ev_get_gpe_xrupt_block ( | |||
540 | else { | 540 | else { |
541 | acpi_gbl_gpe_xrupt_list_head = gpe_xrupt; | 541 | acpi_gbl_gpe_xrupt_list_head = gpe_xrupt; |
542 | } | 542 | } |
543 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 543 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
544 | 544 | ||
545 | /* Install new interrupt handler if not SCI_INT */ | 545 | /* Install new interrupt handler if not SCI_INT */ |
546 | 546 | ||
547 | if (interrupt_level != acpi_gbl_FADT->sci_int) { | 547 | if (interrupt_number != acpi_gbl_FADT->sci_int) { |
548 | status = acpi_os_install_interrupt_handler (interrupt_level, | 548 | status = acpi_os_install_interrupt_handler (interrupt_number, |
549 | acpi_ev_gpe_xrupt_handler, gpe_xrupt); | 549 | acpi_ev_gpe_xrupt_handler, gpe_xrupt); |
550 | if (ACPI_FAILURE (status)) { | 550 | if (ACPI_FAILURE (status)) { |
551 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | 551 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, |
552 | "Could not install GPE interrupt handler at level 0x%X\n", | 552 | "Could not install GPE interrupt handler at level 0x%X\n", |
553 | interrupt_level)); | 553 | interrupt_number)); |
554 | return_PTR (NULL); | 554 | return_PTR (NULL); |
555 | } | 555 | } |
556 | } | 556 | } |
@@ -577,6 +577,7 @@ acpi_ev_delete_gpe_xrupt ( | |||
577 | struct acpi_gpe_xrupt_info *gpe_xrupt) | 577 | struct acpi_gpe_xrupt_info *gpe_xrupt) |
578 | { | 578 | { |
579 | acpi_status status; | 579 | acpi_status status; |
580 | u32 flags; | ||
580 | 581 | ||
581 | 582 | ||
582 | ACPI_FUNCTION_TRACE ("ev_delete_gpe_xrupt"); | 583 | ACPI_FUNCTION_TRACE ("ev_delete_gpe_xrupt"); |
@@ -584,14 +585,14 @@ acpi_ev_delete_gpe_xrupt ( | |||
584 | 585 | ||
585 | /* We never want to remove the SCI interrupt handler */ | 586 | /* We never want to remove the SCI interrupt handler */ |
586 | 587 | ||
587 | if (gpe_xrupt->interrupt_level == acpi_gbl_FADT->sci_int) { | 588 | if (gpe_xrupt->interrupt_number == acpi_gbl_FADT->sci_int) { |
588 | gpe_xrupt->gpe_block_list_head = NULL; | 589 | gpe_xrupt->gpe_block_list_head = NULL; |
589 | return_ACPI_STATUS (AE_OK); | 590 | return_ACPI_STATUS (AE_OK); |
590 | } | 591 | } |
591 | 592 | ||
592 | /* Disable this interrupt */ | 593 | /* Disable this interrupt */ |
593 | 594 | ||
594 | status = acpi_os_remove_interrupt_handler (gpe_xrupt->interrupt_level, | 595 | status = acpi_os_remove_interrupt_handler (gpe_xrupt->interrupt_number, |
595 | acpi_ev_gpe_xrupt_handler); | 596 | acpi_ev_gpe_xrupt_handler); |
596 | if (ACPI_FAILURE (status)) { | 597 | if (ACPI_FAILURE (status)) { |
597 | return_ACPI_STATUS (status); | 598 | return_ACPI_STATUS (status); |
@@ -599,7 +600,7 @@ acpi_ev_delete_gpe_xrupt ( | |||
599 | 600 | ||
600 | /* Unlink the interrupt block with lock */ | 601 | /* Unlink the interrupt block with lock */ |
601 | 602 | ||
602 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 603 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
603 | if (gpe_xrupt->previous) { | 604 | if (gpe_xrupt->previous) { |
604 | gpe_xrupt->previous->next = gpe_xrupt->next; | 605 | gpe_xrupt->previous->next = gpe_xrupt->next; |
605 | } | 606 | } |
@@ -607,7 +608,7 @@ acpi_ev_delete_gpe_xrupt ( | |||
607 | if (gpe_xrupt->next) { | 608 | if (gpe_xrupt->next) { |
608 | gpe_xrupt->next->previous = gpe_xrupt->previous; | 609 | gpe_xrupt->next->previous = gpe_xrupt->previous; |
609 | } | 610 | } |
610 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 611 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
611 | 612 | ||
612 | /* Free the block */ | 613 | /* Free the block */ |
613 | 614 | ||
@@ -621,7 +622,7 @@ acpi_ev_delete_gpe_xrupt ( | |||
621 | * FUNCTION: acpi_ev_install_gpe_block | 622 | * FUNCTION: acpi_ev_install_gpe_block |
622 | * | 623 | * |
623 | * PARAMETERS: gpe_block - New GPE block | 624 | * PARAMETERS: gpe_block - New GPE block |
624 | * interrupt_level - Level to be associated with this GPE block | 625 | * interrupt_number - Xrupt to be associated with this GPE block |
625 | * | 626 | * |
626 | * RETURN: Status | 627 | * RETURN: Status |
627 | * | 628 | * |
@@ -632,11 +633,12 @@ acpi_ev_delete_gpe_xrupt ( | |||
632 | static acpi_status | 633 | static acpi_status |
633 | acpi_ev_install_gpe_block ( | 634 | acpi_ev_install_gpe_block ( |
634 | struct acpi_gpe_block_info *gpe_block, | 635 | struct acpi_gpe_block_info *gpe_block, |
635 | u32 interrupt_level) | 636 | u32 interrupt_number) |
636 | { | 637 | { |
637 | struct acpi_gpe_block_info *next_gpe_block; | 638 | struct acpi_gpe_block_info *next_gpe_block; |
638 | struct acpi_gpe_xrupt_info *gpe_xrupt_block; | 639 | struct acpi_gpe_xrupt_info *gpe_xrupt_block; |
639 | acpi_status status; | 640 | acpi_status status; |
641 | u32 flags; | ||
640 | 642 | ||
641 | 643 | ||
642 | ACPI_FUNCTION_TRACE ("ev_install_gpe_block"); | 644 | ACPI_FUNCTION_TRACE ("ev_install_gpe_block"); |
@@ -647,7 +649,7 @@ acpi_ev_install_gpe_block ( | |||
647 | return_ACPI_STATUS (status); | 649 | return_ACPI_STATUS (status); |
648 | } | 650 | } |
649 | 651 | ||
650 | gpe_xrupt_block = acpi_ev_get_gpe_xrupt_block (interrupt_level); | 652 | gpe_xrupt_block = acpi_ev_get_gpe_xrupt_block (interrupt_number); |
651 | if (!gpe_xrupt_block) { | 653 | if (!gpe_xrupt_block) { |
652 | status = AE_NO_MEMORY; | 654 | status = AE_NO_MEMORY; |
653 | goto unlock_and_exit; | 655 | goto unlock_and_exit; |
@@ -655,7 +657,7 @@ acpi_ev_install_gpe_block ( | |||
655 | 657 | ||
656 | /* Install the new block at the end of the list with lock */ | 658 | /* Install the new block at the end of the list with lock */ |
657 | 659 | ||
658 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 660 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
659 | if (gpe_xrupt_block->gpe_block_list_head) { | 661 | if (gpe_xrupt_block->gpe_block_list_head) { |
660 | next_gpe_block = gpe_xrupt_block->gpe_block_list_head; | 662 | next_gpe_block = gpe_xrupt_block->gpe_block_list_head; |
661 | while (next_gpe_block->next) { | 663 | while (next_gpe_block->next) { |
@@ -670,7 +672,7 @@ acpi_ev_install_gpe_block ( | |||
670 | } | 672 | } |
671 | 673 | ||
672 | gpe_block->xrupt_block = gpe_xrupt_block; | 674 | gpe_block->xrupt_block = gpe_xrupt_block; |
673 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 675 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
674 | 676 | ||
675 | unlock_and_exit: | 677 | unlock_and_exit: |
676 | status = acpi_ut_release_mutex (ACPI_MTX_EVENTS); | 678 | status = acpi_ut_release_mutex (ACPI_MTX_EVENTS); |
@@ -695,6 +697,7 @@ acpi_ev_delete_gpe_block ( | |||
695 | struct acpi_gpe_block_info *gpe_block) | 697 | struct acpi_gpe_block_info *gpe_block) |
696 | { | 698 | { |
697 | acpi_status status; | 699 | acpi_status status; |
700 | u32 flags; | ||
698 | 701 | ||
699 | 702 | ||
700 | ACPI_FUNCTION_TRACE ("ev_install_gpe_block"); | 703 | ACPI_FUNCTION_TRACE ("ev_install_gpe_block"); |
@@ -720,7 +723,7 @@ acpi_ev_delete_gpe_block ( | |||
720 | else { | 723 | else { |
721 | /* Remove the block on this interrupt with lock */ | 724 | /* Remove the block on this interrupt with lock */ |
722 | 725 | ||
723 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 726 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
724 | if (gpe_block->previous) { | 727 | if (gpe_block->previous) { |
725 | gpe_block->previous->next = gpe_block->next; | 728 | gpe_block->previous->next = gpe_block->next; |
726 | } | 729 | } |
@@ -731,7 +734,7 @@ acpi_ev_delete_gpe_block ( | |||
731 | if (gpe_block->next) { | 734 | if (gpe_block->next) { |
732 | gpe_block->next->previous = gpe_block->previous; | 735 | gpe_block->next->previous = gpe_block->previous; |
733 | } | 736 | } |
734 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 737 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
735 | } | 738 | } |
736 | 739 | ||
737 | /* Free the gpe_block */ | 740 | /* Free the gpe_block */ |
@@ -887,7 +890,7 @@ error_exit: | |||
887 | * gpe_block_address - Address and space_iD | 890 | * gpe_block_address - Address and space_iD |
888 | * register_count - Number of GPE register pairs in the block | 891 | * register_count - Number of GPE register pairs in the block |
889 | * gpe_block_base_number - Starting GPE number for the block | 892 | * gpe_block_base_number - Starting GPE number for the block |
890 | * interrupt_level - H/W interrupt for the block | 893 | * interrupt_number - H/W interrupt for the block |
891 | * return_gpe_block - Where the new block descriptor is returned | 894 | * return_gpe_block - Where the new block descriptor is returned |
892 | * | 895 | * |
893 | * RETURN: Status | 896 | * RETURN: Status |
@@ -902,7 +905,7 @@ acpi_ev_create_gpe_block ( | |||
902 | struct acpi_generic_address *gpe_block_address, | 905 | struct acpi_generic_address *gpe_block_address, |
903 | u32 register_count, | 906 | u32 register_count, |
904 | u8 gpe_block_base_number, | 907 | u8 gpe_block_base_number, |
905 | u32 interrupt_level, | 908 | u32 interrupt_number, |
906 | struct acpi_gpe_block_info **return_gpe_block) | 909 | struct acpi_gpe_block_info **return_gpe_block) |
907 | { | 910 | { |
908 | struct acpi_gpe_block_info *gpe_block; | 911 | struct acpi_gpe_block_info *gpe_block; |
@@ -948,7 +951,7 @@ acpi_ev_create_gpe_block ( | |||
948 | 951 | ||
949 | /* Install the new block in the global list(s) */ | 952 | /* Install the new block in the global list(s) */ |
950 | 953 | ||
951 | status = acpi_ev_install_gpe_block (gpe_block, interrupt_level); | 954 | status = acpi_ev_install_gpe_block (gpe_block, interrupt_number); |
952 | if (ACPI_FAILURE (status)) { | 955 | if (ACPI_FAILURE (status)) { |
953 | ACPI_MEM_FREE (gpe_block); | 956 | ACPI_MEM_FREE (gpe_block); |
954 | return_ACPI_STATUS (status); | 957 | return_ACPI_STATUS (status); |
@@ -1013,7 +1016,7 @@ acpi_ev_create_gpe_block ( | |||
1013 | ((gpe_block->register_count * ACPI_GPE_REGISTER_WIDTH) -1)), | 1016 | ((gpe_block->register_count * ACPI_GPE_REGISTER_WIDTH) -1)), |
1014 | gpe_device->name.ascii, | 1017 | gpe_device->name.ascii, |
1015 | gpe_block->register_count, | 1018 | gpe_block->register_count, |
1016 | interrupt_level)); | 1019 | interrupt_number)); |
1017 | 1020 | ||
1018 | /* Enable all valid GPEs found above */ | 1021 | /* Enable all valid GPEs found above */ |
1019 | 1022 | ||
diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index 659e90956112..3df3ada4b9e7 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c | |||
@@ -411,6 +411,9 @@ acpi_ev_init_global_lock_handler ( | |||
411 | * with an error. | 411 | * with an error. |
412 | */ | 412 | */ |
413 | if (status == AE_NO_HARDWARE_RESPONSE) { | 413 | if (status == AE_NO_HARDWARE_RESPONSE) { |
414 | ACPI_REPORT_ERROR (( | ||
415 | "No response from Global Lock hardware, disabling lock\n")); | ||
416 | |||
414 | acpi_gbl_global_lock_present = FALSE; | 417 | acpi_gbl_global_lock_present = FALSE; |
415 | status = AE_OK; | 418 | status = AE_OK; |
416 | } | 419 | } |
@@ -589,7 +592,7 @@ acpi_ev_terminate ( | |||
589 | 592 | ||
590 | /* Disable all GPEs in all GPE blocks */ | 593 | /* Disable all GPEs in all GPE blocks */ |
591 | 594 | ||
592 | status = acpi_ev_walk_gpe_list (acpi_hw_disable_gpe_block, ACPI_NOT_ISR); | 595 | status = acpi_ev_walk_gpe_list (acpi_hw_disable_gpe_block); |
593 | 596 | ||
594 | /* Remove SCI handler */ | 597 | /* Remove SCI handler */ |
595 | 598 | ||
@@ -602,7 +605,7 @@ acpi_ev_terminate ( | |||
602 | 605 | ||
603 | /* Deallocate all handler objects installed within GPE info structs */ | 606 | /* Deallocate all handler objects installed within GPE info structs */ |
604 | 607 | ||
605 | status = acpi_ev_walk_gpe_list (acpi_ev_delete_gpe_handlers, ACPI_NOT_ISR); | 608 | status = acpi_ev_walk_gpe_list (acpi_ev_delete_gpe_handlers); |
606 | 609 | ||
607 | /* Return to original mode if necessary */ | 610 | /* Return to original mode if necessary */ |
608 | 611 | ||
diff --git a/drivers/acpi/events/evrgnini.c b/drivers/acpi/events/evrgnini.c index 95bc09c73a6a..f2d53af97610 100644 --- a/drivers/acpi/events/evrgnini.c +++ b/drivers/acpi/events/evrgnini.c | |||
@@ -218,10 +218,14 @@ acpi_ev_pci_config_region_setup ( | |||
218 | while (pci_root_node != acpi_gbl_root_node) { | 218 | while (pci_root_node != acpi_gbl_root_node) { |
219 | status = acpi_ut_execute_HID (pci_root_node, &object_hID); | 219 | status = acpi_ut_execute_HID (pci_root_node, &object_hID); |
220 | if (ACPI_SUCCESS (status)) { | 220 | if (ACPI_SUCCESS (status)) { |
221 | /* Got a valid _HID, check if this is a PCI root */ | 221 | /* |
222 | 222 | * Got a valid _HID string, check if this is a PCI root. | |
223 | * New for ACPI 3.0: check for a PCI Express root also. | ||
224 | */ | ||
223 | if (!(ACPI_STRNCMP (object_hID.value, PCI_ROOT_HID_STRING, | 225 | if (!(ACPI_STRNCMP (object_hID.value, PCI_ROOT_HID_STRING, |
224 | sizeof (PCI_ROOT_HID_STRING)))) { | 226 | sizeof (PCI_ROOT_HID_STRING)) || |
227 | !(ACPI_STRNCMP (object_hID.value, PCI_EXPRESS_ROOT_HID_STRING, | ||
228 | sizeof (PCI_EXPRESS_ROOT_HID_STRING))))) { | ||
225 | /* Install a handler for this PCI root bridge */ | 229 | /* Install a handler for this PCI root bridge */ |
226 | 230 | ||
227 | status = acpi_install_address_space_handler ((acpi_handle) pci_root_node, | 231 | status = acpi_install_address_space_handler ((acpi_handle) pci_root_node, |
diff --git a/drivers/acpi/events/evxface.c b/drivers/acpi/events/evxface.c index 4092d47f6758..4c1c25e316a8 100644 --- a/drivers/acpi/events/evxface.c +++ b/drivers/acpi/events/evxface.c | |||
@@ -591,6 +591,7 @@ acpi_install_gpe_handler ( | |||
591 | struct acpi_gpe_event_info *gpe_event_info; | 591 | struct acpi_gpe_event_info *gpe_event_info; |
592 | struct acpi_handler_info *handler; | 592 | struct acpi_handler_info *handler; |
593 | acpi_status status; | 593 | acpi_status status; |
594 | u32 flags; | ||
594 | 595 | ||
595 | 596 | ||
596 | ACPI_FUNCTION_TRACE ("acpi_install_gpe_handler"); | 597 | ACPI_FUNCTION_TRACE ("acpi_install_gpe_handler"); |
@@ -643,7 +644,7 @@ acpi_install_gpe_handler ( | |||
643 | 644 | ||
644 | /* Install the handler */ | 645 | /* Install the handler */ |
645 | 646 | ||
646 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 647 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
647 | gpe_event_info->dispatch.handler = handler; | 648 | gpe_event_info->dispatch.handler = handler; |
648 | 649 | ||
649 | /* Setup up dispatch flags to indicate handler (vs. method) */ | 650 | /* Setup up dispatch flags to indicate handler (vs. method) */ |
@@ -651,7 +652,7 @@ acpi_install_gpe_handler ( | |||
651 | gpe_event_info->flags &= ~(ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); /* Clear bits */ | 652 | gpe_event_info->flags &= ~(ACPI_GPE_XRUPT_TYPE_MASK | ACPI_GPE_DISPATCH_MASK); /* Clear bits */ |
652 | gpe_event_info->flags |= (u8) (type | ACPI_GPE_DISPATCH_HANDLER); | 653 | gpe_event_info->flags |= (u8) (type | ACPI_GPE_DISPATCH_HANDLER); |
653 | 654 | ||
654 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 655 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
655 | 656 | ||
656 | 657 | ||
657 | unlock_and_exit: | 658 | unlock_and_exit: |
@@ -685,6 +686,7 @@ acpi_remove_gpe_handler ( | |||
685 | struct acpi_gpe_event_info *gpe_event_info; | 686 | struct acpi_gpe_event_info *gpe_event_info; |
686 | struct acpi_handler_info *handler; | 687 | struct acpi_handler_info *handler; |
687 | acpi_status status; | 688 | acpi_status status; |
689 | u32 flags; | ||
688 | 690 | ||
689 | 691 | ||
690 | ACPI_FUNCTION_TRACE ("acpi_remove_gpe_handler"); | 692 | ACPI_FUNCTION_TRACE ("acpi_remove_gpe_handler"); |
@@ -741,7 +743,7 @@ acpi_remove_gpe_handler ( | |||
741 | 743 | ||
742 | /* Remove the handler */ | 744 | /* Remove the handler */ |
743 | 745 | ||
744 | acpi_os_acquire_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 746 | flags = acpi_os_acquire_lock (acpi_gbl_gpe_lock); |
745 | handler = gpe_event_info->dispatch.handler; | 747 | handler = gpe_event_info->dispatch.handler; |
746 | 748 | ||
747 | /* Restore Method node (if any), set dispatch flags */ | 749 | /* Restore Method node (if any), set dispatch flags */ |
@@ -751,7 +753,7 @@ acpi_remove_gpe_handler ( | |||
751 | if (handler->method_node) { | 753 | if (handler->method_node) { |
752 | gpe_event_info->flags |= ACPI_GPE_DISPATCH_METHOD; | 754 | gpe_event_info->flags |= ACPI_GPE_DISPATCH_METHOD; |
753 | } | 755 | } |
754 | acpi_os_release_lock (acpi_gbl_gpe_lock, ACPI_NOT_ISR); | 756 | acpi_os_release_lock (acpi_gbl_gpe_lock, flags); |
755 | 757 | ||
756 | /* Now we can free the handler object */ | 758 | /* Now we can free the handler object */ |
757 | 759 | ||
diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index f337dc2cc569..c5f74d7b64d8 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c | |||
@@ -635,7 +635,7 @@ unlock_and_exit: | |||
635 | * PARAMETERS: gpe_device - Handle to the parent GPE Block Device | 635 | * PARAMETERS: gpe_device - Handle to the parent GPE Block Device |
636 | * gpe_block_address - Address and space_iD | 636 | * gpe_block_address - Address and space_iD |
637 | * register_count - Number of GPE register pairs in the block | 637 | * register_count - Number of GPE register pairs in the block |
638 | * interrupt_level - H/W interrupt for the block | 638 | * interrupt_number - H/W interrupt for the block |
639 | * | 639 | * |
640 | * RETURN: Status | 640 | * RETURN: Status |
641 | * | 641 | * |
@@ -648,7 +648,7 @@ acpi_install_gpe_block ( | |||
648 | acpi_handle gpe_device, | 648 | acpi_handle gpe_device, |
649 | struct acpi_generic_address *gpe_block_address, | 649 | struct acpi_generic_address *gpe_block_address, |
650 | u32 register_count, | 650 | u32 register_count, |
651 | u32 interrupt_level) | 651 | u32 interrupt_number) |
652 | { | 652 | { |
653 | acpi_status status; | 653 | acpi_status status; |
654 | union acpi_operand_object *obj_desc; | 654 | union acpi_operand_object *obj_desc; |
@@ -681,7 +681,7 @@ acpi_install_gpe_block ( | |||
681 | * is always zero | 681 | * is always zero |
682 | */ | 682 | */ |
683 | status = acpi_ev_create_gpe_block (node, gpe_block_address, register_count, | 683 | status = acpi_ev_create_gpe_block (node, gpe_block_address, register_count, |
684 | 0, interrupt_level, &gpe_block); | 684 | 0, interrupt_number, &gpe_block); |
685 | if (ACPI_FAILURE (status)) { | 685 | if (ACPI_FAILURE (status)) { |
686 | goto unlock_and_exit; | 686 | goto unlock_and_exit; |
687 | } | 687 | } |
diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index 734b2f24af48..d11e9ec827f1 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c | |||
@@ -99,6 +99,11 @@ acpi_ex_add_table ( | |||
99 | return_ACPI_STATUS (AE_NO_MEMORY); | 99 | return_ACPI_STATUS (AE_NO_MEMORY); |
100 | } | 100 | } |
101 | 101 | ||
102 | /* Init the table handle */ | ||
103 | |||
104 | obj_desc->reference.opcode = AML_LOAD_OP; | ||
105 | *ddb_handle = obj_desc; | ||
106 | |||
102 | /* Install the new table into the local data structures */ | 107 | /* Install the new table into the local data structures */ |
103 | 108 | ||
104 | ACPI_MEMSET (&table_info, 0, sizeof (struct acpi_table_desc)); | 109 | ACPI_MEMSET (&table_info, 0, sizeof (struct acpi_table_desc)); |
@@ -109,7 +114,14 @@ acpi_ex_add_table ( | |||
109 | table_info.allocation = ACPI_MEM_ALLOCATED; | 114 | table_info.allocation = ACPI_MEM_ALLOCATED; |
110 | 115 | ||
111 | status = acpi_tb_install_table (&table_info); | 116 | status = acpi_tb_install_table (&table_info); |
117 | obj_desc->reference.object = table_info.installed_desc; | ||
118 | |||
112 | if (ACPI_FAILURE (status)) { | 119 | if (ACPI_FAILURE (status)) { |
120 | if (status == AE_ALREADY_EXISTS) { | ||
121 | /* Table already exists, just return the handle */ | ||
122 | |||
123 | return_ACPI_STATUS (AE_OK); | ||
124 | } | ||
113 | goto cleanup; | 125 | goto cleanup; |
114 | } | 126 | } |
115 | 127 | ||
@@ -123,16 +135,12 @@ acpi_ex_add_table ( | |||
123 | goto cleanup; | 135 | goto cleanup; |
124 | } | 136 | } |
125 | 137 | ||
126 | /* Init the table handle */ | ||
127 | |||
128 | obj_desc->reference.opcode = AML_LOAD_OP; | ||
129 | obj_desc->reference.object = table_info.installed_desc; | ||
130 | *ddb_handle = obj_desc; | ||
131 | return_ACPI_STATUS (AE_OK); | 138 | return_ACPI_STATUS (AE_OK); |
132 | 139 | ||
133 | 140 | ||
134 | cleanup: | 141 | cleanup: |
135 | acpi_ut_remove_reference (obj_desc); | 142 | acpi_ut_remove_reference (obj_desc); |
143 | *ddb_handle = NULL; | ||
136 | return_ACPI_STATUS (status); | 144 | return_ACPI_STATUS (status); |
137 | } | 145 | } |
138 | 146 | ||
@@ -376,16 +384,22 @@ acpi_ex_load_op ( | |||
376 | */ | 384 | */ |
377 | status = acpi_ex_read_data_from_field (walk_state, obj_desc, &buffer_desc); | 385 | status = acpi_ex_read_data_from_field (walk_state, obj_desc, &buffer_desc); |
378 | if (ACPI_FAILURE (status)) { | 386 | if (ACPI_FAILURE (status)) { |
379 | goto cleanup; | 387 | return_ACPI_STATUS (status); |
380 | } | 388 | } |
381 | 389 | ||
382 | table_ptr = ACPI_CAST_PTR (struct acpi_table_header, | 390 | table_ptr = ACPI_CAST_PTR (struct acpi_table_header, |
383 | buffer_desc->buffer.pointer); | 391 | buffer_desc->buffer.pointer); |
384 | 392 | ||
385 | /* Sanity check the table length */ | 393 | /* All done with the buffer_desc, delete it */ |
394 | |||
395 | buffer_desc->buffer.pointer = NULL; | ||
396 | acpi_ut_remove_reference (buffer_desc); | ||
397 | |||
398 | /* Sanity check the table length */ | ||
386 | 399 | ||
387 | if (table_ptr->length < sizeof (struct acpi_table_header)) { | 400 | if (table_ptr->length < sizeof (struct acpi_table_header)) { |
388 | return_ACPI_STATUS (AE_BAD_HEADER); | 401 | status = AE_BAD_HEADER; |
402 | goto cleanup; | ||
389 | } | 403 | } |
390 | break; | 404 | break; |
391 | 405 | ||
@@ -413,7 +427,9 @@ acpi_ex_load_op ( | |||
413 | 427 | ||
414 | status = acpi_ex_add_table (table_ptr, acpi_gbl_root_node, &ddb_handle); | 428 | status = acpi_ex_add_table (table_ptr, acpi_gbl_root_node, &ddb_handle); |
415 | if (ACPI_FAILURE (status)) { | 429 | if (ACPI_FAILURE (status)) { |
416 | goto cleanup; | 430 | /* On error, table_ptr was deallocated above */ |
431 | |||
432 | return_ACPI_STATUS (status); | ||
417 | } | 433 | } |
418 | 434 | ||
419 | /* Store the ddb_handle into the Target operand */ | 435 | /* Store the ddb_handle into the Target operand */ |
@@ -421,17 +437,14 @@ acpi_ex_load_op ( | |||
421 | status = acpi_ex_store (ddb_handle, target, walk_state); | 437 | status = acpi_ex_store (ddb_handle, target, walk_state); |
422 | if (ACPI_FAILURE (status)) { | 438 | if (ACPI_FAILURE (status)) { |
423 | (void) acpi_ex_unload_table (ddb_handle); | 439 | (void) acpi_ex_unload_table (ddb_handle); |
424 | } | ||
425 | 440 | ||
426 | return_ACPI_STATUS (status); | 441 | /* table_ptr was deallocated above */ |
427 | 442 | ||
443 | return_ACPI_STATUS (status); | ||
444 | } | ||
428 | 445 | ||
429 | cleanup: | 446 | cleanup: |
430 | 447 | if (ACPI_FAILURE (status)) { | |
431 | if (buffer_desc) { | ||
432 | acpi_ut_remove_reference (buffer_desc); | ||
433 | } | ||
434 | else { | ||
435 | ACPI_MEM_FREE (table_ptr); | 448 | ACPI_MEM_FREE (table_ptr); |
436 | } | 449 | } |
437 | return_ACPI_STATUS (status); | 450 | return_ACPI_STATUS (status); |
@@ -482,7 +495,8 @@ acpi_ex_unload_table ( | |||
482 | * Delete the entire namespace under this table Node | 495 | * Delete the entire namespace under this table Node |
483 | * (Offset contains the table_id) | 496 | * (Offset contains the table_id) |
484 | */ | 497 | */ |
485 | acpi_ns_delete_namespace_by_owner (table_info->table_id); | 498 | acpi_ns_delete_namespace_by_owner (table_info->owner_id); |
499 | acpi_ut_release_owner_id (&table_info->owner_id); | ||
486 | 500 | ||
487 | /* Delete the table itself */ | 501 | /* Delete the table itself */ |
488 | 502 | ||
diff --git a/drivers/acpi/executer/exconvrt.c b/drivers/acpi/executer/exconvrt.c index 97856c48bd74..21331625e66e 100644 --- a/drivers/acpi/executer/exconvrt.c +++ b/drivers/acpi/executer/exconvrt.c | |||
@@ -367,7 +367,7 @@ acpi_ex_convert_to_ascii ( | |||
367 | 367 | ||
368 | /* hex_length: 2 ascii hex chars per data byte */ | 368 | /* hex_length: 2 ascii hex chars per data byte */ |
369 | 369 | ||
370 | hex_length = ACPI_MUL_2 (data_width); | 370 | hex_length = (acpi_native_uint) ACPI_MUL_2 (data_width); |
371 | for (i = 0, j = (hex_length-1); i < hex_length; i++, j--) { | 371 | for (i = 0, j = (hex_length-1); i < hex_length; i++, j--) { |
372 | /* Get one hex digit, most significant digits first */ | 372 | /* Get one hex digit, most significant digits first */ |
373 | 373 | ||
diff --git a/drivers/acpi/executer/exdump.c b/drivers/acpi/executer/exdump.c index 408500648114..4f98dceed39a 100644 --- a/drivers/acpi/executer/exdump.c +++ b/drivers/acpi/executer/exdump.c | |||
@@ -51,6 +51,11 @@ | |||
51 | #define _COMPONENT ACPI_EXECUTER | 51 | #define _COMPONENT ACPI_EXECUTER |
52 | ACPI_MODULE_NAME ("exdump") | 52 | ACPI_MODULE_NAME ("exdump") |
53 | 53 | ||
54 | /* | ||
55 | * The following routines are used for debug output only | ||
56 | */ | ||
57 | #if defined(ACPI_DEBUG_OUTPUT) || defined(ACPI_DEBUGGER) | ||
58 | |||
54 | /* Local prototypes */ | 59 | /* Local prototypes */ |
55 | 60 | ||
56 | #ifdef ACPI_FUTURE_USAGE | 61 | #ifdef ACPI_FUTURE_USAGE |
@@ -73,13 +78,17 @@ static void | |||
73 | acpi_ex_out_address ( | 78 | acpi_ex_out_address ( |
74 | char *title, | 79 | char *title, |
75 | acpi_physical_address value); | 80 | acpi_physical_address value); |
76 | #endif /* ACPI_FUTURE_USAGE */ | ||
77 | 81 | ||
82 | static void | ||
83 | acpi_ex_dump_reference ( | ||
84 | union acpi_operand_object *obj_desc); | ||
78 | 85 | ||
79 | /* | 86 | static void |
80 | * The following routines are used for debug output only | 87 | acpi_ex_dump_package ( |
81 | */ | 88 | union acpi_operand_object *obj_desc, |
82 | #if defined(ACPI_DEBUG_OUTPUT) || defined(ACPI_DEBUGGER) | 89 | u32 level, |
90 | u32 index); | ||
91 | #endif /* ACPI_FUTURE_USAGE */ | ||
83 | 92 | ||
84 | /******************************************************************************* | 93 | /******************************************************************************* |
85 | * | 94 | * |
@@ -118,7 +127,7 @@ acpi_ex_dump_operand ( | |||
118 | } | 127 | } |
119 | 128 | ||
120 | if (ACPI_GET_DESCRIPTOR_TYPE (obj_desc) == ACPI_DESC_TYPE_NAMED) { | 129 | if (ACPI_GET_DESCRIPTOR_TYPE (obj_desc) == ACPI_DESC_TYPE_NAMED) { |
121 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "%p is a NS Node: ", obj_desc)); | 130 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "%p Namespace Node: ", obj_desc)); |
122 | ACPI_DUMP_ENTRY (obj_desc, ACPI_LV_EXEC); | 131 | ACPI_DUMP_ENTRY (obj_desc, ACPI_LV_EXEC); |
123 | return; | 132 | return; |
124 | } | 133 | } |
@@ -467,7 +476,7 @@ acpi_ex_dump_operands ( | |||
467 | } | 476 | } |
468 | 477 | ||
469 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, | 478 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, |
470 | "************* Stack dump from %s(%d), %s\n", | 479 | "************* Operand Stack dump from %s(%d), %s\n", |
471 | module_name, line_number, note)); | 480 | module_name, line_number, note)); |
472 | return; | 481 | return; |
473 | } | 482 | } |
@@ -508,7 +517,7 @@ acpi_ex_out_integer ( | |||
508 | char *title, | 517 | char *title, |
509 | u32 value) | 518 | u32 value) |
510 | { | 519 | { |
511 | acpi_os_printf ("%20s : %X\n", title, value); | 520 | acpi_os_printf ("%20s : %.2X\n", title, value); |
512 | } | 521 | } |
513 | 522 | ||
514 | static void | 523 | static void |
@@ -565,9 +574,144 @@ acpi_ex_dump_node ( | |||
565 | 574 | ||
566 | /******************************************************************************* | 575 | /******************************************************************************* |
567 | * | 576 | * |
577 | * FUNCTION: acpi_ex_dump_reference | ||
578 | * | ||
579 | * PARAMETERS: Object - Descriptor to dump | ||
580 | * | ||
581 | * DESCRIPTION: Dumps a reference object | ||
582 | * | ||
583 | ******************************************************************************/ | ||
584 | |||
585 | static void | ||
586 | acpi_ex_dump_reference ( | ||
587 | union acpi_operand_object *obj_desc) | ||
588 | { | ||
589 | struct acpi_buffer ret_buf; | ||
590 | acpi_status status; | ||
591 | |||
592 | |||
593 | if (obj_desc->reference.opcode == AML_INT_NAMEPATH_OP) { | ||
594 | acpi_os_printf ("Named Object %p ", obj_desc->reference.node); | ||
595 | ret_buf.length = ACPI_ALLOCATE_LOCAL_BUFFER; | ||
596 | status = acpi_ns_handle_to_pathname (obj_desc->reference.node, &ret_buf); | ||
597 | if (ACPI_FAILURE (status)) { | ||
598 | acpi_os_printf ("Could not convert name to pathname\n"); | ||
599 | } | ||
600 | else { | ||
601 | acpi_os_printf ("%s\n", (char *) ret_buf.pointer); | ||
602 | ACPI_MEM_FREE (ret_buf.pointer); | ||
603 | } | ||
604 | } | ||
605 | else if (obj_desc->reference.object) { | ||
606 | acpi_os_printf ("\nReferenced Object: %p\n", obj_desc->reference.object); | ||
607 | } | ||
608 | } | ||
609 | |||
610 | |||
611 | /******************************************************************************* | ||
612 | * | ||
613 | * FUNCTION: acpi_ex_dump_package | ||
614 | * | ||
615 | * PARAMETERS: Object - Descriptor to dump | ||
616 | * Level - Indentation Level | ||
617 | * Index - Package index for this object | ||
618 | * | ||
619 | * DESCRIPTION: Dumps the elements of the package | ||
620 | * | ||
621 | ******************************************************************************/ | ||
622 | |||
623 | static void | ||
624 | acpi_ex_dump_package ( | ||
625 | union acpi_operand_object *obj_desc, | ||
626 | u32 level, | ||
627 | u32 index) | ||
628 | { | ||
629 | u32 i; | ||
630 | |||
631 | |||
632 | /* Indentation and index output */ | ||
633 | |||
634 | if (level > 0) { | ||
635 | for (i = 0; i < level; i++) { | ||
636 | acpi_os_printf (" "); | ||
637 | } | ||
638 | |||
639 | acpi_os_printf ("[%.2d] ", index); | ||
640 | } | ||
641 | |||
642 | acpi_os_printf ("%p ", obj_desc); | ||
643 | |||
644 | /* Null package elements are allowed */ | ||
645 | |||
646 | if (!obj_desc) { | ||
647 | acpi_os_printf ("[Null Object]\n"); | ||
648 | return; | ||
649 | } | ||
650 | |||
651 | /* Packages may only contain a few object types */ | ||
652 | |||
653 | switch (ACPI_GET_OBJECT_TYPE (obj_desc)) { | ||
654 | case ACPI_TYPE_INTEGER: | ||
655 | |||
656 | acpi_os_printf ("[Integer] = %8.8X%8.8X\n", | ||
657 | ACPI_FORMAT_UINT64 (obj_desc->integer.value)); | ||
658 | break; | ||
659 | |||
660 | |||
661 | case ACPI_TYPE_STRING: | ||
662 | |||
663 | acpi_os_printf ("[String] Value: "); | ||
664 | for (i = 0; i < obj_desc->string.length; i++) { | ||
665 | acpi_os_printf ("%c", obj_desc->string.pointer[i]); | ||
666 | } | ||
667 | acpi_os_printf ("\n"); | ||
668 | break; | ||
669 | |||
670 | |||
671 | case ACPI_TYPE_BUFFER: | ||
672 | |||
673 | acpi_os_printf ("[Buffer] Length %.2X = ", obj_desc->buffer.length); | ||
674 | if (obj_desc->buffer.length) { | ||
675 | acpi_ut_dump_buffer ((u8 *) obj_desc->buffer.pointer, | ||
676 | obj_desc->buffer.length, DB_DWORD_DISPLAY, _COMPONENT); | ||
677 | } | ||
678 | else { | ||
679 | acpi_os_printf ("\n"); | ||
680 | } | ||
681 | break; | ||
682 | |||
683 | |||
684 | case ACPI_TYPE_PACKAGE: | ||
685 | |||
686 | acpi_os_printf ("[Package] Contains %d Elements: \n", | ||
687 | obj_desc->package.count); | ||
688 | |||
689 | for (i = 0; i < obj_desc->package.count; i++) { | ||
690 | acpi_ex_dump_package (obj_desc->package.elements[i], level+1, i); | ||
691 | } | ||
692 | break; | ||
693 | |||
694 | |||
695 | case ACPI_TYPE_LOCAL_REFERENCE: | ||
696 | |||
697 | acpi_os_printf ("[Object Reference] "); | ||
698 | acpi_ex_dump_reference (obj_desc); | ||
699 | break; | ||
700 | |||
701 | |||
702 | default: | ||
703 | |||
704 | acpi_os_printf ("[Unknown Type] %X\n", ACPI_GET_OBJECT_TYPE (obj_desc)); | ||
705 | break; | ||
706 | } | ||
707 | } | ||
708 | |||
709 | |||
710 | /******************************************************************************* | ||
711 | * | ||
568 | * FUNCTION: acpi_ex_dump_object_descriptor | 712 | * FUNCTION: acpi_ex_dump_object_descriptor |
569 | * | 713 | * |
570 | * PARAMETERS: *Object - Descriptor to dump | 714 | * PARAMETERS: Object - Descriptor to dump |
571 | * Flags - Force display if TRUE | 715 | * Flags - Force display if TRUE |
572 | * | 716 | * |
573 | * DESCRIPTION: Dumps the members of the object descriptor given. | 717 | * DESCRIPTION: Dumps the members of the object descriptor given. |
@@ -579,9 +723,6 @@ acpi_ex_dump_object_descriptor ( | |||
579 | union acpi_operand_object *obj_desc, | 723 | union acpi_operand_object *obj_desc, |
580 | u32 flags) | 724 | u32 flags) |
581 | { | 725 | { |
582 | u32 i; | ||
583 | |||
584 | |||
585 | ACPI_FUNCTION_TRACE ("ex_dump_object_descriptor"); | 726 | ACPI_FUNCTION_TRACE ("ex_dump_object_descriptor"); |
586 | 727 | ||
587 | 728 | ||
@@ -648,22 +789,13 @@ acpi_ex_dump_object_descriptor ( | |||
648 | case ACPI_TYPE_PACKAGE: | 789 | case ACPI_TYPE_PACKAGE: |
649 | 790 | ||
650 | acpi_ex_out_integer ("Flags", obj_desc->package.flags); | 791 | acpi_ex_out_integer ("Flags", obj_desc->package.flags); |
651 | acpi_ex_out_integer ("Count", obj_desc->package.count); | 792 | acpi_ex_out_integer ("Elements", obj_desc->package.count); |
652 | acpi_ex_out_pointer ("Elements", obj_desc->package.elements); | 793 | acpi_ex_out_pointer ("Element List", obj_desc->package.elements); |
653 | 794 | ||
654 | /* Dump the package contents */ | 795 | /* Dump the package contents */ |
655 | 796 | ||
656 | if (obj_desc->package.count > 0) { | 797 | acpi_os_printf ("\nPackage Contents:\n"); |
657 | acpi_os_printf ("\nPackage Contents:\n"); | 798 | acpi_ex_dump_package (obj_desc, 0, 0); |
658 | for (i = 0; i < obj_desc->package.count; i++) { | ||
659 | acpi_os_printf ("[%.3d] %p", i, obj_desc->package.elements[i]); | ||
660 | if (obj_desc->package.elements[i]) { | ||
661 | acpi_os_printf (" %s", | ||
662 | acpi_ut_get_object_type_name (obj_desc->package.elements[i])); | ||
663 | } | ||
664 | acpi_os_printf ("\n"); | ||
665 | } | ||
666 | } | ||
667 | break; | 799 | break; |
668 | 800 | ||
669 | 801 | ||
@@ -686,7 +818,7 @@ acpi_ex_dump_object_descriptor ( | |||
686 | acpi_ex_out_integer ("param_count", obj_desc->method.param_count); | 818 | acpi_ex_out_integer ("param_count", obj_desc->method.param_count); |
687 | acpi_ex_out_integer ("Concurrency", obj_desc->method.concurrency); | 819 | acpi_ex_out_integer ("Concurrency", obj_desc->method.concurrency); |
688 | acpi_ex_out_pointer ("Semaphore", obj_desc->method.semaphore); | 820 | acpi_ex_out_pointer ("Semaphore", obj_desc->method.semaphore); |
689 | acpi_ex_out_integer ("owning_id", obj_desc->method.owning_id); | 821 | acpi_ex_out_integer ("owner_id", obj_desc->method.owner_id); |
690 | acpi_ex_out_integer ("aml_length", obj_desc->method.aml_length); | 822 | acpi_ex_out_integer ("aml_length", obj_desc->method.aml_length); |
691 | acpi_ex_out_pointer ("aml_start", obj_desc->method.aml_start); | 823 | acpi_ex_out_pointer ("aml_start", obj_desc->method.aml_start); |
692 | break; | 824 | break; |
@@ -790,10 +922,7 @@ acpi_ex_dump_object_descriptor ( | |||
790 | acpi_ex_out_pointer ("Node", obj_desc->reference.node); | 922 | acpi_ex_out_pointer ("Node", obj_desc->reference.node); |
791 | acpi_ex_out_pointer ("Where", obj_desc->reference.where); | 923 | acpi_ex_out_pointer ("Where", obj_desc->reference.where); |
792 | 924 | ||
793 | if (obj_desc->reference.object) { | 925 | acpi_ex_dump_reference (obj_desc); |
794 | acpi_os_printf ("\nReferenced Object:\n"); | ||
795 | acpi_ex_dump_object_descriptor (obj_desc->reference.object, flags); | ||
796 | } | ||
797 | break; | 926 | break; |
798 | 927 | ||
799 | 928 | ||
diff --git a/drivers/acpi/executer/exfield.c b/drivers/acpi/executer/exfield.c index 22c8fa480f60..a690c9250990 100644 --- a/drivers/acpi/executer/exfield.c +++ b/drivers/acpi/executer/exfield.c | |||
@@ -87,6 +87,9 @@ acpi_ex_read_data_from_field ( | |||
87 | if (!obj_desc) { | 87 | if (!obj_desc) { |
88 | return_ACPI_STATUS (AE_AML_NO_OPERAND); | 88 | return_ACPI_STATUS (AE_AML_NO_OPERAND); |
89 | } | 89 | } |
90 | if (!ret_buffer_desc) { | ||
91 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
92 | } | ||
90 | 93 | ||
91 | if (ACPI_GET_OBJECT_TYPE (obj_desc) == ACPI_TYPE_BUFFER_FIELD) { | 94 | if (ACPI_GET_OBJECT_TYPE (obj_desc) == ACPI_TYPE_BUFFER_FIELD) { |
92 | /* | 95 | /* |
@@ -182,7 +185,7 @@ exit: | |||
182 | if (ACPI_FAILURE (status)) { | 185 | if (ACPI_FAILURE (status)) { |
183 | acpi_ut_remove_reference (buffer_desc); | 186 | acpi_ut_remove_reference (buffer_desc); |
184 | } | 187 | } |
185 | else if (ret_buffer_desc) { | 188 | else { |
186 | *ret_buffer_desc = buffer_desc; | 189 | *ret_buffer_desc = buffer_desc; |
187 | } | 190 | } |
188 | 191 | ||
diff --git a/drivers/acpi/executer/exmisc.c b/drivers/acpi/executer/exmisc.c index 022f281345b8..237ef28c8132 100644 --- a/drivers/acpi/executer/exmisc.c +++ b/drivers/acpi/executer/exmisc.c | |||
@@ -302,7 +302,7 @@ acpi_ex_do_concatenate ( | |||
302 | /* Result of two Integers is a Buffer */ | 302 | /* Result of two Integers is a Buffer */ |
303 | /* Need enough buffer space for two integers */ | 303 | /* Need enough buffer space for two integers */ |
304 | 304 | ||
305 | return_desc = acpi_ut_create_buffer_object ( | 305 | return_desc = acpi_ut_create_buffer_object ((acpi_size) |
306 | ACPI_MUL_2 (acpi_gbl_integer_byte_width)); | 306 | ACPI_MUL_2 (acpi_gbl_integer_byte_width)); |
307 | if (!return_desc) { | 307 | if (!return_desc) { |
308 | status = AE_NO_MEMORY; | 308 | status = AE_NO_MEMORY; |
diff --git a/drivers/acpi/executer/exnames.c b/drivers/acpi/executer/exnames.c index 639f0bd3f6d8..b6ba1a7a677a 100644 --- a/drivers/acpi/executer/exnames.c +++ b/drivers/acpi/executer/exnames.c | |||
@@ -438,6 +438,13 @@ acpi_ex_get_name_string ( | |||
438 | status = AE_AML_BAD_NAME; | 438 | status = AE_AML_BAD_NAME; |
439 | } | 439 | } |
440 | 440 | ||
441 | if (ACPI_FAILURE (status)) { | ||
442 | if (name_string) { | ||
443 | ACPI_MEM_FREE (name_string); | ||
444 | } | ||
445 | return_ACPI_STATUS (status); | ||
446 | } | ||
447 | |||
441 | *out_name_string = name_string; | 448 | *out_name_string = name_string; |
442 | *out_name_length = (u32) (aml_address - in_aml_address); | 449 | *out_name_length = (u32) (aml_address - in_aml_address); |
443 | 450 | ||
diff --git a/drivers/acpi/executer/exoparg1.c b/drivers/acpi/executer/exoparg1.c index dbdf8262ba00..48c30f800083 100644 --- a/drivers/acpi/executer/exoparg1.c +++ b/drivers/acpi/executer/exoparg1.c | |||
@@ -113,8 +113,9 @@ acpi_ex_opcode_0A_0T_1R ( | |||
113 | status = AE_NO_MEMORY; | 113 | status = AE_NO_MEMORY; |
114 | goto cleanup; | 114 | goto cleanup; |
115 | } | 115 | } |
116 | 116 | #if ACPI_MACHINE_WIDTH != 16 | |
117 | return_desc->integer.value = acpi_os_get_timer (); | 117 | return_desc->integer.value = acpi_os_get_timer (); |
118 | #endif | ||
118 | break; | 119 | break; |
119 | 120 | ||
120 | default: /* Unknown opcode */ | 121 | default: /* Unknown opcode */ |
@@ -127,15 +128,16 @@ acpi_ex_opcode_0A_0T_1R ( | |||
127 | 128 | ||
128 | cleanup: | 129 | cleanup: |
129 | 130 | ||
130 | if (!walk_state->result_obj) { | ||
131 | walk_state->result_obj = return_desc; | ||
132 | } | ||
133 | |||
134 | /* Delete return object on error */ | 131 | /* Delete return object on error */ |
135 | 132 | ||
136 | if (ACPI_FAILURE (status)) { | 133 | if ((ACPI_FAILURE (status)) || walk_state->result_obj) { |
137 | acpi_ut_remove_reference (return_desc); | 134 | acpi_ut_remove_reference (return_desc); |
138 | } | 135 | } |
136 | else { | ||
137 | /* Save the return value */ | ||
138 | |||
139 | walk_state->result_obj = return_desc; | ||
140 | } | ||
139 | 141 | ||
140 | return_ACPI_STATUS (status); | 142 | return_ACPI_STATUS (status); |
141 | } | 143 | } |
@@ -902,6 +904,7 @@ acpi_ex_opcode_1A_0T_1R ( | |||
902 | */ | 904 | */ |
903 | return_desc = acpi_ns_get_attached_object ( | 905 | return_desc = acpi_ns_get_attached_object ( |
904 | (struct acpi_namespace_node *) operand[0]); | 906 | (struct acpi_namespace_node *) operand[0]); |
907 | acpi_ut_add_reference (return_desc); | ||
905 | } | 908 | } |
906 | else { | 909 | else { |
907 | /* | 910 | /* |
@@ -951,20 +954,10 @@ acpi_ex_opcode_1A_0T_1R ( | |||
951 | * add another reference to the referenced object, however. | 954 | * add another reference to the referenced object, however. |
952 | */ | 955 | */ |
953 | return_desc = *(operand[0]->reference.where); | 956 | return_desc = *(operand[0]->reference.where); |
954 | if (!return_desc) { | 957 | if (return_desc) { |
955 | /* | 958 | acpi_ut_add_reference (return_desc); |
956 | * We can't return a NULL dereferenced value. This is | ||
957 | * an uninitialized package element and is thus a | ||
958 | * severe error. | ||
959 | */ | ||
960 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
961 | "NULL package element obj %p\n", | ||
962 | operand[0])); | ||
963 | status = AE_AML_UNINITIALIZED_ELEMENT; | ||
964 | goto cleanup; | ||
965 | } | 959 | } |
966 | 960 | ||
967 | acpi_ut_add_reference (return_desc); | ||
968 | break; | 961 | break; |
969 | 962 | ||
970 | 963 | ||
diff --git a/drivers/acpi/executer/exoparg3.c b/drivers/acpi/executer/exoparg3.c index 23b068adbf58..197890f443b5 100644 --- a/drivers/acpi/executer/exoparg3.c +++ b/drivers/acpi/executer/exoparg3.c | |||
@@ -160,7 +160,7 @@ acpi_ex_opcode_3A_1T_1R ( | |||
160 | { | 160 | { |
161 | union acpi_operand_object **operand = &walk_state->operands[0]; | 161 | union acpi_operand_object **operand = &walk_state->operands[0]; |
162 | union acpi_operand_object *return_desc = NULL; | 162 | union acpi_operand_object *return_desc = NULL; |
163 | char *buffer; | 163 | char *buffer = NULL; |
164 | acpi_status status = AE_OK; | 164 | acpi_status status = AE_OK; |
165 | acpi_integer index; | 165 | acpi_integer index; |
166 | acpi_size length; | 166 | acpi_size length; |
@@ -193,34 +193,63 @@ acpi_ex_opcode_3A_1T_1R ( | |||
193 | * If the index is beyond the length of the String/Buffer, or if the | 193 | * If the index is beyond the length of the String/Buffer, or if the |
194 | * requested length is zero, return a zero-length String/Buffer | 194 | * requested length is zero, return a zero-length String/Buffer |
195 | */ | 195 | */ |
196 | if ((index < operand[0]->string.length) && | 196 | if (index >= operand[0]->string.length) { |
197 | (length > 0)) { | 197 | length = 0; |
198 | /* Truncate request if larger than the actual String/Buffer */ | 198 | } |
199 | 199 | ||
200 | if ((index + length) > | 200 | /* Truncate request if larger than the actual String/Buffer */ |
201 | operand[0]->string.length) { | 201 | |
202 | length = (acpi_size) operand[0]->string.length - | 202 | else if ((index + length) > operand[0]->string.length) { |
203 | (acpi_size) index; | 203 | length = (acpi_size) operand[0]->string.length - |
204 | } | 204 | (acpi_size) index; |
205 | } | ||
205 | 206 | ||
206 | /* Allocate a new buffer for the String/Buffer */ | 207 | /* Strings always have a sub-pointer, not so for buffers */ |
208 | |||
209 | switch (ACPI_GET_OBJECT_TYPE (operand[0])) { | ||
210 | case ACPI_TYPE_STRING: | ||
211 | |||
212 | /* Always allocate a new buffer for the String */ | ||
207 | 213 | ||
208 | buffer = ACPI_MEM_CALLOCATE ((acpi_size) length + 1); | 214 | buffer = ACPI_MEM_CALLOCATE ((acpi_size) length + 1); |
209 | if (!buffer) { | 215 | if (!buffer) { |
210 | status = AE_NO_MEMORY; | 216 | status = AE_NO_MEMORY; |
211 | goto cleanup; | 217 | goto cleanup; |
212 | } | 218 | } |
219 | break; | ||
220 | |||
221 | case ACPI_TYPE_BUFFER: | ||
222 | |||
223 | /* If the requested length is zero, don't allocate a buffer */ | ||
224 | |||
225 | if (length > 0) { | ||
226 | /* Allocate a new buffer for the Buffer */ | ||
227 | |||
228 | buffer = ACPI_MEM_CALLOCATE (length); | ||
229 | if (!buffer) { | ||
230 | status = AE_NO_MEMORY; | ||
231 | goto cleanup; | ||
232 | } | ||
233 | } | ||
234 | break; | ||
213 | 235 | ||
236 | default: /* Should not happen */ | ||
237 | |||
238 | status = AE_AML_OPERAND_TYPE; | ||
239 | goto cleanup; | ||
240 | } | ||
241 | |||
242 | if (length > 0) { | ||
214 | /* Copy the portion requested */ | 243 | /* Copy the portion requested */ |
215 | 244 | ||
216 | ACPI_MEMCPY (buffer, operand[0]->string.pointer + index, | 245 | ACPI_MEMCPY (buffer, operand[0]->string.pointer + index, |
217 | length); | 246 | length); |
247 | } | ||
218 | 248 | ||
219 | /* Set the length of the new String/Buffer */ | 249 | /* Set the length of the new String/Buffer */ |
220 | 250 | ||
221 | return_desc->string.pointer = buffer; | 251 | return_desc->string.pointer = buffer; |
222 | return_desc->string.length = (u32) length; | 252 | return_desc->string.length = (u32) length; |
223 | } | ||
224 | 253 | ||
225 | /* Mark buffer initialized */ | 254 | /* Mark buffer initialized */ |
226 | 255 | ||
@@ -244,13 +273,13 @@ cleanup: | |||
244 | 273 | ||
245 | /* Delete return object on error */ | 274 | /* Delete return object on error */ |
246 | 275 | ||
247 | if (ACPI_FAILURE (status)) { | 276 | if (ACPI_FAILURE (status) || walk_state->result_obj) { |
248 | acpi_ut_remove_reference (return_desc); | 277 | acpi_ut_remove_reference (return_desc); |
249 | } | 278 | } |
250 | 279 | ||
251 | /* Set the return object and exit */ | 280 | /* Set the return object and exit */ |
252 | 281 | ||
253 | if (!walk_state->result_obj) { | 282 | else { |
254 | walk_state->result_obj = return_desc; | 283 | walk_state->result_obj = return_desc; |
255 | } | 284 | } |
256 | return_ACPI_STATUS (status); | 285 | return_ACPI_STATUS (status); |
diff --git a/drivers/acpi/executer/exresop.c b/drivers/acpi/executer/exresop.c index d8b470eefe7a..aaba7abcb52d 100644 --- a/drivers/acpi/executer/exresop.c +++ b/drivers/acpi/executer/exresop.c | |||
@@ -426,6 +426,10 @@ acpi_ex_resolve_operands ( | |||
426 | 426 | ||
427 | return_ACPI_STATUS (status); | 427 | return_ACPI_STATUS (status); |
428 | } | 428 | } |
429 | |||
430 | if (obj_desc != *stack_ptr) { | ||
431 | acpi_ut_remove_reference (obj_desc); | ||
432 | } | ||
429 | goto next_operand; | 433 | goto next_operand; |
430 | 434 | ||
431 | 435 | ||
@@ -448,6 +452,10 @@ acpi_ex_resolve_operands ( | |||
448 | 452 | ||
449 | return_ACPI_STATUS (status); | 453 | return_ACPI_STATUS (status); |
450 | } | 454 | } |
455 | |||
456 | if (obj_desc != *stack_ptr) { | ||
457 | acpi_ut_remove_reference (obj_desc); | ||
458 | } | ||
451 | goto next_operand; | 459 | goto next_operand; |
452 | 460 | ||
453 | 461 | ||
@@ -471,6 +479,10 @@ acpi_ex_resolve_operands ( | |||
471 | 479 | ||
472 | return_ACPI_STATUS (status); | 480 | return_ACPI_STATUS (status); |
473 | } | 481 | } |
482 | |||
483 | if (obj_desc != *stack_ptr) { | ||
484 | acpi_ut_remove_reference (obj_desc); | ||
485 | } | ||
474 | goto next_operand; | 486 | goto next_operand; |
475 | 487 | ||
476 | 488 | ||
@@ -515,6 +527,10 @@ acpi_ex_resolve_operands ( | |||
515 | if (ACPI_FAILURE (status)) { | 527 | if (ACPI_FAILURE (status)) { |
516 | return_ACPI_STATUS (status); | 528 | return_ACPI_STATUS (status); |
517 | } | 529 | } |
530 | |||
531 | if (obj_desc != *stack_ptr) { | ||
532 | acpi_ut_remove_reference (obj_desc); | ||
533 | } | ||
518 | break; | 534 | break; |
519 | 535 | ||
520 | default: | 536 | default: |
diff --git a/drivers/acpi/executer/exstore.c b/drivers/acpi/executer/exstore.c index 2725db0901b8..59dbfeaa54c0 100644 --- a/drivers/acpi/executer/exstore.c +++ b/drivers/acpi/executer/exstore.c | |||
@@ -147,7 +147,7 @@ acpi_ex_do_debug_object ( | |||
147 | 147 | ||
148 | case ACPI_TYPE_BUFFER: | 148 | case ACPI_TYPE_BUFFER: |
149 | 149 | ||
150 | ACPI_DEBUG_PRINT_RAW ((ACPI_DB_DEBUG_OBJECT, "[0x%.2X]", | 150 | ACPI_DEBUG_PRINT_RAW ((ACPI_DB_DEBUG_OBJECT, "[0x%.2X]\n", |
151 | (u32) source_desc->buffer.length)); | 151 | (u32) source_desc->buffer.length)); |
152 | ACPI_DUMP_BUFFER (source_desc->buffer.pointer, | 152 | ACPI_DUMP_BUFFER (source_desc->buffer.pointer, |
153 | (source_desc->buffer.length < 32) ? source_desc->buffer.length : 32); | 153 | (source_desc->buffer.length < 32) ? source_desc->buffer.length : 32); |
@@ -574,7 +574,7 @@ acpi_ex_store_object_to_node ( | |||
574 | 574 | ||
575 | /* If no implicit conversion, drop into the default case below */ | 575 | /* If no implicit conversion, drop into the default case below */ |
576 | 576 | ||
577 | if (!implicit_conversion) { | 577 | if ((!implicit_conversion) || (walk_state->opcode == AML_COPY_OP)) { |
578 | /* Force execution of default (no implicit conversion) */ | 578 | /* Force execution of default (no implicit conversion) */ |
579 | 579 | ||
580 | target_type = ACPI_TYPE_ANY; | 580 | target_type = ACPI_TYPE_ANY; |
@@ -634,7 +634,7 @@ acpi_ex_store_object_to_node ( | |||
634 | default: | 634 | default: |
635 | 635 | ||
636 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, | 636 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, |
637 | "Storing %s (%p) directly into node (%p), no implicit conversion\n", | 637 | "Storing %s (%p) directly into node (%p) with no implicit conversion\n", |
638 | acpi_ut_get_object_type_name (source_desc), source_desc, node)); | 638 | acpi_ut_get_object_type_name (source_desc), source_desc, node)); |
639 | 639 | ||
640 | /* No conversions for all other types. Just attach the source object */ | 640 | /* No conversions for all other types. Just attach the source object */ |
diff --git a/drivers/acpi/executer/exstoren.c b/drivers/acpi/executer/exstoren.c index 120f30ed0bd4..433588ab432a 100644 --- a/drivers/acpi/executer/exstoren.c +++ b/drivers/acpi/executer/exstoren.c | |||
@@ -265,10 +265,6 @@ acpi_ex_store_object_to_object ( | |||
265 | 265 | ||
266 | case ACPI_TYPE_BUFFER: | 266 | case ACPI_TYPE_BUFFER: |
267 | 267 | ||
268 | /* | ||
269 | * Note: There is different store behavior depending on the original | ||
270 | * source type | ||
271 | */ | ||
272 | status = acpi_ex_store_buffer_to_buffer (actual_src_desc, dest_desc); | 268 | status = acpi_ex_store_buffer_to_buffer (actual_src_desc, dest_desc); |
273 | break; | 269 | break; |
274 | 270 | ||
diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c index 5c7ec0c04177..d00b0dcba96a 100644 --- a/drivers/acpi/executer/exutils.c +++ b/drivers/acpi/executer/exutils.c | |||
@@ -369,7 +369,7 @@ acpi_ex_eisa_id_to_string ( | |||
369 | * | 369 | * |
370 | * RETURN: None, string | 370 | * RETURN: None, string |
371 | * | 371 | * |
372 | * DESCRIPTOIN: Convert a number to string representation. Assumes string | 372 | * DESCRIPTION: Convert a number to string representation. Assumes string |
373 | * buffer is large enough to hold the string. | 373 | * buffer is large enough to hold the string. |
374 | * | 374 | * |
375 | ******************************************************************************/ | 375 | ******************************************************************************/ |
diff --git a/drivers/acpi/hardware/hwgpe.c b/drivers/acpi/hardware/hwgpe.c index 8daeabb2fc7a..3536bbb990c3 100644 --- a/drivers/acpi/hardware/hwgpe.c +++ b/drivers/acpi/hardware/hwgpe.c | |||
@@ -374,7 +374,7 @@ acpi_hw_enable_wakeup_gpe_block ( | |||
374 | * | 374 | * |
375 | * FUNCTION: acpi_hw_disable_all_gpes | 375 | * FUNCTION: acpi_hw_disable_all_gpes |
376 | * | 376 | * |
377 | * PARAMETERS: Flags - ACPI_NOT_ISR or ACPI_ISR | 377 | * PARAMETERS: None |
378 | * | 378 | * |
379 | * RETURN: Status | 379 | * RETURN: Status |
380 | * | 380 | * |
@@ -384,7 +384,7 @@ acpi_hw_enable_wakeup_gpe_block ( | |||
384 | 384 | ||
385 | acpi_status | 385 | acpi_status |
386 | acpi_hw_disable_all_gpes ( | 386 | acpi_hw_disable_all_gpes ( |
387 | u32 flags) | 387 | void) |
388 | { | 388 | { |
389 | acpi_status status; | 389 | acpi_status status; |
390 | 390 | ||
@@ -392,8 +392,8 @@ acpi_hw_disable_all_gpes ( | |||
392 | ACPI_FUNCTION_TRACE ("hw_disable_all_gpes"); | 392 | ACPI_FUNCTION_TRACE ("hw_disable_all_gpes"); |
393 | 393 | ||
394 | 394 | ||
395 | status = acpi_ev_walk_gpe_list (acpi_hw_disable_gpe_block, flags); | 395 | status = acpi_ev_walk_gpe_list (acpi_hw_disable_gpe_block); |
396 | status = acpi_ev_walk_gpe_list (acpi_hw_clear_gpe_block, flags); | 396 | status = acpi_ev_walk_gpe_list (acpi_hw_clear_gpe_block); |
397 | return_ACPI_STATUS (status); | 397 | return_ACPI_STATUS (status); |
398 | } | 398 | } |
399 | 399 | ||
@@ -402,7 +402,7 @@ acpi_hw_disable_all_gpes ( | |||
402 | * | 402 | * |
403 | * FUNCTION: acpi_hw_enable_all_runtime_gpes | 403 | * FUNCTION: acpi_hw_enable_all_runtime_gpes |
404 | * | 404 | * |
405 | * PARAMETERS: Flags - ACPI_NOT_ISR or ACPI_ISR | 405 | * PARAMETERS: None |
406 | * | 406 | * |
407 | * RETURN: Status | 407 | * RETURN: Status |
408 | * | 408 | * |
@@ -412,7 +412,7 @@ acpi_hw_disable_all_gpes ( | |||
412 | 412 | ||
413 | acpi_status | 413 | acpi_status |
414 | acpi_hw_enable_all_runtime_gpes ( | 414 | acpi_hw_enable_all_runtime_gpes ( |
415 | u32 flags) | 415 | void) |
416 | { | 416 | { |
417 | acpi_status status; | 417 | acpi_status status; |
418 | 418 | ||
@@ -420,7 +420,7 @@ acpi_hw_enable_all_runtime_gpes ( | |||
420 | ACPI_FUNCTION_TRACE ("hw_enable_all_runtime_gpes"); | 420 | ACPI_FUNCTION_TRACE ("hw_enable_all_runtime_gpes"); |
421 | 421 | ||
422 | 422 | ||
423 | status = acpi_ev_walk_gpe_list (acpi_hw_enable_runtime_gpe_block, flags); | 423 | status = acpi_ev_walk_gpe_list (acpi_hw_enable_runtime_gpe_block); |
424 | return_ACPI_STATUS (status); | 424 | return_ACPI_STATUS (status); |
425 | } | 425 | } |
426 | 426 | ||
@@ -429,7 +429,7 @@ acpi_hw_enable_all_runtime_gpes ( | |||
429 | * | 429 | * |
430 | * FUNCTION: acpi_hw_enable_all_wakeup_gpes | 430 | * FUNCTION: acpi_hw_enable_all_wakeup_gpes |
431 | * | 431 | * |
432 | * PARAMETERS: Flags - ACPI_NOT_ISR or ACPI_ISR | 432 | * PARAMETERS: None |
433 | * | 433 | * |
434 | * RETURN: Status | 434 | * RETURN: Status |
435 | * | 435 | * |
@@ -439,7 +439,7 @@ acpi_hw_enable_all_runtime_gpes ( | |||
439 | 439 | ||
440 | acpi_status | 440 | acpi_status |
441 | acpi_hw_enable_all_wakeup_gpes ( | 441 | acpi_hw_enable_all_wakeup_gpes ( |
442 | u32 flags) | 442 | void) |
443 | { | 443 | { |
444 | acpi_status status; | 444 | acpi_status status; |
445 | 445 | ||
@@ -447,7 +447,7 @@ acpi_hw_enable_all_wakeup_gpes ( | |||
447 | ACPI_FUNCTION_TRACE ("hw_enable_all_wakeup_gpes"); | 447 | ACPI_FUNCTION_TRACE ("hw_enable_all_wakeup_gpes"); |
448 | 448 | ||
449 | 449 | ||
450 | status = acpi_ev_walk_gpe_list (acpi_hw_enable_wakeup_gpe_block, flags); | 450 | status = acpi_ev_walk_gpe_list (acpi_hw_enable_wakeup_gpe_block); |
451 | return_ACPI_STATUS (status); | 451 | return_ACPI_STATUS (status); |
452 | } | 452 | } |
453 | 453 | ||
diff --git a/drivers/acpi/hardware/hwregs.c b/drivers/acpi/hardware/hwregs.c index 6d9e4eb84836..04a058565d8d 100644 --- a/drivers/acpi/hardware/hwregs.c +++ b/drivers/acpi/hardware/hwregs.c | |||
@@ -106,7 +106,7 @@ acpi_hw_clear_acpi_status ( | |||
106 | 106 | ||
107 | /* Clear the GPE Bits in all GPE registers in all GPE blocks */ | 107 | /* Clear the GPE Bits in all GPE registers in all GPE blocks */ |
108 | 108 | ||
109 | status = acpi_ev_walk_gpe_list (acpi_hw_clear_gpe_block, ACPI_ISR); | 109 | status = acpi_ev_walk_gpe_list (acpi_hw_clear_gpe_block); |
110 | 110 | ||
111 | unlock_and_exit: | 111 | unlock_and_exit: |
112 | if (flags & ACPI_MTX_LOCK) { | 112 | if (flags & ACPI_MTX_LOCK) { |
diff --git a/drivers/acpi/hardware/hwsleep.c b/drivers/acpi/hardware/hwsleep.c index 415d342aeab5..cedee0c43b5f 100644 --- a/drivers/acpi/hardware/hwsleep.c +++ b/drivers/acpi/hardware/hwsleep.c | |||
@@ -274,13 +274,13 @@ acpi_enter_sleep_state ( | |||
274 | * 1) Disable/Clear all GPEs | 274 | * 1) Disable/Clear all GPEs |
275 | * 2) Enable all wakeup GPEs | 275 | * 2) Enable all wakeup GPEs |
276 | */ | 276 | */ |
277 | status = acpi_hw_disable_all_gpes (ACPI_ISR); | 277 | status = acpi_hw_disable_all_gpes (); |
278 | if (ACPI_FAILURE (status)) { | 278 | if (ACPI_FAILURE (status)) { |
279 | return_ACPI_STATUS (status); | 279 | return_ACPI_STATUS (status); |
280 | } | 280 | } |
281 | acpi_gbl_system_awake_and_running = FALSE; | 281 | acpi_gbl_system_awake_and_running = FALSE; |
282 | 282 | ||
283 | status = acpi_hw_enable_all_wakeup_gpes (ACPI_ISR); | 283 | status = acpi_hw_enable_all_wakeup_gpes (); |
284 | if (ACPI_FAILURE (status)) { | 284 | if (ACPI_FAILURE (status)) { |
285 | return_ACPI_STATUS (status); | 285 | return_ACPI_STATUS (status); |
286 | } | 286 | } |
@@ -424,13 +424,13 @@ acpi_enter_sleep_state_s4bios ( | |||
424 | * 1) Disable/Clear all GPEs | 424 | * 1) Disable/Clear all GPEs |
425 | * 2) Enable all wakeup GPEs | 425 | * 2) Enable all wakeup GPEs |
426 | */ | 426 | */ |
427 | status = acpi_hw_disable_all_gpes (ACPI_ISR); | 427 | status = acpi_hw_disable_all_gpes (); |
428 | if (ACPI_FAILURE (status)) { | 428 | if (ACPI_FAILURE (status)) { |
429 | return_ACPI_STATUS (status); | 429 | return_ACPI_STATUS (status); |
430 | } | 430 | } |
431 | acpi_gbl_system_awake_and_running = FALSE; | 431 | acpi_gbl_system_awake_and_running = FALSE; |
432 | 432 | ||
433 | status = acpi_hw_enable_all_wakeup_gpes (ACPI_ISR); | 433 | status = acpi_hw_enable_all_wakeup_gpes (); |
434 | if (ACPI_FAILURE (status)) { | 434 | if (ACPI_FAILURE (status)) { |
435 | return_ACPI_STATUS (status); | 435 | return_ACPI_STATUS (status); |
436 | } | 436 | } |
@@ -557,13 +557,13 @@ acpi_leave_sleep_state ( | |||
557 | * 1) Disable/Clear all GPEs | 557 | * 1) Disable/Clear all GPEs |
558 | * 2) Enable all runtime GPEs | 558 | * 2) Enable all runtime GPEs |
559 | */ | 559 | */ |
560 | status = acpi_hw_disable_all_gpes (ACPI_NOT_ISR); | 560 | status = acpi_hw_disable_all_gpes (); |
561 | if (ACPI_FAILURE (status)) { | 561 | if (ACPI_FAILURE (status)) { |
562 | return_ACPI_STATUS (status); | 562 | return_ACPI_STATUS (status); |
563 | } | 563 | } |
564 | acpi_gbl_system_awake_and_running = TRUE; | 564 | acpi_gbl_system_awake_and_running = TRUE; |
565 | 565 | ||
566 | status = acpi_hw_enable_all_runtime_gpes (ACPI_NOT_ISR); | 566 | status = acpi_hw_enable_all_runtime_gpes (); |
567 | if (ACPI_FAILURE (status)) { | 567 | if (ACPI_FAILURE (status)) { |
568 | return_ACPI_STATUS (status); | 568 | return_ACPI_STATUS (status); |
569 | } | 569 | } |
diff --git a/drivers/acpi/namespace/nsaccess.c b/drivers/acpi/namespace/nsaccess.c index ece7a9dedd5c..7589e1fdf25a 100644 --- a/drivers/acpi/namespace/nsaccess.c +++ b/drivers/acpi/namespace/nsaccess.c | |||
@@ -159,19 +159,20 @@ acpi_ns_root_initialize ( | |||
159 | obj_desc->method.param_count = (u8) ACPI_TO_INTEGER (val); | 159 | obj_desc->method.param_count = (u8) ACPI_TO_INTEGER (val); |
160 | obj_desc->common.flags |= AOPOBJ_DATA_VALID; | 160 | obj_desc->common.flags |= AOPOBJ_DATA_VALID; |
161 | 161 | ||
162 | #if defined (_ACPI_ASL_COMPILER) || defined (_ACPI_DUMP_App) | 162 | #if defined (ACPI_ASL_COMPILER) |
163 | 163 | ||
164 | /* | 164 | /* save the parameter count for the i_aSL compiler */ |
165 | * i_aSL Compiler cheats by putting parameter count | 165 | |
166 | * in the owner_iD | 166 | new_node->value = obj_desc->method.param_count; |
167 | */ | ||
168 | new_node->owner_id = obj_desc->method.param_count; | ||
169 | #else | 167 | #else |
170 | /* Mark this as a very SPECIAL method */ | 168 | /* Mark this as a very SPECIAL method */ |
171 | 169 | ||
172 | obj_desc->method.method_flags = AML_METHOD_INTERNAL_ONLY; | 170 | obj_desc->method.method_flags = AML_METHOD_INTERNAL_ONLY; |
171 | |||
172 | #ifndef ACPI_DUMP_APP | ||
173 | obj_desc->method.implementation = acpi_ut_osi_implementation; | 173 | obj_desc->method.implementation = acpi_ut_osi_implementation; |
174 | #endif | 174 | #endif |
175 | #endif | ||
175 | break; | 176 | break; |
176 | 177 | ||
177 | case ACPI_TYPE_INTEGER: | 178 | case ACPI_TYPE_INTEGER: |
diff --git a/drivers/acpi/namespace/nsalloc.c b/drivers/acpi/namespace/nsalloc.c index 5653a19d7172..21d560decbf9 100644 --- a/drivers/acpi/namespace/nsalloc.c +++ b/drivers/acpi/namespace/nsalloc.c | |||
@@ -83,7 +83,7 @@ acpi_ns_create_node ( | |||
83 | return_PTR (NULL); | 83 | return_PTR (NULL); |
84 | } | 84 | } |
85 | 85 | ||
86 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_NSNODE].total_allocated++); | 86 | ACPI_MEM_TRACKING (acpi_gbl_ns_node_list->total_allocated++); |
87 | 87 | ||
88 | node->name.integer = name; | 88 | node->name.integer = name; |
89 | node->reference_count = 1; | 89 | node->reference_count = 1; |
@@ -151,7 +151,7 @@ acpi_ns_delete_node ( | |||
151 | } | 151 | } |
152 | } | 152 | } |
153 | 153 | ||
154 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_NSNODE].total_freed++); | 154 | ACPI_MEM_TRACKING (acpi_gbl_ns_node_list->total_freed++); |
155 | 155 | ||
156 | /* | 156 | /* |
157 | * Detach an object if there is one then delete the node | 157 | * Detach an object if there is one then delete the node |
@@ -176,10 +176,9 @@ acpi_ns_delete_node ( | |||
176 | * DESCRIPTION: Initialize a new namespace node and install it amongst | 176 | * DESCRIPTION: Initialize a new namespace node and install it amongst |
177 | * its peers. | 177 | * its peers. |
178 | * | 178 | * |
179 | * Note: Current namespace lookup is linear search. However, the | 179 | * Note: Current namespace lookup is linear search. This appears |
180 | * nodes are linked in alphabetical order to 1) put all reserved | 180 | * to be sufficient as namespace searches consume only a small |
181 | * names (start with underscore) first, and to 2) make a readable | 181 | * fraction of the execution time of the ACPI subsystem. |
182 | * namespace dump. | ||
183 | * | 182 | * |
184 | ******************************************************************************/ | 183 | ******************************************************************************/ |
185 | 184 | ||
@@ -190,12 +189,8 @@ acpi_ns_install_node ( | |||
190 | struct acpi_namespace_node *node, /* New Child*/ | 189 | struct acpi_namespace_node *node, /* New Child*/ |
191 | acpi_object_type type) | 190 | acpi_object_type type) |
192 | { | 191 | { |
193 | u16 owner_id = 0; | 192 | acpi_owner_id owner_id = 0; |
194 | struct acpi_namespace_node *child_node; | 193 | struct acpi_namespace_node *child_node; |
195 | #ifdef ACPI_ALPHABETIC_NAMESPACE | ||
196 | |||
197 | struct acpi_namespace_node *previous_child_node; | ||
198 | #endif | ||
199 | 194 | ||
200 | 195 | ||
201 | ACPI_FUNCTION_TRACE ("ns_install_node"); | 196 | ACPI_FUNCTION_TRACE ("ns_install_node"); |
@@ -219,57 +214,6 @@ acpi_ns_install_node ( | |||
219 | node->peer = parent_node; | 214 | node->peer = parent_node; |
220 | } | 215 | } |
221 | else { | 216 | else { |
222 | #ifdef ACPI_ALPHABETIC_NAMESPACE | ||
223 | /* | ||
224 | * Walk the list whilst searching for the correct | ||
225 | * alphabetic placement. | ||
226 | */ | ||
227 | previous_child_node = NULL; | ||
228 | while (acpi_ns_compare_names (acpi_ut_get_node_name (child_node), | ||
229 | acpi_ut_get_node_name (node)) < 0) { | ||
230 | if (child_node->flags & ANOBJ_END_OF_PEER_LIST) { | ||
231 | /* Last peer; Clear end-of-list flag */ | ||
232 | |||
233 | child_node->flags &= ~ANOBJ_END_OF_PEER_LIST; | ||
234 | |||
235 | /* This node is the new peer to the child node */ | ||
236 | |||
237 | child_node->peer = node; | ||
238 | |||
239 | /* This node is the new end-of-list */ | ||
240 | |||
241 | node->flags |= ANOBJ_END_OF_PEER_LIST; | ||
242 | node->peer = parent_node; | ||
243 | break; | ||
244 | } | ||
245 | |||
246 | /* Get next peer */ | ||
247 | |||
248 | previous_child_node = child_node; | ||
249 | child_node = child_node->peer; | ||
250 | } | ||
251 | |||
252 | /* Did the node get inserted at the end-of-list? */ | ||
253 | |||
254 | if (!(node->flags & ANOBJ_END_OF_PEER_LIST)) { | ||
255 | /* | ||
256 | * Loop above terminated without reaching the end-of-list. | ||
257 | * Insert the new node at the current location | ||
258 | */ | ||
259 | if (previous_child_node) { | ||
260 | /* Insert node alphabetically */ | ||
261 | |||
262 | node->peer = child_node; | ||
263 | previous_child_node->peer = node; | ||
264 | } | ||
265 | else { | ||
266 | /* Insert node alphabetically at start of list */ | ||
267 | |||
268 | node->peer = child_node; | ||
269 | parent_node->child = node; | ||
270 | } | ||
271 | } | ||
272 | #else | ||
273 | while (!(child_node->flags & ANOBJ_END_OF_PEER_LIST)) { | 217 | while (!(child_node->flags & ANOBJ_END_OF_PEER_LIST)) { |
274 | child_node = child_node->peer; | 218 | child_node = child_node->peer; |
275 | } | 219 | } |
@@ -279,9 +223,8 @@ acpi_ns_install_node ( | |||
279 | /* Clear end-of-list flag */ | 223 | /* Clear end-of-list flag */ |
280 | 224 | ||
281 | child_node->flags &= ~ANOBJ_END_OF_PEER_LIST; | 225 | child_node->flags &= ~ANOBJ_END_OF_PEER_LIST; |
282 | node->flags |= ANOBJ_END_OF_PEER_LIST; | 226 | node->flags |= ANOBJ_END_OF_PEER_LIST; |
283 | node->peer = parent_node; | 227 | node->peer = parent_node; |
284 | #endif | ||
285 | } | 228 | } |
286 | 229 | ||
287 | /* Init the new entry */ | 230 | /* Init the new entry */ |
@@ -362,7 +305,7 @@ acpi_ns_delete_children ( | |||
362 | 305 | ||
363 | /* Now we can free this child object */ | 306 | /* Now we can free this child object */ |
364 | 307 | ||
365 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_NSNODE].total_freed++); | 308 | ACPI_MEM_TRACKING (acpi_gbl_ns_node_list->total_freed++); |
366 | 309 | ||
367 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Object %p, Remaining %X\n", | 310 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Object %p, Remaining %X\n", |
368 | child_node, acpi_gbl_current_node_count)); | 311 | child_node, acpi_gbl_current_node_count)); |
@@ -559,7 +502,7 @@ acpi_ns_remove_reference ( | |||
559 | 502 | ||
560 | void | 503 | void |
561 | acpi_ns_delete_namespace_by_owner ( | 504 | acpi_ns_delete_namespace_by_owner ( |
562 | u16 owner_id) | 505 | acpi_owner_id owner_id) |
563 | { | 506 | { |
564 | struct acpi_namespace_node *child_node; | 507 | struct acpi_namespace_node *child_node; |
565 | struct acpi_namespace_node *deletion_node; | 508 | struct acpi_namespace_node *deletion_node; |
@@ -570,6 +513,10 @@ acpi_ns_delete_namespace_by_owner ( | |||
570 | ACPI_FUNCTION_TRACE_U32 ("ns_delete_namespace_by_owner", owner_id); | 513 | ACPI_FUNCTION_TRACE_U32 ("ns_delete_namespace_by_owner", owner_id); |
571 | 514 | ||
572 | 515 | ||
516 | if (owner_id == 0) { | ||
517 | return_VOID; | ||
518 | } | ||
519 | |||
573 | parent_node = acpi_gbl_root_node; | 520 | parent_node = acpi_gbl_root_node; |
574 | child_node = NULL; | 521 | child_node = NULL; |
575 | deletion_node = NULL; | 522 | deletion_node = NULL; |
@@ -639,54 +586,3 @@ acpi_ns_delete_namespace_by_owner ( | |||
639 | } | 586 | } |
640 | 587 | ||
641 | 588 | ||
642 | #ifdef ACPI_ALPHABETIC_NAMESPACE | ||
643 | /******************************************************************************* | ||
644 | * | ||
645 | * FUNCTION: acpi_ns_compare_names | ||
646 | * | ||
647 | * PARAMETERS: Name1 - First name to compare | ||
648 | * Name2 - Second name to compare | ||
649 | * | ||
650 | * RETURN: value from strncmp | ||
651 | * | ||
652 | * DESCRIPTION: Compare two ACPI names. Names that are prefixed with an | ||
653 | * underscore are forced to be alphabetically first. | ||
654 | * | ||
655 | ******************************************************************************/ | ||
656 | |||
657 | int | ||
658 | acpi_ns_compare_names ( | ||
659 | char *name1, | ||
660 | char *name2) | ||
661 | { | ||
662 | char reversed_name1[ACPI_NAME_SIZE]; | ||
663 | char reversed_name2[ACPI_NAME_SIZE]; | ||
664 | u32 i; | ||
665 | u32 j; | ||
666 | |||
667 | |||
668 | /* | ||
669 | * Replace all instances of "underscore" with a value that is smaller so | ||
670 | * that all names that are prefixed with underscore(s) are alphabetically | ||
671 | * first. | ||
672 | * | ||
673 | * Reverse the name bytewise so we can just do a 32-bit compare instead | ||
674 | * of a strncmp. | ||
675 | */ | ||
676 | for (i = 0, j= (ACPI_NAME_SIZE - 1); i < ACPI_NAME_SIZE; i++, j--) { | ||
677 | reversed_name1[j] = name1[i]; | ||
678 | if (name1[i] == '_') { | ||
679 | reversed_name1[j] = '*'; | ||
680 | } | ||
681 | |||
682 | reversed_name2[j] = name2[i]; | ||
683 | if (name2[i] == '_') { | ||
684 | reversed_name2[j] = '*'; | ||
685 | } | ||
686 | } | ||
687 | |||
688 | return (*(int *) reversed_name1 - *(int *) reversed_name2); | ||
689 | } | ||
690 | #endif | ||
691 | |||
692 | |||
diff --git a/drivers/acpi/namespace/nsdump.c b/drivers/acpi/namespace/nsdump.c index 6c2aef0e0dd4..5d25add6b031 100644 --- a/drivers/acpi/namespace/nsdump.c +++ b/drivers/acpi/namespace/nsdump.c | |||
@@ -85,6 +85,9 @@ acpi_ns_print_pathname ( | |||
85 | u32 num_segments, | 85 | u32 num_segments, |
86 | char *pathname) | 86 | char *pathname) |
87 | { | 87 | { |
88 | acpi_native_uint i; | ||
89 | |||
90 | |||
88 | ACPI_FUNCTION_NAME ("ns_print_pathname"); | 91 | ACPI_FUNCTION_NAME ("ns_print_pathname"); |
89 | 92 | ||
90 | 93 | ||
@@ -97,9 +100,13 @@ acpi_ns_print_pathname ( | |||
97 | ACPI_DEBUG_PRINT ((ACPI_DB_NAMES, "[")); | 100 | ACPI_DEBUG_PRINT ((ACPI_DB_NAMES, "[")); |
98 | 101 | ||
99 | while (num_segments) { | 102 | while (num_segments) { |
100 | acpi_os_printf ("%4.4s", pathname); | 103 | for (i = 0; i < 4; i++) { |
101 | pathname += ACPI_NAME_SIZE; | 104 | ACPI_IS_PRINT (pathname[i]) ? |
105 | acpi_os_printf ("%c", pathname[i]) : | ||
106 | acpi_os_printf ("?"); | ||
107 | } | ||
102 | 108 | ||
109 | pathname += ACPI_NAME_SIZE; | ||
103 | num_segments--; | 110 | num_segments--; |
104 | if (num_segments) { | 111 | if (num_segments) { |
105 | acpi_os_printf ("."); | 112 | acpi_os_printf ("."); |
@@ -203,38 +210,42 @@ acpi_ns_dump_one_object ( | |||
203 | 210 | ||
204 | /* Check if the owner matches */ | 211 | /* Check if the owner matches */ |
205 | 212 | ||
206 | if ((info->owner_id != ACPI_UINT32_MAX) && | 213 | if ((info->owner_id != ACPI_OWNER_ID_MAX) && |
207 | (info->owner_id != this_node->owner_id)) { | 214 | (info->owner_id != this_node->owner_id)) { |
208 | return (AE_OK); | 215 | return (AE_OK); |
209 | } | 216 | } |
210 | 217 | ||
211 | /* Indent the object according to the level */ | 218 | if (!(info->display_type & ACPI_DISPLAY_SHORT)) { |
219 | /* Indent the object according to the level */ | ||
212 | 220 | ||
213 | acpi_os_printf ("%2d%*s", (u32) level - 1, (int) level * 2, " "); | 221 | acpi_os_printf ("%2d%*s", (u32) level - 1, (int) level * 2, " "); |
214 | 222 | ||
215 | /* Check the node type and name */ | 223 | /* Check the node type and name */ |
216 | 224 | ||
217 | if (type > ACPI_TYPE_LOCAL_MAX) { | 225 | if (type > ACPI_TYPE_LOCAL_MAX) { |
218 | ACPI_REPORT_WARNING (("Invalid ACPI Type %08X\n", type)); | 226 | ACPI_REPORT_WARNING (("Invalid ACPI Type %08X\n", type)); |
219 | } | 227 | } |
220 | 228 | ||
221 | if (!acpi_ut_valid_acpi_name (this_node->name.integer)) { | 229 | if (!acpi_ut_valid_acpi_name (this_node->name.integer)) { |
222 | ACPI_REPORT_WARNING (("Invalid ACPI Name %08X\n", | 230 | ACPI_REPORT_WARNING (("Invalid ACPI Name %08X\n", |
223 | this_node->name.integer)); | 231 | this_node->name.integer)); |
232 | } | ||
233 | |||
234 | acpi_os_printf ("%4.4s", acpi_ut_get_node_name (this_node)); | ||
224 | } | 235 | } |
225 | 236 | ||
226 | /* | 237 | /* |
227 | * Now we can print out the pertinent information | 238 | * Now we can print out the pertinent information |
228 | */ | 239 | */ |
229 | acpi_os_printf ("%4.4s %-12s %p ", | 240 | acpi_os_printf (" %-12s %p ", |
230 | acpi_ut_get_node_name (this_node), acpi_ut_get_type_name (type), this_node); | 241 | acpi_ut_get_type_name (type), this_node); |
231 | 242 | ||
232 | dbg_level = acpi_dbg_level; | 243 | dbg_level = acpi_dbg_level; |
233 | acpi_dbg_level = 0; | 244 | acpi_dbg_level = 0; |
234 | obj_desc = acpi_ns_get_attached_object (this_node); | 245 | obj_desc = acpi_ns_get_attached_object (this_node); |
235 | acpi_dbg_level = dbg_level; | 246 | acpi_dbg_level = dbg_level; |
236 | 247 | ||
237 | switch (info->display_type) { | 248 | switch (info->display_type & ACPI_DISPLAY_MASK) { |
238 | case ACPI_DISPLAY_SUMMARY: | 249 | case ACPI_DISPLAY_SUMMARY: |
239 | 250 | ||
240 | if (!obj_desc) { | 251 | if (!obj_desc) { |
@@ -475,7 +486,7 @@ acpi_ns_dump_one_object ( | |||
475 | 486 | ||
476 | while (obj_desc) { | 487 | while (obj_desc) { |
477 | obj_type = ACPI_TYPE_INVALID; | 488 | obj_type = ACPI_TYPE_INVALID; |
478 | acpi_os_printf (" Attached Object %p: ", obj_desc); | 489 | acpi_os_printf ("Attached Object %p: ", obj_desc); |
479 | 490 | ||
480 | /* Decode the type of attached object and dump the contents */ | 491 | /* Decode the type of attached object and dump the contents */ |
481 | 492 | ||
@@ -484,9 +495,9 @@ acpi_ns_dump_one_object ( | |||
484 | 495 | ||
485 | acpi_os_printf ("(Ptr to Node)\n"); | 496 | acpi_os_printf ("(Ptr to Node)\n"); |
486 | bytes_to_dump = sizeof (struct acpi_namespace_node); | 497 | bytes_to_dump = sizeof (struct acpi_namespace_node); |
498 | ACPI_DUMP_BUFFER (obj_desc, bytes_to_dump); | ||
487 | break; | 499 | break; |
488 | 500 | ||
489 | |||
490 | case ACPI_DESC_TYPE_OPERAND: | 501 | case ACPI_DESC_TYPE_OPERAND: |
491 | 502 | ||
492 | obj_type = ACPI_GET_OBJECT_TYPE (obj_desc); | 503 | obj_type = ACPI_GET_OBJECT_TYPE (obj_desc); |
@@ -497,24 +508,19 @@ acpi_ns_dump_one_object ( | |||
497 | bytes_to_dump = 32; | 508 | bytes_to_dump = 32; |
498 | } | 509 | } |
499 | else { | 510 | else { |
500 | acpi_os_printf ("(Ptr to ACPI Object type %s, %X)\n", | 511 | acpi_os_printf ("(Ptr to ACPI Object type %X [%s])\n", |
501 | acpi_ut_get_type_name (obj_type), obj_type); | 512 | obj_type, acpi_ut_get_type_name (obj_type)); |
502 | bytes_to_dump = sizeof (union acpi_operand_object); | 513 | bytes_to_dump = sizeof (union acpi_operand_object); |
503 | } | 514 | } |
504 | break; | ||
505 | 515 | ||
516 | ACPI_DUMP_BUFFER (obj_desc, bytes_to_dump); | ||
517 | break; | ||
506 | 518 | ||
507 | default: | 519 | default: |
508 | 520 | ||
509 | acpi_os_printf ( | ||
510 | "(String or Buffer ptr - not an object descriptor) [%s]\n", | ||
511 | acpi_ut_get_descriptor_name (obj_desc)); | ||
512 | bytes_to_dump = 16; | ||
513 | break; | 521 | break; |
514 | } | 522 | } |
515 | 523 | ||
516 | ACPI_DUMP_BUFFER (obj_desc, bytes_to_dump); | ||
517 | |||
518 | /* If value is NOT an internal object, we are done */ | 524 | /* If value is NOT an internal object, we are done */ |
519 | 525 | ||
520 | if (ACPI_GET_DESCRIPTOR_TYPE (obj_desc) != ACPI_DESC_TYPE_OPERAND) { | 526 | if (ACPI_GET_DESCRIPTOR_TYPE (obj_desc) != ACPI_DESC_TYPE_OPERAND) { |
@@ -525,13 +531,17 @@ acpi_ns_dump_one_object ( | |||
525 | * Valid object, get the pointer to next level, if any | 531 | * Valid object, get the pointer to next level, if any |
526 | */ | 532 | */ |
527 | switch (obj_type) { | 533 | switch (obj_type) { |
534 | case ACPI_TYPE_BUFFER: | ||
528 | case ACPI_TYPE_STRING: | 535 | case ACPI_TYPE_STRING: |
536 | /* | ||
537 | * NOTE: takes advantage of common fields between string/buffer | ||
538 | */ | ||
539 | bytes_to_dump = obj_desc->string.length; | ||
529 | obj_desc = (void *) obj_desc->string.pointer; | 540 | obj_desc = (void *) obj_desc->string.pointer; |
530 | break; | 541 | acpi_os_printf ( "(Buffer/String pointer %p length %X)\n", |
531 | 542 | obj_desc, bytes_to_dump); | |
532 | case ACPI_TYPE_BUFFER: | 543 | ACPI_DUMP_BUFFER (obj_desc, bytes_to_dump); |
533 | obj_desc = (void *) obj_desc->buffer.pointer; | 544 | goto cleanup; |
534 | break; | ||
535 | 545 | ||
536 | case ACPI_TYPE_BUFFER_FIELD: | 546 | case ACPI_TYPE_BUFFER_FIELD: |
537 | obj_desc = (union acpi_operand_object *) obj_desc->buffer_field.buffer_obj; | 547 | obj_desc = (union acpi_operand_object *) obj_desc->buffer_field.buffer_obj; |
@@ -595,7 +605,7 @@ acpi_ns_dump_objects ( | |||
595 | acpi_object_type type, | 605 | acpi_object_type type, |
596 | u8 display_type, | 606 | u8 display_type, |
597 | u32 max_depth, | 607 | u32 max_depth, |
598 | u32 owner_id, | 608 | acpi_owner_id owner_id, |
599 | acpi_handle start_handle) | 609 | acpi_handle start_handle) |
600 | { | 610 | { |
601 | struct acpi_walk_info info; | 611 | struct acpi_walk_info info; |
@@ -640,14 +650,14 @@ acpi_ns_dump_entry ( | |||
640 | 650 | ||
641 | 651 | ||
642 | info.debug_level = debug_level; | 652 | info.debug_level = debug_level; |
643 | info.owner_id = ACPI_UINT32_MAX; | 653 | info.owner_id = ACPI_OWNER_ID_MAX; |
644 | info.display_type = ACPI_DISPLAY_SUMMARY; | 654 | info.display_type = ACPI_DISPLAY_SUMMARY; |
645 | 655 | ||
646 | (void) acpi_ns_dump_one_object (handle, 1, &info, NULL); | 656 | (void) acpi_ns_dump_one_object (handle, 1, &info, NULL); |
647 | } | 657 | } |
648 | 658 | ||
649 | 659 | ||
650 | #ifdef _ACPI_ASL_COMPILER | 660 | #ifdef ACPI_ASL_COMPILER |
651 | /******************************************************************************* | 661 | /******************************************************************************* |
652 | * | 662 | * |
653 | * FUNCTION: acpi_ns_dump_tables | 663 | * FUNCTION: acpi_ns_dump_tables |
@@ -691,7 +701,7 @@ acpi_ns_dump_tables ( | |||
691 | } | 701 | } |
692 | 702 | ||
693 | acpi_ns_dump_objects (ACPI_TYPE_ANY, ACPI_DISPLAY_OBJECTS, max_depth, | 703 | acpi_ns_dump_objects (ACPI_TYPE_ANY, ACPI_DISPLAY_OBJECTS, max_depth, |
694 | ACPI_UINT32_MAX, search_handle); | 704 | ACPI_OWNER_ID_MAX, search_handle); |
695 | return_VOID; | 705 | return_VOID; |
696 | } | 706 | } |
697 | #endif /* _ACPI_ASL_COMPILER */ | 707 | #endif /* _ACPI_ASL_COMPILER */ |
diff --git a/drivers/acpi/namespace/nseval.c b/drivers/acpi/namespace/nseval.c index 1ae89a1c8826..908cffd5e720 100644 --- a/drivers/acpi/namespace/nseval.c +++ b/drivers/acpi/namespace/nseval.c | |||
@@ -365,6 +365,7 @@ acpi_ns_evaluate_by_handle ( | |||
365 | * | 365 | * |
366 | * PARAMETERS: Info - Method info block, contains: | 366 | * PARAMETERS: Info - Method info block, contains: |
367 | * Node - Method Node to execute | 367 | * Node - Method Node to execute |
368 | * obj_desc - Method object | ||
368 | * Parameters - List of parameters to pass to the method, | 369 | * Parameters - List of parameters to pass to the method, |
369 | * terminated by NULL. Params itself may be | 370 | * terminated by NULL. Params itself may be |
370 | * NULL if no parameters are being passed. | 371 | * NULL if no parameters are being passed. |
@@ -387,7 +388,6 @@ acpi_ns_execute_control_method ( | |||
387 | struct acpi_parameter_info *info) | 388 | struct acpi_parameter_info *info) |
388 | { | 389 | { |
389 | acpi_status status; | 390 | acpi_status status; |
390 | union acpi_operand_object *obj_desc; | ||
391 | 391 | ||
392 | 392 | ||
393 | ACPI_FUNCTION_TRACE ("ns_execute_control_method"); | 393 | ACPI_FUNCTION_TRACE ("ns_execute_control_method"); |
@@ -395,8 +395,8 @@ acpi_ns_execute_control_method ( | |||
395 | 395 | ||
396 | /* Verify that there is a method associated with this object */ | 396 | /* Verify that there is a method associated with this object */ |
397 | 397 | ||
398 | obj_desc = acpi_ns_get_attached_object (info->node); | 398 | info->obj_desc = acpi_ns_get_attached_object (info->node); |
399 | if (!obj_desc) { | 399 | if (!info->obj_desc) { |
400 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No attached method object\n")); | 400 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No attached method object\n")); |
401 | 401 | ||
402 | (void) acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); | 402 | (void) acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); |
@@ -407,7 +407,7 @@ acpi_ns_execute_control_method ( | |||
407 | ACPI_LV_INFO, _COMPONENT); | 407 | ACPI_LV_INFO, _COMPONENT); |
408 | 408 | ||
409 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Method at AML address %p Length %X\n", | 409 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Method at AML address %p Length %X\n", |
410 | obj_desc->method.aml_start + 1, obj_desc->method.aml_length - 1)); | 410 | info->obj_desc->method.aml_start + 1, info->obj_desc->method.aml_length - 1)); |
411 | 411 | ||
412 | /* | 412 | /* |
413 | * Unlock the namespace before execution. This allows namespace access | 413 | * Unlock the namespace before execution. This allows namespace access |
@@ -430,7 +430,7 @@ acpi_ns_execute_control_method ( | |||
430 | return_ACPI_STATUS (status); | 430 | return_ACPI_STATUS (status); |
431 | } | 431 | } |
432 | 432 | ||
433 | status = acpi_psx_execute (info); | 433 | status = acpi_ps_execute_method (info); |
434 | acpi_ex_exit_interpreter (); | 434 | acpi_ex_exit_interpreter (); |
435 | 435 | ||
436 | return_ACPI_STATUS (status); | 436 | return_ACPI_STATUS (status); |
diff --git a/drivers/acpi/namespace/nsload.c b/drivers/acpi/namespace/nsload.c index 34e497016601..1428a84a31e6 100644 --- a/drivers/acpi/namespace/nsload.c +++ b/drivers/acpi/namespace/nsload.c | |||
@@ -198,7 +198,7 @@ acpi_ns_load_table_by_type ( | |||
198 | switch (table_type) { | 198 | switch (table_type) { |
199 | case ACPI_TABLE_DSDT: | 199 | case ACPI_TABLE_DSDT: |
200 | 200 | ||
201 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Loading DSDT\n")); | 201 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Namespace load: DSDT\n")); |
202 | 202 | ||
203 | table_desc = acpi_gbl_table_lists[ACPI_TABLE_DSDT].next; | 203 | table_desc = acpi_gbl_table_lists[ACPI_TABLE_DSDT].next; |
204 | 204 | ||
@@ -218,17 +218,18 @@ acpi_ns_load_table_by_type ( | |||
218 | 218 | ||
219 | 219 | ||
220 | case ACPI_TABLE_SSDT: | 220 | case ACPI_TABLE_SSDT: |
221 | case ACPI_TABLE_PSDT: | ||
221 | 222 | ||
222 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Loading %d SSDTs\n", | 223 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Namespace load: %d SSDT or PSDTs\n", |
223 | acpi_gbl_table_lists[ACPI_TABLE_SSDT].count)); | 224 | acpi_gbl_table_lists[table_type].count)); |
224 | 225 | ||
225 | /* | 226 | /* |
226 | * Traverse list of SSDT tables | 227 | * Traverse list of SSDT or PSDT tables |
227 | */ | 228 | */ |
228 | table_desc = acpi_gbl_table_lists[ACPI_TABLE_SSDT].next; | 229 | table_desc = acpi_gbl_table_lists[table_type].next; |
229 | for (i = 0; i < acpi_gbl_table_lists[ACPI_TABLE_SSDT].count; i++) { | 230 | for (i = 0; i < acpi_gbl_table_lists[table_type].count; i++) { |
230 | /* | 231 | /* |
231 | * Only attempt to load table if it is not | 232 | * Only attempt to load table into namespace if it is not |
232 | * already loaded! | 233 | * already loaded! |
233 | */ | 234 | */ |
234 | if (!table_desc->loaded_into_namespace) { | 235 | if (!table_desc->loaded_into_namespace) { |
@@ -245,33 +246,6 @@ acpi_ns_load_table_by_type ( | |||
245 | break; | 246 | break; |
246 | 247 | ||
247 | 248 | ||
248 | case ACPI_TABLE_PSDT: | ||
249 | |||
250 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Loading %d PSDTs\n", | ||
251 | acpi_gbl_table_lists[ACPI_TABLE_PSDT].count)); | ||
252 | |||
253 | /* | ||
254 | * Traverse list of PSDT tables | ||
255 | */ | ||
256 | table_desc = acpi_gbl_table_lists[ACPI_TABLE_PSDT].next; | ||
257 | |||
258 | for (i = 0; i < acpi_gbl_table_lists[ACPI_TABLE_PSDT].count; i++) { | ||
259 | /* Only attempt to load table if it is not already loaded! */ | ||
260 | |||
261 | if (!table_desc->loaded_into_namespace) { | ||
262 | status = acpi_ns_load_table (table_desc, acpi_gbl_root_node); | ||
263 | if (ACPI_FAILURE (status)) { | ||
264 | break; | ||
265 | } | ||
266 | |||
267 | table_desc->loaded_into_namespace = TRUE; | ||
268 | } | ||
269 | |||
270 | table_desc = table_desc->next; | ||
271 | } | ||
272 | break; | ||
273 | |||
274 | |||
275 | default: | 249 | default: |
276 | status = AE_SUPPORT; | 250 | status = AE_SUPPORT; |
277 | break; | 251 | break; |
diff --git a/drivers/acpi/namespace/nsparse.c b/drivers/acpi/namespace/nsparse.c index a0e13e8d3764..24bed931d39d 100644 --- a/drivers/acpi/namespace/nsparse.c +++ b/drivers/acpi/namespace/nsparse.c | |||
@@ -67,7 +67,7 @@ | |||
67 | 67 | ||
68 | acpi_status | 68 | acpi_status |
69 | acpi_ns_one_complete_parse ( | 69 | acpi_ns_one_complete_parse ( |
70 | u32 pass_number, | 70 | u8 pass_number, |
71 | struct acpi_table_desc *table_desc) | 71 | struct acpi_table_desc *table_desc) |
72 | { | 72 | { |
73 | union acpi_parse_object *parse_root; | 73 | union acpi_parse_object *parse_root; |
@@ -87,7 +87,7 @@ acpi_ns_one_complete_parse ( | |||
87 | 87 | ||
88 | /* Create and initialize a new walk state */ | 88 | /* Create and initialize a new walk state */ |
89 | 89 | ||
90 | walk_state = acpi_ds_create_walk_state (table_desc->table_id, | 90 | walk_state = acpi_ds_create_walk_state (table_desc->owner_id, |
91 | NULL, NULL, NULL); | 91 | NULL, NULL, NULL); |
92 | if (!walk_state) { | 92 | if (!walk_state) { |
93 | acpi_ps_free_op (parse_root); | 93 | acpi_ps_free_op (parse_root); |
@@ -146,6 +146,7 @@ acpi_ns_parse_table ( | |||
146 | * to service the entire parse. The second pass of the parse then | 146 | * to service the entire parse. The second pass of the parse then |
147 | * performs another complete parse of the AML.. | 147 | * performs another complete parse of the AML.. |
148 | */ | 148 | */ |
149 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "**** Start pass 1\n")); | ||
149 | status = acpi_ns_one_complete_parse (1, table_desc); | 150 | status = acpi_ns_one_complete_parse (1, table_desc); |
150 | if (ACPI_FAILURE (status)) { | 151 | if (ACPI_FAILURE (status)) { |
151 | return_ACPI_STATUS (status); | 152 | return_ACPI_STATUS (status); |
@@ -160,6 +161,7 @@ acpi_ns_parse_table ( | |||
160 | * overhead of this is compensated for by the fact that the | 161 | * overhead of this is compensated for by the fact that the |
161 | * parse objects are all cached. | 162 | * parse objects are all cached. |
162 | */ | 163 | */ |
164 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "**** Start pass 2\n")); | ||
163 | status = acpi_ns_one_complete_parse (2, table_desc); | 165 | status = acpi_ns_one_complete_parse (2, table_desc); |
164 | if (ACPI_FAILURE (status)) { | 166 | if (ACPI_FAILURE (status)) { |
165 | return_ACPI_STATUS (status); | 167 | return_ACPI_STATUS (status); |
diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index 7289da3c4db6..f3a807c342c0 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c | |||
@@ -782,54 +782,6 @@ acpi_os_delete_lock ( | |||
782 | return_VOID; | 782 | return_VOID; |
783 | } | 783 | } |
784 | 784 | ||
785 | /* | ||
786 | * Acquire a spinlock. | ||
787 | * | ||
788 | * handle is a pointer to the spinlock_t. | ||
789 | * flags is *not* the result of save_flags - it is an ACPI-specific flag variable | ||
790 | * that indicates whether we are at interrupt level. | ||
791 | */ | ||
792 | void | ||
793 | acpi_os_acquire_lock ( | ||
794 | acpi_handle handle, | ||
795 | u32 flags) | ||
796 | { | ||
797 | ACPI_FUNCTION_TRACE ("os_acquire_lock"); | ||
798 | |||
799 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Acquiring spinlock[%p] from %s level\n", handle, | ||
800 | ((flags & ACPI_NOT_ISR) ? "non-interrupt" : "interrupt"))); | ||
801 | |||
802 | if (flags & ACPI_NOT_ISR) | ||
803 | ACPI_DISABLE_IRQS(); | ||
804 | |||
805 | spin_lock((spinlock_t *)handle); | ||
806 | |||
807 | return_VOID; | ||
808 | } | ||
809 | |||
810 | |||
811 | /* | ||
812 | * Release a spinlock. See above. | ||
813 | */ | ||
814 | void | ||
815 | acpi_os_release_lock ( | ||
816 | acpi_handle handle, | ||
817 | u32 flags) | ||
818 | { | ||
819 | ACPI_FUNCTION_TRACE ("os_release_lock"); | ||
820 | |||
821 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Releasing spinlock[%p] from %s level\n", handle, | ||
822 | ((flags & ACPI_NOT_ISR) ? "non-interrupt" : "interrupt"))); | ||
823 | |||
824 | spin_unlock((spinlock_t *)handle); | ||
825 | |||
826 | if (flags & ACPI_NOT_ISR) | ||
827 | ACPI_ENABLE_IRQS(); | ||
828 | |||
829 | return_VOID; | ||
830 | } | ||
831 | |||
832 | |||
833 | acpi_status | 785 | acpi_status |
834 | acpi_os_create_semaphore( | 786 | acpi_os_create_semaphore( |
835 | u32 max_units, | 787 | u32 max_units, |
@@ -1176,3 +1128,151 @@ unsigned int max_cstate = ACPI_PROCESSOR_MAX_POWER; | |||
1176 | 1128 | ||
1177 | 1129 | ||
1178 | EXPORT_SYMBOL(max_cstate); | 1130 | EXPORT_SYMBOL(max_cstate); |
1131 | |||
1132 | /* | ||
1133 | * Acquire a spinlock. | ||
1134 | * | ||
1135 | * handle is a pointer to the spinlock_t. | ||
1136 | * flags is *not* the result of save_flags - it is an ACPI-specific flag variable | ||
1137 | * that indicates whether we are at interrupt level. | ||
1138 | */ | ||
1139 | |||
1140 | unsigned long | ||
1141 | acpi_os_acquire_lock ( | ||
1142 | acpi_handle handle) | ||
1143 | { | ||
1144 | unsigned long flags; | ||
1145 | spin_lock_irqsave((spinlock_t *)handle, flags); | ||
1146 | return flags; | ||
1147 | } | ||
1148 | |||
1149 | /* | ||
1150 | * Release a spinlock. See above. | ||
1151 | */ | ||
1152 | |||
1153 | void | ||
1154 | acpi_os_release_lock ( | ||
1155 | acpi_handle handle, | ||
1156 | unsigned long flags) | ||
1157 | { | ||
1158 | spin_unlock_irqrestore((spinlock_t *)handle, flags); | ||
1159 | } | ||
1160 | |||
1161 | |||
1162 | #ifndef ACPI_USE_LOCAL_CACHE | ||
1163 | |||
1164 | /******************************************************************************* | ||
1165 | * | ||
1166 | * FUNCTION: acpi_os_create_cache | ||
1167 | * | ||
1168 | * PARAMETERS: CacheName - Ascii name for the cache | ||
1169 | * ObjectSize - Size of each cached object | ||
1170 | * MaxDepth - Maximum depth of the cache (in objects) | ||
1171 | * ReturnCache - Where the new cache object is returned | ||
1172 | * | ||
1173 | * RETURN: Status | ||
1174 | * | ||
1175 | * DESCRIPTION: Create a cache object | ||
1176 | * | ||
1177 | ******************************************************************************/ | ||
1178 | |||
1179 | acpi_status | ||
1180 | acpi_os_create_cache ( | ||
1181 | char *name, | ||
1182 | u16 size, | ||
1183 | u16 depth, | ||
1184 | acpi_cache_t **cache) | ||
1185 | { | ||
1186 | *cache = kmem_cache_create (name, size, 0, 0, NULL, NULL); | ||
1187 | return AE_OK; | ||
1188 | } | ||
1189 | |||
1190 | /******************************************************************************* | ||
1191 | * | ||
1192 | * FUNCTION: acpi_os_purge_cache | ||
1193 | * | ||
1194 | * PARAMETERS: Cache - Handle to cache object | ||
1195 | * | ||
1196 | * RETURN: Status | ||
1197 | * | ||
1198 | * DESCRIPTION: Free all objects within the requested cache. | ||
1199 | * | ||
1200 | ******************************************************************************/ | ||
1201 | |||
1202 | acpi_status | ||
1203 | acpi_os_purge_cache ( | ||
1204 | acpi_cache_t *cache) | ||
1205 | { | ||
1206 | (void) kmem_cache_shrink(cache); | ||
1207 | return (AE_OK); | ||
1208 | } | ||
1209 | |||
1210 | /******************************************************************************* | ||
1211 | * | ||
1212 | * FUNCTION: acpi_os_delete_cache | ||
1213 | * | ||
1214 | * PARAMETERS: Cache - Handle to cache object | ||
1215 | * | ||
1216 | * RETURN: Status | ||
1217 | * | ||
1218 | * DESCRIPTION: Free all objects within the requested cache and delete the | ||
1219 | * cache object. | ||
1220 | * | ||
1221 | ******************************************************************************/ | ||
1222 | |||
1223 | acpi_status | ||
1224 | acpi_os_delete_cache ( | ||
1225 | acpi_cache_t *cache) | ||
1226 | { | ||
1227 | (void)kmem_cache_destroy(cache); | ||
1228 | return (AE_OK); | ||
1229 | } | ||
1230 | |||
1231 | /******************************************************************************* | ||
1232 | * | ||
1233 | * FUNCTION: acpi_os_release_object | ||
1234 | * | ||
1235 | * PARAMETERS: Cache - Handle to cache object | ||
1236 | * Object - The object to be released | ||
1237 | * | ||
1238 | * RETURN: None | ||
1239 | * | ||
1240 | * DESCRIPTION: Release an object to the specified cache. If cache is full, | ||
1241 | * the object is deleted. | ||
1242 | * | ||
1243 | ******************************************************************************/ | ||
1244 | |||
1245 | acpi_status | ||
1246 | acpi_os_release_object ( | ||
1247 | acpi_cache_t *cache, | ||
1248 | void *object) | ||
1249 | { | ||
1250 | kmem_cache_free(cache, object); | ||
1251 | return (AE_OK); | ||
1252 | } | ||
1253 | |||
1254 | /******************************************************************************* | ||
1255 | * | ||
1256 | * FUNCTION: acpi_os_acquire_object | ||
1257 | * | ||
1258 | * PARAMETERS: Cache - Handle to cache object | ||
1259 | * ReturnObject - Where the object is returned | ||
1260 | * | ||
1261 | * RETURN: Status | ||
1262 | * | ||
1263 | * DESCRIPTION: Get an object from the specified cache. If cache is empty, | ||
1264 | * the object is allocated. | ||
1265 | * | ||
1266 | ******************************************************************************/ | ||
1267 | |||
1268 | void * | ||
1269 | acpi_os_acquire_object ( | ||
1270 | acpi_cache_t *cache) | ||
1271 | { | ||
1272 | void *object = kmem_cache_alloc(cache, GFP_KERNEL); | ||
1273 | WARN_ON(!object); | ||
1274 | return object; | ||
1275 | } | ||
1276 | |||
1277 | #endif | ||
1278 | |||
diff --git a/drivers/acpi/parser/Makefile b/drivers/acpi/parser/Makefile index bbdd286c660d..db24ee09cf11 100644 --- a/drivers/acpi/parser/Makefile +++ b/drivers/acpi/parser/Makefile | |||
@@ -2,7 +2,7 @@ | |||
2 | # Makefile for all Linux ACPI interpreter subdirectories | 2 | # Makefile for all Linux ACPI interpreter subdirectories |
3 | # | 3 | # |
4 | 4 | ||
5 | obj-y := psargs.o psparse.o pstree.o pswalk.o \ | 5 | obj-y := psargs.o psparse.o psloop.o pstree.o pswalk.o \ |
6 | psopcode.o psscope.o psutils.o psxface.o | 6 | psopcode.o psscope.o psutils.o psxface.o |
7 | 7 | ||
8 | EXTRA_CFLAGS += $(ACPI_CFLAGS) | 8 | EXTRA_CFLAGS += $(ACPI_CFLAGS) |
diff --git a/drivers/acpi/parser/psloop.c b/drivers/acpi/parser/psloop.c new file mode 100644 index 000000000000..551d54bdbec3 --- /dev/null +++ b/drivers/acpi/parser/psloop.c | |||
@@ -0,0 +1,781 @@ | |||
1 | /****************************************************************************** | ||
2 | * | ||
3 | * Module Name: psloop - Main AML parse loop | ||
4 | * | ||
5 | *****************************************************************************/ | ||
6 | |||
7 | /* | ||
8 | * Copyright (C) 2000 - 2005, R. Byron Moore | ||
9 | * All rights reserved. | ||
10 | * | ||
11 | * Redistribution and use in source and binary forms, with or without | ||
12 | * modification, are permitted provided that the following conditions | ||
13 | * are met: | ||
14 | * 1. Redistributions of source code must retain the above copyright | ||
15 | * notice, this list of conditions, and the following disclaimer, | ||
16 | * without modification. | ||
17 | * 2. Redistributions in binary form must reproduce at minimum a disclaimer | ||
18 | * substantially similar to the "NO WARRANTY" disclaimer below | ||
19 | * ("Disclaimer") and any redistribution must be conditioned upon | ||
20 | * including a substantially similar Disclaimer requirement for further | ||
21 | * binary redistribution. | ||
22 | * 3. Neither the names of the above-listed copyright holders nor the names | ||
23 | * of any contributors may be used to endorse or promote products derived | ||
24 | * from this software without specific prior written permission. | ||
25 | * | ||
26 | * Alternatively, this software may be distributed under the terms of the | ||
27 | * GNU General Public License ("GPL") version 2 as published by the Free | ||
28 | * Software Foundation. | ||
29 | * | ||
30 | * NO WARRANTY | ||
31 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
32 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
33 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR | ||
34 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
35 | * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
36 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
37 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
38 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
39 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING | ||
40 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | ||
41 | * POSSIBILITY OF SUCH DAMAGES. | ||
42 | */ | ||
43 | |||
44 | |||
45 | /* | ||
46 | * Parse the AML and build an operation tree as most interpreters, | ||
47 | * like Perl, do. Parsing is done by hand rather than with a YACC | ||
48 | * generated parser to tightly constrain stack and dynamic memory | ||
49 | * usage. At the same time, parsing is kept flexible and the code | ||
50 | * fairly compact by parsing based on a list of AML opcode | ||
51 | * templates in aml_op_info[] | ||
52 | */ | ||
53 | |||
54 | #include <acpi/acpi.h> | ||
55 | #include <acpi/acparser.h> | ||
56 | #include <acpi/acdispat.h> | ||
57 | #include <acpi/amlcode.h> | ||
58 | |||
59 | #define _COMPONENT ACPI_PARSER | ||
60 | ACPI_MODULE_NAME ("psloop") | ||
61 | |||
62 | static u32 acpi_gbl_depth = 0; | ||
63 | |||
64 | |||
65 | /******************************************************************************* | ||
66 | * | ||
67 | * FUNCTION: acpi_ps_parse_loop | ||
68 | * | ||
69 | * PARAMETERS: walk_state - Current state | ||
70 | * | ||
71 | * RETURN: Status | ||
72 | * | ||
73 | * DESCRIPTION: Parse AML (pointed to by the current parser state) and return | ||
74 | * a tree of ops. | ||
75 | * | ||
76 | ******************************************************************************/ | ||
77 | |||
78 | acpi_status | ||
79 | acpi_ps_parse_loop ( | ||
80 | struct acpi_walk_state *walk_state) | ||
81 | { | ||
82 | acpi_status status = AE_OK; | ||
83 | acpi_status status2; | ||
84 | union acpi_parse_object *op = NULL; /* current op */ | ||
85 | union acpi_parse_object *arg = NULL; | ||
86 | union acpi_parse_object *pre_op = NULL; | ||
87 | struct acpi_parse_state *parser_state; | ||
88 | u8 *aml_op_start = NULL; | ||
89 | |||
90 | |||
91 | ACPI_FUNCTION_TRACE_PTR ("ps_parse_loop", walk_state); | ||
92 | |||
93 | if (walk_state->descending_callback == NULL) { | ||
94 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
95 | } | ||
96 | |||
97 | parser_state = &walk_state->parser_state; | ||
98 | walk_state->arg_types = 0; | ||
99 | |||
100 | #if (!defined (ACPI_NO_METHOD_EXECUTION) && !defined (ACPI_CONSTANT_EVAL_ONLY)) | ||
101 | |||
102 | if (walk_state->walk_type & ACPI_WALK_METHOD_RESTART) { | ||
103 | /* We are restarting a preempted control method */ | ||
104 | |||
105 | if (acpi_ps_has_completed_scope (parser_state)) { | ||
106 | /* | ||
107 | * We must check if a predicate to an IF or WHILE statement | ||
108 | * was just completed | ||
109 | */ | ||
110 | if ((parser_state->scope->parse_scope.op) && | ||
111 | ((parser_state->scope->parse_scope.op->common.aml_opcode == AML_IF_OP) || | ||
112 | (parser_state->scope->parse_scope.op->common.aml_opcode == AML_WHILE_OP)) && | ||
113 | (walk_state->control_state) && | ||
114 | (walk_state->control_state->common.state == | ||
115 | ACPI_CONTROL_PREDICATE_EXECUTING)) { | ||
116 | /* | ||
117 | * A predicate was just completed, get the value of the | ||
118 | * predicate and branch based on that value | ||
119 | */ | ||
120 | walk_state->op = NULL; | ||
121 | status = acpi_ds_get_predicate_value (walk_state, ACPI_TO_POINTER (TRUE)); | ||
122 | if (ACPI_FAILURE (status) && | ||
123 | ((status & AE_CODE_MASK) != AE_CODE_CONTROL)) { | ||
124 | if (status == AE_AML_NO_RETURN_VALUE) { | ||
125 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
126 | "Invoked method did not return a value, %s\n", | ||
127 | acpi_format_exception (status))); | ||
128 | |||
129 | } | ||
130 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
131 | "get_predicate Failed, %s\n", | ||
132 | acpi_format_exception (status))); | ||
133 | return_ACPI_STATUS (status); | ||
134 | } | ||
135 | |||
136 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
137 | } | ||
138 | |||
139 | acpi_ps_pop_scope (parser_state, &op, | ||
140 | &walk_state->arg_types, &walk_state->arg_count); | ||
141 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Popped scope, Op=%p\n", op)); | ||
142 | } | ||
143 | else if (walk_state->prev_op) { | ||
144 | /* We were in the middle of an op */ | ||
145 | |||
146 | op = walk_state->prev_op; | ||
147 | walk_state->arg_types = walk_state->prev_arg_types; | ||
148 | } | ||
149 | } | ||
150 | #endif | ||
151 | |||
152 | /* Iterative parsing loop, while there is more AML to process: */ | ||
153 | |||
154 | while ((parser_state->aml < parser_state->aml_end) || (op)) { | ||
155 | aml_op_start = parser_state->aml; | ||
156 | if (!op) { | ||
157 | /* Get the next opcode from the AML stream */ | ||
158 | |||
159 | walk_state->aml_offset = (u32) ACPI_PTR_DIFF (parser_state->aml, | ||
160 | parser_state->aml_start); | ||
161 | walk_state->opcode = acpi_ps_peek_opcode (parser_state); | ||
162 | |||
163 | /* | ||
164 | * First cut to determine what we have found: | ||
165 | * 1) A valid AML opcode | ||
166 | * 2) A name string | ||
167 | * 3) An unknown/invalid opcode | ||
168 | */ | ||
169 | walk_state->op_info = acpi_ps_get_opcode_info (walk_state->opcode); | ||
170 | switch (walk_state->op_info->class) { | ||
171 | case AML_CLASS_ASCII: | ||
172 | case AML_CLASS_PREFIX: | ||
173 | /* | ||
174 | * Starts with a valid prefix or ASCII char, this is a name | ||
175 | * string. Convert the bare name string to a namepath. | ||
176 | */ | ||
177 | walk_state->opcode = AML_INT_NAMEPATH_OP; | ||
178 | walk_state->arg_types = ARGP_NAMESTRING; | ||
179 | break; | ||
180 | |||
181 | case AML_CLASS_UNKNOWN: | ||
182 | |||
183 | /* The opcode is unrecognized. Just skip unknown opcodes */ | ||
184 | |||
185 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
186 | "Found unknown opcode %X at AML address %p offset %X, ignoring\n", | ||
187 | walk_state->opcode, parser_state->aml, walk_state->aml_offset)); | ||
188 | |||
189 | ACPI_DUMP_BUFFER (parser_state->aml, 128); | ||
190 | |||
191 | /* Assume one-byte bad opcode */ | ||
192 | |||
193 | parser_state->aml++; | ||
194 | continue; | ||
195 | |||
196 | default: | ||
197 | |||
198 | /* Found opcode info, this is a normal opcode */ | ||
199 | |||
200 | parser_state->aml += acpi_ps_get_opcode_size (walk_state->opcode); | ||
201 | walk_state->arg_types = walk_state->op_info->parse_args; | ||
202 | break; | ||
203 | } | ||
204 | |||
205 | /* Create Op structure and append to parent's argument list */ | ||
206 | |||
207 | if (walk_state->op_info->flags & AML_NAMED) { | ||
208 | /* Allocate a new pre_op if necessary */ | ||
209 | |||
210 | if (!pre_op) { | ||
211 | pre_op = acpi_ps_alloc_op (walk_state->opcode); | ||
212 | if (!pre_op) { | ||
213 | status = AE_NO_MEMORY; | ||
214 | goto close_this_op; | ||
215 | } | ||
216 | } | ||
217 | |||
218 | pre_op->common.value.arg = NULL; | ||
219 | pre_op->common.aml_opcode = walk_state->opcode; | ||
220 | |||
221 | /* | ||
222 | * Get and append arguments until we find the node that contains | ||
223 | * the name (the type ARGP_NAME). | ||
224 | */ | ||
225 | while (GET_CURRENT_ARG_TYPE (walk_state->arg_types) && | ||
226 | (GET_CURRENT_ARG_TYPE (walk_state->arg_types) != ARGP_NAME)) { | ||
227 | status = acpi_ps_get_next_arg (walk_state, parser_state, | ||
228 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), &arg); | ||
229 | if (ACPI_FAILURE (status)) { | ||
230 | goto close_this_op; | ||
231 | } | ||
232 | |||
233 | acpi_ps_append_arg (pre_op, arg); | ||
234 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
235 | } | ||
236 | |||
237 | /* | ||
238 | * Make sure that we found a NAME and didn't run out of | ||
239 | * arguments | ||
240 | */ | ||
241 | if (!GET_CURRENT_ARG_TYPE (walk_state->arg_types)) { | ||
242 | status = AE_AML_NO_OPERAND; | ||
243 | goto close_this_op; | ||
244 | } | ||
245 | |||
246 | /* We know that this arg is a name, move to next arg */ | ||
247 | |||
248 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
249 | |||
250 | /* | ||
251 | * Find the object. This will either insert the object into | ||
252 | * the namespace or simply look it up | ||
253 | */ | ||
254 | walk_state->op = NULL; | ||
255 | |||
256 | status = walk_state->descending_callback (walk_state, &op); | ||
257 | if (ACPI_FAILURE (status)) { | ||
258 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
259 | "During name lookup/catalog, %s\n", | ||
260 | acpi_format_exception (status))); | ||
261 | goto close_this_op; | ||
262 | } | ||
263 | |||
264 | if (!op) { | ||
265 | continue; | ||
266 | } | ||
267 | |||
268 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
269 | if (status == AE_CTRL_PENDING) { | ||
270 | status = AE_OK; | ||
271 | goto close_this_op; | ||
272 | } | ||
273 | |||
274 | if (ACPI_FAILURE (status)) { | ||
275 | goto close_this_op; | ||
276 | } | ||
277 | |||
278 | acpi_ps_append_arg (op, pre_op->common.value.arg); | ||
279 | acpi_gbl_depth++; | ||
280 | |||
281 | if (op->common.aml_opcode == AML_REGION_OP) { | ||
282 | /* | ||
283 | * Defer final parsing of an operation_region body, | ||
284 | * because we don't have enough info in the first pass | ||
285 | * to parse it correctly (i.e., there may be method | ||
286 | * calls within the term_arg elements of the body.) | ||
287 | * | ||
288 | * However, we must continue parsing because | ||
289 | * the opregion is not a standalone package -- | ||
290 | * we don't know where the end is at this point. | ||
291 | * | ||
292 | * (Length is unknown until parse of the body complete) | ||
293 | */ | ||
294 | op->named.data = aml_op_start; | ||
295 | op->named.length = 0; | ||
296 | } | ||
297 | } | ||
298 | else { | ||
299 | /* Not a named opcode, just allocate Op and append to parent */ | ||
300 | |||
301 | walk_state->op_info = acpi_ps_get_opcode_info (walk_state->opcode); | ||
302 | op = acpi_ps_alloc_op (walk_state->opcode); | ||
303 | if (!op) { | ||
304 | status = AE_NO_MEMORY; | ||
305 | goto close_this_op; | ||
306 | } | ||
307 | |||
308 | if (walk_state->op_info->flags & AML_CREATE) { | ||
309 | /* | ||
310 | * Backup to beginning of create_xXXfield declaration | ||
311 | * body_length is unknown until we parse the body | ||
312 | */ | ||
313 | op->named.data = aml_op_start; | ||
314 | op->named.length = 0; | ||
315 | } | ||
316 | |||
317 | acpi_ps_append_arg (acpi_ps_get_parent_scope (parser_state), op); | ||
318 | |||
319 | if ((walk_state->descending_callback != NULL)) { | ||
320 | /* | ||
321 | * Find the object. This will either insert the object into | ||
322 | * the namespace or simply look it up | ||
323 | */ | ||
324 | walk_state->op = op; | ||
325 | |||
326 | status = walk_state->descending_callback (walk_state, &op); | ||
327 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
328 | if (status == AE_CTRL_PENDING) { | ||
329 | status = AE_OK; | ||
330 | goto close_this_op; | ||
331 | } | ||
332 | |||
333 | if (ACPI_FAILURE (status)) { | ||
334 | goto close_this_op; | ||
335 | } | ||
336 | } | ||
337 | } | ||
338 | |||
339 | op->common.aml_offset = walk_state->aml_offset; | ||
340 | |||
341 | if (walk_state->op_info) { | ||
342 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | ||
343 | "Opcode %4.4X [%s] Op %p Aml %p aml_offset %5.5X\n", | ||
344 | (u32) op->common.aml_opcode, walk_state->op_info->name, | ||
345 | op, parser_state->aml, op->common.aml_offset)); | ||
346 | } | ||
347 | } | ||
348 | |||
349 | |||
350 | /* | ||
351 | * Start arg_count at zero because we don't know if there are | ||
352 | * any args yet | ||
353 | */ | ||
354 | walk_state->arg_count = 0; | ||
355 | |||
356 | /* Are there any arguments that must be processed? */ | ||
357 | |||
358 | if (walk_state->arg_types) { | ||
359 | /* Get arguments */ | ||
360 | |||
361 | switch (op->common.aml_opcode) { | ||
362 | case AML_BYTE_OP: /* AML_BYTEDATA_ARG */ | ||
363 | case AML_WORD_OP: /* AML_WORDDATA_ARG */ | ||
364 | case AML_DWORD_OP: /* AML_DWORDATA_ARG */ | ||
365 | case AML_QWORD_OP: /* AML_QWORDATA_ARG */ | ||
366 | case AML_STRING_OP: /* AML_ASCIICHARLIST_ARG */ | ||
367 | |||
368 | /* Fill in constant or string argument directly */ | ||
369 | |||
370 | acpi_ps_get_next_simple_arg (parser_state, | ||
371 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), op); | ||
372 | break; | ||
373 | |||
374 | case AML_INT_NAMEPATH_OP: /* AML_NAMESTRING_ARG */ | ||
375 | |||
376 | status = acpi_ps_get_next_namepath (walk_state, parser_state, op, 1); | ||
377 | if (ACPI_FAILURE (status)) { | ||
378 | goto close_this_op; | ||
379 | } | ||
380 | |||
381 | walk_state->arg_types = 0; | ||
382 | break; | ||
383 | |||
384 | default: | ||
385 | /* | ||
386 | * Op is not a constant or string, append each argument | ||
387 | * to the Op | ||
388 | */ | ||
389 | while (GET_CURRENT_ARG_TYPE (walk_state->arg_types) && | ||
390 | !walk_state->arg_count) { | ||
391 | walk_state->aml_offset = (u32) | ||
392 | ACPI_PTR_DIFF (parser_state->aml, parser_state->aml_start); | ||
393 | |||
394 | status = acpi_ps_get_next_arg (walk_state, parser_state, | ||
395 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), | ||
396 | &arg); | ||
397 | if (ACPI_FAILURE (status)) { | ||
398 | goto close_this_op; | ||
399 | } | ||
400 | |||
401 | if (arg) { | ||
402 | arg->common.aml_offset = walk_state->aml_offset; | ||
403 | acpi_ps_append_arg (op, arg); | ||
404 | } | ||
405 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
406 | } | ||
407 | |||
408 | |||
409 | /* Special processing for certain opcodes */ | ||
410 | |||
411 | /* TBD (remove): Temporary mechanism to disable this code if needed */ | ||
412 | |||
413 | #ifdef ACPI_ENABLE_MODULE_LEVEL_CODE | ||
414 | |||
415 | if ((walk_state->pass_number <= ACPI_IMODE_LOAD_PASS1) && | ||
416 | ((walk_state->parse_flags & ACPI_PARSE_DISASSEMBLE) == 0)) { | ||
417 | /* | ||
418 | * We want to skip If/Else/While constructs during Pass1 | ||
419 | * because we want to actually conditionally execute the | ||
420 | * code during Pass2. | ||
421 | * | ||
422 | * Except for disassembly, where we always want to | ||
423 | * walk the If/Else/While packages | ||
424 | */ | ||
425 | switch (op->common.aml_opcode) { | ||
426 | case AML_IF_OP: | ||
427 | case AML_ELSE_OP: | ||
428 | case AML_WHILE_OP: | ||
429 | |||
430 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | ||
431 | "Pass1: Skipping an If/Else/While body\n")); | ||
432 | |||
433 | /* Skip body of if/else/while in pass 1 */ | ||
434 | |||
435 | parser_state->aml = parser_state->pkg_end; | ||
436 | walk_state->arg_count = 0; | ||
437 | break; | ||
438 | |||
439 | default: | ||
440 | break; | ||
441 | } | ||
442 | } | ||
443 | #endif | ||
444 | switch (op->common.aml_opcode) { | ||
445 | case AML_METHOD_OP: | ||
446 | |||
447 | /* | ||
448 | * Skip parsing of control method | ||
449 | * because we don't have enough info in the first pass | ||
450 | * to parse it correctly. | ||
451 | * | ||
452 | * Save the length and address of the body | ||
453 | */ | ||
454 | op->named.data = parser_state->aml; | ||
455 | op->named.length = (u32) (parser_state->pkg_end - | ||
456 | parser_state->aml); | ||
457 | |||
458 | /* Skip body of method */ | ||
459 | |||
460 | parser_state->aml = parser_state->pkg_end; | ||
461 | walk_state->arg_count = 0; | ||
462 | break; | ||
463 | |||
464 | case AML_BUFFER_OP: | ||
465 | case AML_PACKAGE_OP: | ||
466 | case AML_VAR_PACKAGE_OP: | ||
467 | |||
468 | if ((op->common.parent) && | ||
469 | (op->common.parent->common.aml_opcode == AML_NAME_OP) && | ||
470 | (walk_state->pass_number <= ACPI_IMODE_LOAD_PASS2)) { | ||
471 | /* | ||
472 | * Skip parsing of Buffers and Packages | ||
473 | * because we don't have enough info in the first pass | ||
474 | * to parse them correctly. | ||
475 | */ | ||
476 | op->named.data = aml_op_start; | ||
477 | op->named.length = (u32) (parser_state->pkg_end - | ||
478 | aml_op_start); | ||
479 | |||
480 | /* Skip body */ | ||
481 | |||
482 | parser_state->aml = parser_state->pkg_end; | ||
483 | walk_state->arg_count = 0; | ||
484 | } | ||
485 | break; | ||
486 | |||
487 | case AML_WHILE_OP: | ||
488 | |||
489 | if (walk_state->control_state) { | ||
490 | walk_state->control_state->control.package_end = | ||
491 | parser_state->pkg_end; | ||
492 | } | ||
493 | break; | ||
494 | |||
495 | default: | ||
496 | |||
497 | /* No action for all other opcodes */ | ||
498 | break; | ||
499 | } | ||
500 | break; | ||
501 | } | ||
502 | } | ||
503 | |||
504 | /* Check for arguments that need to be processed */ | ||
505 | |||
506 | if (walk_state->arg_count) { | ||
507 | /* | ||
508 | * There are arguments (complex ones), push Op and | ||
509 | * prepare for argument | ||
510 | */ | ||
511 | status = acpi_ps_push_scope (parser_state, op, | ||
512 | walk_state->arg_types, walk_state->arg_count); | ||
513 | if (ACPI_FAILURE (status)) { | ||
514 | goto close_this_op; | ||
515 | } | ||
516 | op = NULL; | ||
517 | continue; | ||
518 | } | ||
519 | |||
520 | /* | ||
521 | * All arguments have been processed -- Op is complete, | ||
522 | * prepare for next | ||
523 | */ | ||
524 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
525 | if (walk_state->op_info->flags & AML_NAMED) { | ||
526 | if (acpi_gbl_depth) { | ||
527 | acpi_gbl_depth--; | ||
528 | } | ||
529 | |||
530 | if (op->common.aml_opcode == AML_REGION_OP) { | ||
531 | /* | ||
532 | * Skip parsing of control method or opregion body, | ||
533 | * because we don't have enough info in the first pass | ||
534 | * to parse them correctly. | ||
535 | * | ||
536 | * Completed parsing an op_region declaration, we now | ||
537 | * know the length. | ||
538 | */ | ||
539 | op->named.length = (u32) (parser_state->aml - op->named.data); | ||
540 | } | ||
541 | } | ||
542 | |||
543 | if (walk_state->op_info->flags & AML_CREATE) { | ||
544 | /* | ||
545 | * Backup to beginning of create_xXXfield declaration (1 for | ||
546 | * Opcode) | ||
547 | * | ||
548 | * body_length is unknown until we parse the body | ||
549 | */ | ||
550 | op->named.length = (u32) (parser_state->aml - op->named.data); | ||
551 | } | ||
552 | |||
553 | /* This op complete, notify the dispatcher */ | ||
554 | |||
555 | if (walk_state->ascending_callback != NULL) { | ||
556 | walk_state->op = op; | ||
557 | walk_state->opcode = op->common.aml_opcode; | ||
558 | |||
559 | status = walk_state->ascending_callback (walk_state); | ||
560 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
561 | if (status == AE_CTRL_PENDING) { | ||
562 | status = AE_OK; | ||
563 | goto close_this_op; | ||
564 | } | ||
565 | } | ||
566 | |||
567 | |||
568 | close_this_op: | ||
569 | /* | ||
570 | * Finished one argument of the containing scope | ||
571 | */ | ||
572 | parser_state->scope->parse_scope.arg_count--; | ||
573 | |||
574 | /* Finished with pre_op */ | ||
575 | |||
576 | if (pre_op) { | ||
577 | acpi_ps_free_op (pre_op); | ||
578 | pre_op = NULL; | ||
579 | } | ||
580 | |||
581 | /* Close this Op (will result in parse subtree deletion) */ | ||
582 | |||
583 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
584 | if (ACPI_FAILURE (status2)) { | ||
585 | return_ACPI_STATUS (status2); | ||
586 | } | ||
587 | op = NULL; | ||
588 | |||
589 | switch (status) { | ||
590 | case AE_OK: | ||
591 | break; | ||
592 | |||
593 | |||
594 | case AE_CTRL_TRANSFER: | ||
595 | |||
596 | /* We are about to transfer to a called method. */ | ||
597 | |||
598 | walk_state->prev_op = op; | ||
599 | walk_state->prev_arg_types = walk_state->arg_types; | ||
600 | return_ACPI_STATUS (status); | ||
601 | |||
602 | |||
603 | case AE_CTRL_END: | ||
604 | |||
605 | acpi_ps_pop_scope (parser_state, &op, | ||
606 | &walk_state->arg_types, &walk_state->arg_count); | ||
607 | |||
608 | if (op) { | ||
609 | walk_state->op = op; | ||
610 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
611 | walk_state->opcode = op->common.aml_opcode; | ||
612 | |||
613 | status = walk_state->ascending_callback (walk_state); | ||
614 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
615 | |||
616 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
617 | if (ACPI_FAILURE (status2)) { | ||
618 | return_ACPI_STATUS (status2); | ||
619 | } | ||
620 | op = NULL; | ||
621 | } | ||
622 | status = AE_OK; | ||
623 | break; | ||
624 | |||
625 | |||
626 | case AE_CTRL_BREAK: | ||
627 | case AE_CTRL_CONTINUE: | ||
628 | |||
629 | /* Pop off scopes until we find the While */ | ||
630 | |||
631 | while (!op || (op->common.aml_opcode != AML_WHILE_OP)) { | ||
632 | acpi_ps_pop_scope (parser_state, &op, | ||
633 | &walk_state->arg_types, &walk_state->arg_count); | ||
634 | } | ||
635 | |||
636 | /* Close this iteration of the While loop */ | ||
637 | |||
638 | walk_state->op = op; | ||
639 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
640 | walk_state->opcode = op->common.aml_opcode; | ||
641 | |||
642 | status = walk_state->ascending_callback (walk_state); | ||
643 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
644 | |||
645 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
646 | if (ACPI_FAILURE (status2)) { | ||
647 | return_ACPI_STATUS (status2); | ||
648 | } | ||
649 | op = NULL; | ||
650 | |||
651 | status = AE_OK; | ||
652 | break; | ||
653 | |||
654 | |||
655 | case AE_CTRL_TERMINATE: | ||
656 | |||
657 | status = AE_OK; | ||
658 | |||
659 | /* Clean up */ | ||
660 | do { | ||
661 | if (op) { | ||
662 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
663 | if (ACPI_FAILURE (status2)) { | ||
664 | return_ACPI_STATUS (status2); | ||
665 | } | ||
666 | } | ||
667 | acpi_ps_pop_scope (parser_state, &op, | ||
668 | &walk_state->arg_types, &walk_state->arg_count); | ||
669 | |||
670 | } while (op); | ||
671 | |||
672 | return_ACPI_STATUS (status); | ||
673 | |||
674 | |||
675 | default: /* All other non-AE_OK status */ | ||
676 | |||
677 | do { | ||
678 | if (op) { | ||
679 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
680 | if (ACPI_FAILURE (status2)) { | ||
681 | return_ACPI_STATUS (status2); | ||
682 | } | ||
683 | } | ||
684 | acpi_ps_pop_scope (parser_state, &op, | ||
685 | &walk_state->arg_types, &walk_state->arg_count); | ||
686 | |||
687 | } while (op); | ||
688 | |||
689 | |||
690 | /* | ||
691 | * TBD: Cleanup parse ops on error | ||
692 | */ | ||
693 | #if 0 | ||
694 | if (op == NULL) { | ||
695 | acpi_ps_pop_scope (parser_state, &op, | ||
696 | &walk_state->arg_types, &walk_state->arg_count); | ||
697 | } | ||
698 | #endif | ||
699 | walk_state->prev_op = op; | ||
700 | walk_state->prev_arg_types = walk_state->arg_types; | ||
701 | return_ACPI_STATUS (status); | ||
702 | } | ||
703 | |||
704 | /* This scope complete? */ | ||
705 | |||
706 | if (acpi_ps_has_completed_scope (parser_state)) { | ||
707 | acpi_ps_pop_scope (parser_state, &op, | ||
708 | &walk_state->arg_types, &walk_state->arg_count); | ||
709 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Popped scope, Op=%p\n", op)); | ||
710 | } | ||
711 | else { | ||
712 | op = NULL; | ||
713 | } | ||
714 | |||
715 | } /* while parser_state->Aml */ | ||
716 | |||
717 | |||
718 | /* | ||
719 | * Complete the last Op (if not completed), and clear the scope stack. | ||
720 | * It is easily possible to end an AML "package" with an unbounded number | ||
721 | * of open scopes (such as when several ASL blocks are closed with | ||
722 | * sequential closing braces). We want to terminate each one cleanly. | ||
723 | */ | ||
724 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "AML package complete at Op %p\n", op)); | ||
725 | do { | ||
726 | if (op) { | ||
727 | if (walk_state->ascending_callback != NULL) { | ||
728 | walk_state->op = op; | ||
729 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
730 | walk_state->opcode = op->common.aml_opcode; | ||
731 | |||
732 | status = walk_state->ascending_callback (walk_state); | ||
733 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
734 | if (status == AE_CTRL_PENDING) { | ||
735 | status = AE_OK; | ||
736 | goto close_this_op; | ||
737 | } | ||
738 | |||
739 | if (status == AE_CTRL_TERMINATE) { | ||
740 | status = AE_OK; | ||
741 | |||
742 | /* Clean up */ | ||
743 | do { | ||
744 | if (op) { | ||
745 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
746 | if (ACPI_FAILURE (status2)) { | ||
747 | return_ACPI_STATUS (status2); | ||
748 | } | ||
749 | } | ||
750 | |||
751 | acpi_ps_pop_scope (parser_state, &op, | ||
752 | &walk_state->arg_types, &walk_state->arg_count); | ||
753 | |||
754 | } while (op); | ||
755 | |||
756 | return_ACPI_STATUS (status); | ||
757 | } | ||
758 | |||
759 | else if (ACPI_FAILURE (status)) { | ||
760 | /* First error is most important */ | ||
761 | |||
762 | (void) acpi_ps_complete_this_op (walk_state, op); | ||
763 | return_ACPI_STATUS (status); | ||
764 | } | ||
765 | } | ||
766 | |||
767 | status2 = acpi_ps_complete_this_op (walk_state, op); | ||
768 | if (ACPI_FAILURE (status2)) { | ||
769 | return_ACPI_STATUS (status2); | ||
770 | } | ||
771 | } | ||
772 | |||
773 | acpi_ps_pop_scope (parser_state, &op, &walk_state->arg_types, | ||
774 | &walk_state->arg_count); | ||
775 | |||
776 | } while (op); | ||
777 | |||
778 | return_ACPI_STATUS (status); | ||
779 | } | ||
780 | |||
781 | |||
diff --git a/drivers/acpi/parser/psopcode.c b/drivers/acpi/parser/psopcode.c index 5744673568c0..6f7594a516d2 100644 --- a/drivers/acpi/parser/psopcode.c +++ b/drivers/acpi/parser/psopcode.c | |||
@@ -311,7 +311,7 @@ const struct acpi_opcode_info acpi_gbl_aml_op_info[AML_NUM_OPCODES] = | |||
311 | /* ACPI 2.0 opcodes */ | 311 | /* ACPI 2.0 opcodes */ |
312 | 312 | ||
313 | /* 6E */ ACPI_OP ("QwordConst", ARGP_QWORD_OP, ARGI_QWORD_OP, ACPI_TYPE_INTEGER, AML_CLASS_ARGUMENT, AML_TYPE_LITERAL, AML_CONSTANT), | 313 | /* 6E */ ACPI_OP ("QwordConst", ARGP_QWORD_OP, ARGI_QWORD_OP, ACPI_TYPE_INTEGER, AML_CLASS_ARGUMENT, AML_TYPE_LITERAL, AML_CONSTANT), |
314 | /* 6F */ ACPI_OP ("Package /*Var*/", ARGP_VAR_PACKAGE_OP, ARGI_VAR_PACKAGE_OP, ACPI_TYPE_PACKAGE, AML_CLASS_CREATE, AML_TYPE_CREATE_OBJECT, AML_HAS_ARGS | AML_DEFER), | 314 | /* 6F */ ACPI_OP ("Package", /* Var */ ARGP_VAR_PACKAGE_OP, ARGI_VAR_PACKAGE_OP, ACPI_TYPE_PACKAGE, AML_CLASS_CREATE, AML_TYPE_CREATE_OBJECT, AML_HAS_ARGS | AML_DEFER), |
315 | /* 70 */ ACPI_OP ("ConcatenateResTemplate", ARGP_CONCAT_RES_OP, ARGI_CONCAT_RES_OP, ACPI_TYPE_ANY, AML_CLASS_EXECUTE, AML_TYPE_EXEC_2A_1T_1R, AML_FLAGS_EXEC_2A_1T_1R | AML_CONSTANT), | 315 | /* 70 */ ACPI_OP ("ConcatenateResTemplate", ARGP_CONCAT_RES_OP, ARGI_CONCAT_RES_OP, ACPI_TYPE_ANY, AML_CLASS_EXECUTE, AML_TYPE_EXEC_2A_1T_1R, AML_FLAGS_EXEC_2A_1T_1R | AML_CONSTANT), |
316 | /* 71 */ ACPI_OP ("Mod", ARGP_MOD_OP, ARGI_MOD_OP, ACPI_TYPE_ANY, AML_CLASS_EXECUTE, AML_TYPE_EXEC_2A_1T_1R, AML_FLAGS_EXEC_2A_1T_1R | AML_CONSTANT), | 316 | /* 71 */ ACPI_OP ("Mod", ARGP_MOD_OP, ARGI_MOD_OP, ACPI_TYPE_ANY, AML_CLASS_EXECUTE, AML_TYPE_EXEC_2A_1T_1R, AML_FLAGS_EXEC_2A_1T_1R | AML_CONSTANT), |
317 | /* 72 */ ACPI_OP ("CreateQWordField", ARGP_CREATE_QWORD_FIELD_OP,ARGI_CREATE_QWORD_FIELD_OP, ACPI_TYPE_BUFFER_FIELD, AML_CLASS_CREATE, AML_TYPE_CREATE_FIELD, AML_HAS_ARGS | AML_NSOBJECT | AML_NSNODE | AML_DEFER | AML_CREATE), | 317 | /* 72 */ ACPI_OP ("CreateQWordField", ARGP_CREATE_QWORD_FIELD_OP,ARGI_CREATE_QWORD_FIELD_OP, ACPI_TYPE_BUFFER_FIELD, AML_CLASS_CREATE, AML_TYPE_CREATE_FIELD, AML_HAS_ARGS | AML_NSOBJECT | AML_NSNODE | AML_DEFER | AML_CREATE), |
@@ -428,33 +428,23 @@ acpi_ps_get_opcode_info ( | |||
428 | /* | 428 | /* |
429 | * Detect normal 8-bit opcode or extended 16-bit opcode | 429 | * Detect normal 8-bit opcode or extended 16-bit opcode |
430 | */ | 430 | */ |
431 | switch ((u8) (opcode >> 8)) { | 431 | if (!(opcode & 0xFF00)) { |
432 | case 0: | ||
433 | |||
434 | /* Simple (8-bit) opcode: 0-255, can't index beyond table */ | 432 | /* Simple (8-bit) opcode: 0-255, can't index beyond table */ |
435 | 433 | ||
436 | return (&acpi_gbl_aml_op_info [acpi_gbl_short_op_index [(u8) opcode]]); | 434 | return (&acpi_gbl_aml_op_info [acpi_gbl_short_op_index [(u8) opcode]]); |
435 | } | ||
437 | 436 | ||
438 | case AML_EXTOP: | 437 | if (((opcode & 0xFF00) == AML_EXTENDED_OPCODE) && |
439 | 438 | (((u8) opcode) <= MAX_EXTENDED_OPCODE)) { | |
440 | /* Extended (16-bit, prefix+opcode) opcode */ | 439 | /* Valid extended (16-bit) opcode */ |
441 | |||
442 | if (((u8) opcode) <= MAX_EXTENDED_OPCODE) { | ||
443 | return (&acpi_gbl_aml_op_info [acpi_gbl_long_op_index [(u8) opcode]]); | ||
444 | } | ||
445 | |||
446 | /* Else fall through to error case below */ | ||
447 | /*lint -fallthrough */ | ||
448 | |||
449 | default: | ||
450 | 440 | ||
451 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | 441 | return (&acpi_gbl_aml_op_info [acpi_gbl_long_op_index [(u8) opcode]]); |
452 | "Unknown AML opcode [%4.4X]\n", opcode)); | ||
453 | break; | ||
454 | } | 442 | } |
455 | 443 | ||
444 | /* Unknown AML opcode */ | ||
456 | 445 | ||
457 | /* Default is "unknown opcode" */ | 446 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, |
447 | "Unknown AML opcode [%4.4X]\n", opcode)); | ||
458 | 448 | ||
459 | return (&acpi_gbl_aml_op_info [_UNK]); | 449 | return (&acpi_gbl_aml_op_info [_UNK]); |
460 | } | 450 | } |
diff --git a/drivers/acpi/parser/psparse.c b/drivers/acpi/parser/psparse.c index bbfdc1a58c27..16b84a3d0436 100644 --- a/drivers/acpi/parser/psparse.c +++ b/drivers/acpi/parser/psparse.c | |||
@@ -62,26 +62,6 @@ | |||
62 | ACPI_MODULE_NAME ("psparse") | 62 | ACPI_MODULE_NAME ("psparse") |
63 | 63 | ||
64 | 64 | ||
65 | static u32 acpi_gbl_depth = 0; | ||
66 | |||
67 | /* Local prototypes */ | ||
68 | |||
69 | static void | ||
70 | acpi_ps_complete_this_op ( | ||
71 | struct acpi_walk_state *walk_state, | ||
72 | union acpi_parse_object *op); | ||
73 | |||
74 | static acpi_status | ||
75 | acpi_ps_next_parse_state ( | ||
76 | struct acpi_walk_state *walk_state, | ||
77 | union acpi_parse_object *op, | ||
78 | acpi_status callback_status); | ||
79 | |||
80 | static acpi_status | ||
81 | acpi_ps_parse_loop ( | ||
82 | struct acpi_walk_state *walk_state); | ||
83 | |||
84 | |||
85 | /******************************************************************************* | 65 | /******************************************************************************* |
86 | * | 66 | * |
87 | * FUNCTION: acpi_ps_get_opcode_size | 67 | * FUNCTION: acpi_ps_get_opcode_size |
@@ -134,8 +114,8 @@ acpi_ps_peek_opcode ( | |||
134 | aml = parser_state->aml; | 114 | aml = parser_state->aml; |
135 | opcode = (u16) ACPI_GET8 (aml); | 115 | opcode = (u16) ACPI_GET8 (aml); |
136 | 116 | ||
137 | if (opcode == AML_EXTOP) { | 117 | if (opcode == AML_EXTENDED_OP_PREFIX) { |
138 | /* Extended opcode */ | 118 | /* Extended opcode, get the second opcode byte */ |
139 | 119 | ||
140 | aml++; | 120 | aml++; |
141 | opcode = (u16) ((opcode << 8) | ACPI_GET8 (aml)); | 121 | opcode = (u16) ((opcode << 8) | ACPI_GET8 (aml)); |
@@ -152,13 +132,13 @@ acpi_ps_peek_opcode ( | |||
152 | * PARAMETERS: walk_state - Current State | 132 | * PARAMETERS: walk_state - Current State |
153 | * Op - Op to complete | 133 | * Op - Op to complete |
154 | * | 134 | * |
155 | * RETURN: None. | 135 | * RETURN: Status |
156 | * | 136 | * |
157 | * DESCRIPTION: Perform any cleanup at the completion of an Op. | 137 | * DESCRIPTION: Perform any cleanup at the completion of an Op. |
158 | * | 138 | * |
159 | ******************************************************************************/ | 139 | ******************************************************************************/ |
160 | 140 | ||
161 | static void | 141 | acpi_status |
162 | acpi_ps_complete_this_op ( | 142 | acpi_ps_complete_this_op ( |
163 | struct acpi_walk_state *walk_state, | 143 | struct acpi_walk_state *walk_state, |
164 | union acpi_parse_object *op) | 144 | union acpi_parse_object *op) |
@@ -175,19 +155,26 @@ acpi_ps_complete_this_op ( | |||
175 | /* Check for null Op, can happen if AML code is corrupt */ | 155 | /* Check for null Op, can happen if AML code is corrupt */ |
176 | 156 | ||
177 | if (!op) { | 157 | if (!op) { |
178 | return_VOID; | 158 | return_ACPI_STATUS (AE_OK); /* OK for now */ |
179 | } | 159 | } |
180 | 160 | ||
181 | /* Delete this op and the subtree below it if asked to */ | 161 | /* Delete this op and the subtree below it if asked to */ |
182 | 162 | ||
183 | if (((walk_state->parse_flags & ACPI_PARSE_TREE_MASK) != ACPI_PARSE_DELETE_TREE) || | 163 | if (((walk_state->parse_flags & ACPI_PARSE_TREE_MASK) != ACPI_PARSE_DELETE_TREE) || |
184 | (walk_state->op_info->class == AML_CLASS_ARGUMENT)) { | 164 | (walk_state->op_info->class == AML_CLASS_ARGUMENT)) { |
185 | return_VOID; | 165 | return_ACPI_STATUS (AE_OK); |
186 | } | 166 | } |
187 | 167 | ||
188 | /* Make sure that we only delete this subtree */ | 168 | /* Make sure that we only delete this subtree */ |
189 | 169 | ||
190 | if (op->common.parent) { | 170 | if (op->common.parent) { |
171 | prev = op->common.parent->common.value.arg; | ||
172 | if (!prev) { | ||
173 | /* Nothing more to do */ | ||
174 | |||
175 | goto cleanup; | ||
176 | } | ||
177 | |||
191 | /* | 178 | /* |
192 | * Check if we need to replace the operator and its subtree | 179 | * Check if we need to replace the operator and its subtree |
193 | * with a return value op (placeholder op) | 180 | * with a return value op (placeholder op) |
@@ -206,7 +193,7 @@ acpi_ps_complete_this_op ( | |||
206 | */ | 193 | */ |
207 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); | 194 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); |
208 | if (!replacement_op) { | 195 | if (!replacement_op) { |
209 | goto cleanup; | 196 | goto allocate_error; |
210 | } | 197 | } |
211 | break; | 198 | break; |
212 | 199 | ||
@@ -223,18 +210,17 @@ acpi_ps_complete_this_op ( | |||
223 | (op->common.parent->common.aml_opcode == AML_VAR_PACKAGE_OP)) { | 210 | (op->common.parent->common.aml_opcode == AML_VAR_PACKAGE_OP)) { |
224 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); | 211 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); |
225 | if (!replacement_op) { | 212 | if (!replacement_op) { |
226 | goto cleanup; | 213 | goto allocate_error; |
227 | } | 214 | } |
228 | } | 215 | } |
229 | 216 | else if ((op->common.parent->common.aml_opcode == AML_NAME_OP) && | |
230 | if ((op->common.parent->common.aml_opcode == AML_NAME_OP) && | 217 | (walk_state->pass_number <= ACPI_IMODE_LOAD_PASS2)) { |
231 | (walk_state->descending_callback != acpi_ds_exec_begin_op)) { | ||
232 | if ((op->common.aml_opcode == AML_BUFFER_OP) || | 218 | if ((op->common.aml_opcode == AML_BUFFER_OP) || |
233 | (op->common.aml_opcode == AML_PACKAGE_OP) || | 219 | (op->common.aml_opcode == AML_PACKAGE_OP) || |
234 | (op->common.aml_opcode == AML_VAR_PACKAGE_OP)) { | 220 | (op->common.aml_opcode == AML_VAR_PACKAGE_OP)) { |
235 | replacement_op = acpi_ps_alloc_op (op->common.aml_opcode); | 221 | replacement_op = acpi_ps_alloc_op (op->common.aml_opcode); |
236 | if (!replacement_op) { | 222 | if (!replacement_op) { |
237 | goto cleanup; | 223 | goto allocate_error; |
238 | } | 224 | } |
239 | 225 | ||
240 | replacement_op->named.data = op->named.data; | 226 | replacement_op->named.data = op->named.data; |
@@ -244,15 +230,15 @@ acpi_ps_complete_this_op ( | |||
244 | break; | 230 | break; |
245 | 231 | ||
246 | default: | 232 | default: |
233 | |||
247 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); | 234 | replacement_op = acpi_ps_alloc_op (AML_INT_RETURN_VALUE_OP); |
248 | if (!replacement_op) { | 235 | if (!replacement_op) { |
249 | goto cleanup; | 236 | goto allocate_error; |
250 | } | 237 | } |
251 | } | 238 | } |
252 | 239 | ||
253 | /* We must unlink this op from the parent tree */ | 240 | /* We must unlink this op from the parent tree */ |
254 | 241 | ||
255 | prev = op->common.parent->common.value.arg; | ||
256 | if (prev == op) { | 242 | if (prev == op) { |
257 | /* This op is the first in the list */ | 243 | /* This op is the first in the list */ |
258 | 244 | ||
@@ -298,7 +284,15 @@ cleanup: | |||
298 | /* Now we can actually delete the subtree rooted at Op */ | 284 | /* Now we can actually delete the subtree rooted at Op */ |
299 | 285 | ||
300 | acpi_ps_delete_parse_tree (op); | 286 | acpi_ps_delete_parse_tree (op); |
301 | return_VOID; | 287 | return_ACPI_STATUS (AE_OK); |
288 | |||
289 | |||
290 | allocate_error: | ||
291 | |||
292 | /* Always delete the subtree, even on error */ | ||
293 | |||
294 | acpi_ps_delete_parse_tree (op); | ||
295 | return_ACPI_STATUS (AE_NO_MEMORY); | ||
302 | } | 296 | } |
303 | 297 | ||
304 | 298 | ||
@@ -317,7 +311,7 @@ cleanup: | |||
317 | * | 311 | * |
318 | ******************************************************************************/ | 312 | ******************************************************************************/ |
319 | 313 | ||
320 | static acpi_status | 314 | acpi_status |
321 | acpi_ps_next_parse_state ( | 315 | acpi_ps_next_parse_state ( |
322 | struct acpi_walk_state *walk_state, | 316 | struct acpi_walk_state *walk_state, |
323 | union acpi_parse_object *op, | 317 | union acpi_parse_object *op, |
@@ -427,663 +421,6 @@ acpi_ps_next_parse_state ( | |||
427 | 421 | ||
428 | /******************************************************************************* | 422 | /******************************************************************************* |
429 | * | 423 | * |
430 | * FUNCTION: acpi_ps_parse_loop | ||
431 | * | ||
432 | * PARAMETERS: walk_state - Current state | ||
433 | * | ||
434 | * RETURN: Status | ||
435 | * | ||
436 | * DESCRIPTION: Parse AML (pointed to by the current parser state) and return | ||
437 | * a tree of ops. | ||
438 | * | ||
439 | ******************************************************************************/ | ||
440 | |||
441 | static acpi_status | ||
442 | acpi_ps_parse_loop ( | ||
443 | struct acpi_walk_state *walk_state) | ||
444 | { | ||
445 | acpi_status status = AE_OK; | ||
446 | union acpi_parse_object *op = NULL; /* current op */ | ||
447 | union acpi_parse_object *arg = NULL; | ||
448 | union acpi_parse_object *pre_op = NULL; | ||
449 | struct acpi_parse_state *parser_state; | ||
450 | u8 *aml_op_start = NULL; | ||
451 | |||
452 | |||
453 | ACPI_FUNCTION_TRACE_PTR ("ps_parse_loop", walk_state); | ||
454 | |||
455 | if (walk_state->descending_callback == NULL) { | ||
456 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
457 | } | ||
458 | |||
459 | parser_state = &walk_state->parser_state; | ||
460 | walk_state->arg_types = 0; | ||
461 | |||
462 | #if (!defined (ACPI_NO_METHOD_EXECUTION) && !defined (ACPI_CONSTANT_EVAL_ONLY)) | ||
463 | |||
464 | if (walk_state->walk_type & ACPI_WALK_METHOD_RESTART) { | ||
465 | /* We are restarting a preempted control method */ | ||
466 | |||
467 | if (acpi_ps_has_completed_scope (parser_state)) { | ||
468 | /* | ||
469 | * We must check if a predicate to an IF or WHILE statement | ||
470 | * was just completed | ||
471 | */ | ||
472 | if ((parser_state->scope->parse_scope.op) && | ||
473 | ((parser_state->scope->parse_scope.op->common.aml_opcode == AML_IF_OP) || | ||
474 | (parser_state->scope->parse_scope.op->common.aml_opcode == AML_WHILE_OP)) && | ||
475 | (walk_state->control_state) && | ||
476 | (walk_state->control_state->common.state == | ||
477 | ACPI_CONTROL_PREDICATE_EXECUTING)) { | ||
478 | /* | ||
479 | * A predicate was just completed, get the value of the | ||
480 | * predicate and branch based on that value | ||
481 | */ | ||
482 | walk_state->op = NULL; | ||
483 | status = acpi_ds_get_predicate_value (walk_state, ACPI_TO_POINTER (TRUE)); | ||
484 | if (ACPI_FAILURE (status) && | ||
485 | ((status & AE_CODE_MASK) != AE_CODE_CONTROL)) { | ||
486 | if (status == AE_AML_NO_RETURN_VALUE) { | ||
487 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
488 | "Invoked method did not return a value, %s\n", | ||
489 | acpi_format_exception (status))); | ||
490 | |||
491 | } | ||
492 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
493 | "get_predicate Failed, %s\n", | ||
494 | acpi_format_exception (status))); | ||
495 | return_ACPI_STATUS (status); | ||
496 | } | ||
497 | |||
498 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
499 | } | ||
500 | |||
501 | acpi_ps_pop_scope (parser_state, &op, | ||
502 | &walk_state->arg_types, &walk_state->arg_count); | ||
503 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Popped scope, Op=%p\n", op)); | ||
504 | } | ||
505 | else if (walk_state->prev_op) { | ||
506 | /* We were in the middle of an op */ | ||
507 | |||
508 | op = walk_state->prev_op; | ||
509 | walk_state->arg_types = walk_state->prev_arg_types; | ||
510 | } | ||
511 | } | ||
512 | #endif | ||
513 | |||
514 | /* Iterative parsing loop, while there is more AML to process: */ | ||
515 | |||
516 | while ((parser_state->aml < parser_state->aml_end) || (op)) { | ||
517 | aml_op_start = parser_state->aml; | ||
518 | if (!op) { | ||
519 | /* Get the next opcode from the AML stream */ | ||
520 | |||
521 | walk_state->aml_offset = (u32) ACPI_PTR_DIFF (parser_state->aml, | ||
522 | parser_state->aml_start); | ||
523 | walk_state->opcode = acpi_ps_peek_opcode (parser_state); | ||
524 | |||
525 | /* | ||
526 | * First cut to determine what we have found: | ||
527 | * 1) A valid AML opcode | ||
528 | * 2) A name string | ||
529 | * 3) An unknown/invalid opcode | ||
530 | */ | ||
531 | walk_state->op_info = acpi_ps_get_opcode_info (walk_state->opcode); | ||
532 | switch (walk_state->op_info->class) { | ||
533 | case AML_CLASS_ASCII: | ||
534 | case AML_CLASS_PREFIX: | ||
535 | /* | ||
536 | * Starts with a valid prefix or ASCII char, this is a name | ||
537 | * string. Convert the bare name string to a namepath. | ||
538 | */ | ||
539 | walk_state->opcode = AML_INT_NAMEPATH_OP; | ||
540 | walk_state->arg_types = ARGP_NAMESTRING; | ||
541 | break; | ||
542 | |||
543 | case AML_CLASS_UNKNOWN: | ||
544 | |||
545 | /* The opcode is unrecognized. Just skip unknown opcodes */ | ||
546 | |||
547 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
548 | "Found unknown opcode %X at AML address %p offset %X, ignoring\n", | ||
549 | walk_state->opcode, parser_state->aml, walk_state->aml_offset)); | ||
550 | |||
551 | ACPI_DUMP_BUFFER (parser_state->aml, 128); | ||
552 | |||
553 | /* Assume one-byte bad opcode */ | ||
554 | |||
555 | parser_state->aml++; | ||
556 | continue; | ||
557 | |||
558 | default: | ||
559 | |||
560 | /* Found opcode info, this is a normal opcode */ | ||
561 | |||
562 | parser_state->aml += acpi_ps_get_opcode_size (walk_state->opcode); | ||
563 | walk_state->arg_types = walk_state->op_info->parse_args; | ||
564 | break; | ||
565 | } | ||
566 | |||
567 | /* Create Op structure and append to parent's argument list */ | ||
568 | |||
569 | if (walk_state->op_info->flags & AML_NAMED) { | ||
570 | /* Allocate a new pre_op if necessary */ | ||
571 | |||
572 | if (!pre_op) { | ||
573 | pre_op = acpi_ps_alloc_op (walk_state->opcode); | ||
574 | if (!pre_op) { | ||
575 | status = AE_NO_MEMORY; | ||
576 | goto close_this_op; | ||
577 | } | ||
578 | } | ||
579 | |||
580 | pre_op->common.value.arg = NULL; | ||
581 | pre_op->common.aml_opcode = walk_state->opcode; | ||
582 | |||
583 | /* | ||
584 | * Get and append arguments until we find the node that contains | ||
585 | * the name (the type ARGP_NAME). | ||
586 | */ | ||
587 | while (GET_CURRENT_ARG_TYPE (walk_state->arg_types) && | ||
588 | (GET_CURRENT_ARG_TYPE (walk_state->arg_types) != ARGP_NAME)) { | ||
589 | status = acpi_ps_get_next_arg (walk_state, parser_state, | ||
590 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), &arg); | ||
591 | if (ACPI_FAILURE (status)) { | ||
592 | goto close_this_op; | ||
593 | } | ||
594 | |||
595 | acpi_ps_append_arg (pre_op, arg); | ||
596 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
597 | } | ||
598 | |||
599 | /* | ||
600 | * Make sure that we found a NAME and didn't run out of | ||
601 | * arguments | ||
602 | */ | ||
603 | if (!GET_CURRENT_ARG_TYPE (walk_state->arg_types)) { | ||
604 | status = AE_AML_NO_OPERAND; | ||
605 | goto close_this_op; | ||
606 | } | ||
607 | |||
608 | /* We know that this arg is a name, move to next arg */ | ||
609 | |||
610 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
611 | |||
612 | /* | ||
613 | * Find the object. This will either insert the object into | ||
614 | * the namespace or simply look it up | ||
615 | */ | ||
616 | walk_state->op = NULL; | ||
617 | |||
618 | status = walk_state->descending_callback (walk_state, &op); | ||
619 | if (ACPI_FAILURE (status)) { | ||
620 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
621 | "During name lookup/catalog, %s\n", | ||
622 | acpi_format_exception (status))); | ||
623 | goto close_this_op; | ||
624 | } | ||
625 | |||
626 | if (!op) { | ||
627 | continue; | ||
628 | } | ||
629 | |||
630 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
631 | if (status == AE_CTRL_PENDING) { | ||
632 | status = AE_OK; | ||
633 | goto close_this_op; | ||
634 | } | ||
635 | |||
636 | if (ACPI_FAILURE (status)) { | ||
637 | goto close_this_op; | ||
638 | } | ||
639 | |||
640 | acpi_ps_append_arg (op, pre_op->common.value.arg); | ||
641 | acpi_gbl_depth++; | ||
642 | |||
643 | if (op->common.aml_opcode == AML_REGION_OP) { | ||
644 | /* | ||
645 | * Defer final parsing of an operation_region body, | ||
646 | * because we don't have enough info in the first pass | ||
647 | * to parse it correctly (i.e., there may be method | ||
648 | * calls within the term_arg elements of the body.) | ||
649 | * | ||
650 | * However, we must continue parsing because | ||
651 | * the opregion is not a standalone package -- | ||
652 | * we don't know where the end is at this point. | ||
653 | * | ||
654 | * (Length is unknown until parse of the body complete) | ||
655 | */ | ||
656 | op->named.data = aml_op_start; | ||
657 | op->named.length = 0; | ||
658 | } | ||
659 | } | ||
660 | else { | ||
661 | /* Not a named opcode, just allocate Op and append to parent */ | ||
662 | |||
663 | walk_state->op_info = acpi_ps_get_opcode_info (walk_state->opcode); | ||
664 | op = acpi_ps_alloc_op (walk_state->opcode); | ||
665 | if (!op) { | ||
666 | status = AE_NO_MEMORY; | ||
667 | goto close_this_op; | ||
668 | } | ||
669 | |||
670 | if (walk_state->op_info->flags & AML_CREATE) { | ||
671 | /* | ||
672 | * Backup to beginning of create_xXXfield declaration | ||
673 | * body_length is unknown until we parse the body | ||
674 | */ | ||
675 | op->named.data = aml_op_start; | ||
676 | op->named.length = 0; | ||
677 | } | ||
678 | |||
679 | acpi_ps_append_arg (acpi_ps_get_parent_scope (parser_state), op); | ||
680 | |||
681 | if ((walk_state->descending_callback != NULL)) { | ||
682 | /* | ||
683 | * Find the object. This will either insert the object into | ||
684 | * the namespace or simply look it up | ||
685 | */ | ||
686 | walk_state->op = op; | ||
687 | |||
688 | status = walk_state->descending_callback (walk_state, &op); | ||
689 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
690 | if (status == AE_CTRL_PENDING) { | ||
691 | status = AE_OK; | ||
692 | goto close_this_op; | ||
693 | } | ||
694 | |||
695 | if (ACPI_FAILURE (status)) { | ||
696 | goto close_this_op; | ||
697 | } | ||
698 | } | ||
699 | } | ||
700 | |||
701 | op->common.aml_offset = walk_state->aml_offset; | ||
702 | |||
703 | if (walk_state->op_info) { | ||
704 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | ||
705 | "Opcode %4.4X [%s] Op %p Aml %p aml_offset %5.5X\n", | ||
706 | (u32) op->common.aml_opcode, walk_state->op_info->name, | ||
707 | op, parser_state->aml, op->common.aml_offset)); | ||
708 | } | ||
709 | } | ||
710 | |||
711 | |||
712 | /* | ||
713 | * Start arg_count at zero because we don't know if there are | ||
714 | * any args yet | ||
715 | */ | ||
716 | walk_state->arg_count = 0; | ||
717 | |||
718 | /* Are there any arguments that must be processed? */ | ||
719 | |||
720 | if (walk_state->arg_types) { | ||
721 | /* Get arguments */ | ||
722 | |||
723 | switch (op->common.aml_opcode) { | ||
724 | case AML_BYTE_OP: /* AML_BYTEDATA_ARG */ | ||
725 | case AML_WORD_OP: /* AML_WORDDATA_ARG */ | ||
726 | case AML_DWORD_OP: /* AML_DWORDATA_ARG */ | ||
727 | case AML_QWORD_OP: /* AML_QWORDATA_ARG */ | ||
728 | case AML_STRING_OP: /* AML_ASCIICHARLIST_ARG */ | ||
729 | |||
730 | /* Fill in constant or string argument directly */ | ||
731 | |||
732 | acpi_ps_get_next_simple_arg (parser_state, | ||
733 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), op); | ||
734 | break; | ||
735 | |||
736 | case AML_INT_NAMEPATH_OP: /* AML_NAMESTRING_ARG */ | ||
737 | |||
738 | status = acpi_ps_get_next_namepath (walk_state, parser_state, op, 1); | ||
739 | if (ACPI_FAILURE (status)) { | ||
740 | goto close_this_op; | ||
741 | } | ||
742 | |||
743 | walk_state->arg_types = 0; | ||
744 | break; | ||
745 | |||
746 | default: | ||
747 | |||
748 | /* | ||
749 | * Op is not a constant or string, append each argument | ||
750 | * to the Op | ||
751 | */ | ||
752 | while (GET_CURRENT_ARG_TYPE (walk_state->arg_types) && | ||
753 | !walk_state->arg_count) { | ||
754 | walk_state->aml_offset = (u32) | ||
755 | ACPI_PTR_DIFF (parser_state->aml, parser_state->aml_start); | ||
756 | |||
757 | status = acpi_ps_get_next_arg (walk_state, parser_state, | ||
758 | GET_CURRENT_ARG_TYPE (walk_state->arg_types), | ||
759 | &arg); | ||
760 | if (ACPI_FAILURE (status)) { | ||
761 | goto close_this_op; | ||
762 | } | ||
763 | |||
764 | if (arg) { | ||
765 | arg->common.aml_offset = walk_state->aml_offset; | ||
766 | acpi_ps_append_arg (op, arg); | ||
767 | } | ||
768 | INCREMENT_ARG_LIST (walk_state->arg_types); | ||
769 | } | ||
770 | |||
771 | /* Special processing for certain opcodes */ | ||
772 | |||
773 | switch (op->common.aml_opcode) { | ||
774 | case AML_METHOD_OP: | ||
775 | |||
776 | /* | ||
777 | * Skip parsing of control method | ||
778 | * because we don't have enough info in the first pass | ||
779 | * to parse it correctly. | ||
780 | * | ||
781 | * Save the length and address of the body | ||
782 | */ | ||
783 | op->named.data = parser_state->aml; | ||
784 | op->named.length = (u32) (parser_state->pkg_end - | ||
785 | parser_state->aml); | ||
786 | |||
787 | /* Skip body of method */ | ||
788 | |||
789 | parser_state->aml = parser_state->pkg_end; | ||
790 | walk_state->arg_count = 0; | ||
791 | break; | ||
792 | |||
793 | case AML_BUFFER_OP: | ||
794 | case AML_PACKAGE_OP: | ||
795 | case AML_VAR_PACKAGE_OP: | ||
796 | |||
797 | if ((op->common.parent) && | ||
798 | (op->common.parent->common.aml_opcode == AML_NAME_OP) && | ||
799 | (walk_state->descending_callback != acpi_ds_exec_begin_op)) { | ||
800 | /* | ||
801 | * Skip parsing of Buffers and Packages | ||
802 | * because we don't have enough info in the first pass | ||
803 | * to parse them correctly. | ||
804 | */ | ||
805 | op->named.data = aml_op_start; | ||
806 | op->named.length = (u32) (parser_state->pkg_end - | ||
807 | aml_op_start); | ||
808 | |||
809 | /* Skip body */ | ||
810 | |||
811 | parser_state->aml = parser_state->pkg_end; | ||
812 | walk_state->arg_count = 0; | ||
813 | } | ||
814 | break; | ||
815 | |||
816 | case AML_WHILE_OP: | ||
817 | |||
818 | if (walk_state->control_state) { | ||
819 | walk_state->control_state->control.package_end = | ||
820 | parser_state->pkg_end; | ||
821 | } | ||
822 | break; | ||
823 | |||
824 | default: | ||
825 | |||
826 | /* No action for all other opcodes */ | ||
827 | break; | ||
828 | } | ||
829 | break; | ||
830 | } | ||
831 | } | ||
832 | |||
833 | /* Check for arguments that need to be processed */ | ||
834 | |||
835 | if (walk_state->arg_count) { | ||
836 | /* | ||
837 | * There are arguments (complex ones), push Op and | ||
838 | * prepare for argument | ||
839 | */ | ||
840 | status = acpi_ps_push_scope (parser_state, op, | ||
841 | walk_state->arg_types, walk_state->arg_count); | ||
842 | if (ACPI_FAILURE (status)) { | ||
843 | goto close_this_op; | ||
844 | } | ||
845 | op = NULL; | ||
846 | continue; | ||
847 | } | ||
848 | |||
849 | /* | ||
850 | * All arguments have been processed -- Op is complete, | ||
851 | * prepare for next | ||
852 | */ | ||
853 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
854 | if (walk_state->op_info->flags & AML_NAMED) { | ||
855 | if (acpi_gbl_depth) { | ||
856 | acpi_gbl_depth--; | ||
857 | } | ||
858 | |||
859 | if (op->common.aml_opcode == AML_REGION_OP) { | ||
860 | /* | ||
861 | * Skip parsing of control method or opregion body, | ||
862 | * because we don't have enough info in the first pass | ||
863 | * to parse them correctly. | ||
864 | * | ||
865 | * Completed parsing an op_region declaration, we now | ||
866 | * know the length. | ||
867 | */ | ||
868 | op->named.length = (u32) (parser_state->aml - op->named.data); | ||
869 | } | ||
870 | } | ||
871 | |||
872 | if (walk_state->op_info->flags & AML_CREATE) { | ||
873 | /* | ||
874 | * Backup to beginning of create_xXXfield declaration (1 for | ||
875 | * Opcode) | ||
876 | * | ||
877 | * body_length is unknown until we parse the body | ||
878 | */ | ||
879 | op->named.length = (u32) (parser_state->aml - op->named.data); | ||
880 | } | ||
881 | |||
882 | /* This op complete, notify the dispatcher */ | ||
883 | |||
884 | if (walk_state->ascending_callback != NULL) { | ||
885 | walk_state->op = op; | ||
886 | walk_state->opcode = op->common.aml_opcode; | ||
887 | |||
888 | status = walk_state->ascending_callback (walk_state); | ||
889 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
890 | if (status == AE_CTRL_PENDING) { | ||
891 | status = AE_OK; | ||
892 | goto close_this_op; | ||
893 | } | ||
894 | } | ||
895 | |||
896 | |||
897 | close_this_op: | ||
898 | /* | ||
899 | * Finished one argument of the containing scope | ||
900 | */ | ||
901 | parser_state->scope->parse_scope.arg_count--; | ||
902 | |||
903 | /* Close this Op (will result in parse subtree deletion) */ | ||
904 | |||
905 | acpi_ps_complete_this_op (walk_state, op); | ||
906 | op = NULL; | ||
907 | if (pre_op) { | ||
908 | acpi_ps_free_op (pre_op); | ||
909 | pre_op = NULL; | ||
910 | } | ||
911 | |||
912 | switch (status) { | ||
913 | case AE_OK: | ||
914 | break; | ||
915 | |||
916 | |||
917 | case AE_CTRL_TRANSFER: | ||
918 | |||
919 | /* We are about to transfer to a called method. */ | ||
920 | |||
921 | walk_state->prev_op = op; | ||
922 | walk_state->prev_arg_types = walk_state->arg_types; | ||
923 | return_ACPI_STATUS (status); | ||
924 | |||
925 | |||
926 | case AE_CTRL_END: | ||
927 | |||
928 | acpi_ps_pop_scope (parser_state, &op, | ||
929 | &walk_state->arg_types, &walk_state->arg_count); | ||
930 | |||
931 | if (op) { | ||
932 | walk_state->op = op; | ||
933 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
934 | walk_state->opcode = op->common.aml_opcode; | ||
935 | |||
936 | status = walk_state->ascending_callback (walk_state); | ||
937 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
938 | |||
939 | acpi_ps_complete_this_op (walk_state, op); | ||
940 | op = NULL; | ||
941 | } | ||
942 | status = AE_OK; | ||
943 | break; | ||
944 | |||
945 | |||
946 | case AE_CTRL_BREAK: | ||
947 | case AE_CTRL_CONTINUE: | ||
948 | |||
949 | /* Pop off scopes until we find the While */ | ||
950 | |||
951 | while (!op || (op->common.aml_opcode != AML_WHILE_OP)) { | ||
952 | acpi_ps_pop_scope (parser_state, &op, | ||
953 | &walk_state->arg_types, &walk_state->arg_count); | ||
954 | } | ||
955 | |||
956 | /* Close this iteration of the While loop */ | ||
957 | |||
958 | walk_state->op = op; | ||
959 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
960 | walk_state->opcode = op->common.aml_opcode; | ||
961 | |||
962 | status = walk_state->ascending_callback (walk_state); | ||
963 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
964 | |||
965 | acpi_ps_complete_this_op (walk_state, op); | ||
966 | op = NULL; | ||
967 | |||
968 | status = AE_OK; | ||
969 | break; | ||
970 | |||
971 | |||
972 | case AE_CTRL_TERMINATE: | ||
973 | |||
974 | status = AE_OK; | ||
975 | |||
976 | /* Clean up */ | ||
977 | do { | ||
978 | if (op) { | ||
979 | acpi_ps_complete_this_op (walk_state, op); | ||
980 | } | ||
981 | acpi_ps_pop_scope (parser_state, &op, | ||
982 | &walk_state->arg_types, &walk_state->arg_count); | ||
983 | |||
984 | } while (op); | ||
985 | |||
986 | return_ACPI_STATUS (status); | ||
987 | |||
988 | |||
989 | default: /* All other non-AE_OK status */ | ||
990 | |||
991 | do { | ||
992 | if (op) { | ||
993 | acpi_ps_complete_this_op (walk_state, op); | ||
994 | } | ||
995 | acpi_ps_pop_scope (parser_state, &op, | ||
996 | &walk_state->arg_types, &walk_state->arg_count); | ||
997 | |||
998 | } while (op); | ||
999 | |||
1000 | |||
1001 | /* | ||
1002 | * TBD: Cleanup parse ops on error | ||
1003 | */ | ||
1004 | #if 0 | ||
1005 | if (op == NULL) { | ||
1006 | acpi_ps_pop_scope (parser_state, &op, | ||
1007 | &walk_state->arg_types, &walk_state->arg_count); | ||
1008 | } | ||
1009 | #endif | ||
1010 | walk_state->prev_op = op; | ||
1011 | walk_state->prev_arg_types = walk_state->arg_types; | ||
1012 | return_ACPI_STATUS (status); | ||
1013 | } | ||
1014 | |||
1015 | /* This scope complete? */ | ||
1016 | |||
1017 | if (acpi_ps_has_completed_scope (parser_state)) { | ||
1018 | acpi_ps_pop_scope (parser_state, &op, | ||
1019 | &walk_state->arg_types, &walk_state->arg_count); | ||
1020 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Popped scope, Op=%p\n", op)); | ||
1021 | } | ||
1022 | else { | ||
1023 | op = NULL; | ||
1024 | } | ||
1025 | |||
1026 | } /* while parser_state->Aml */ | ||
1027 | |||
1028 | |||
1029 | /* | ||
1030 | * Complete the last Op (if not completed), and clear the scope stack. | ||
1031 | * It is easily possible to end an AML "package" with an unbounded number | ||
1032 | * of open scopes (such as when several ASL blocks are closed with | ||
1033 | * sequential closing braces). We want to terminate each one cleanly. | ||
1034 | */ | ||
1035 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "AML package complete at Op %p\n", op)); | ||
1036 | do { | ||
1037 | if (op) { | ||
1038 | if (walk_state->ascending_callback != NULL) { | ||
1039 | walk_state->op = op; | ||
1040 | walk_state->op_info = acpi_ps_get_opcode_info (op->common.aml_opcode); | ||
1041 | walk_state->opcode = op->common.aml_opcode; | ||
1042 | |||
1043 | status = walk_state->ascending_callback (walk_state); | ||
1044 | status = acpi_ps_next_parse_state (walk_state, op, status); | ||
1045 | if (status == AE_CTRL_PENDING) { | ||
1046 | status = AE_OK; | ||
1047 | goto close_this_op; | ||
1048 | } | ||
1049 | |||
1050 | if (status == AE_CTRL_TERMINATE) { | ||
1051 | status = AE_OK; | ||
1052 | |||
1053 | /* Clean up */ | ||
1054 | do { | ||
1055 | if (op) { | ||
1056 | acpi_ps_complete_this_op (walk_state, op); | ||
1057 | } | ||
1058 | |||
1059 | acpi_ps_pop_scope (parser_state, &op, | ||
1060 | &walk_state->arg_types, &walk_state->arg_count); | ||
1061 | |||
1062 | } while (op); | ||
1063 | |||
1064 | return_ACPI_STATUS (status); | ||
1065 | } | ||
1066 | |||
1067 | else if (ACPI_FAILURE (status)) { | ||
1068 | acpi_ps_complete_this_op (walk_state, op); | ||
1069 | return_ACPI_STATUS (status); | ||
1070 | } | ||
1071 | } | ||
1072 | |||
1073 | acpi_ps_complete_this_op (walk_state, op); | ||
1074 | } | ||
1075 | |||
1076 | acpi_ps_pop_scope (parser_state, &op, &walk_state->arg_types, | ||
1077 | &walk_state->arg_count); | ||
1078 | |||
1079 | } while (op); | ||
1080 | |||
1081 | return_ACPI_STATUS (status); | ||
1082 | } | ||
1083 | |||
1084 | |||
1085 | /******************************************************************************* | ||
1086 | * | ||
1087 | * FUNCTION: acpi_ps_parse_aml | 424 | * FUNCTION: acpi_ps_parse_aml |
1088 | * | 425 | * |
1089 | * PARAMETERS: walk_state - Current state | 426 | * PARAMETERS: walk_state - Current state |
diff --git a/drivers/acpi/parser/psutils.c b/drivers/acpi/parser/psutils.c index a10f88715d43..4221b41ae1a6 100644 --- a/drivers/acpi/parser/psutils.c +++ b/drivers/acpi/parser/psutils.c | |||
@@ -154,12 +154,14 @@ acpi_ps_alloc_op ( | |||
154 | if (flags == ACPI_PARSEOP_GENERIC) { | 154 | if (flags == ACPI_PARSEOP_GENERIC) { |
155 | /* The generic op (default) is by far the most common (16 to 1) */ | 155 | /* The generic op (default) is by far the most common (16 to 1) */ |
156 | 156 | ||
157 | op = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_PSNODE); | 157 | op = acpi_os_acquire_object (acpi_gbl_ps_node_cache); |
158 | memset(op, 0, sizeof(struct acpi_parse_obj_common)); | ||
158 | } | 159 | } |
159 | else { | 160 | else { |
160 | /* Extended parseop */ | 161 | /* Extended parseop */ |
161 | 162 | ||
162 | op = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_PSNODE_EXT); | 163 | op = acpi_os_acquire_object (acpi_gbl_ps_node_ext_cache); |
164 | memset(op, 0, sizeof(struct acpi_parse_obj_named)); | ||
163 | } | 165 | } |
164 | 166 | ||
165 | /* Initialize the Op */ | 167 | /* Initialize the Op */ |
@@ -198,41 +200,14 @@ acpi_ps_free_op ( | |||
198 | } | 200 | } |
199 | 201 | ||
200 | if (op->common.flags & ACPI_PARSEOP_GENERIC) { | 202 | if (op->common.flags & ACPI_PARSEOP_GENERIC) { |
201 | acpi_ut_release_to_cache (ACPI_MEM_LIST_PSNODE, op); | 203 | (void) acpi_os_release_object (acpi_gbl_ps_node_cache, op); |
202 | } | 204 | } |
203 | else { | 205 | else { |
204 | acpi_ut_release_to_cache (ACPI_MEM_LIST_PSNODE_EXT, op); | 206 | (void) acpi_os_release_object (acpi_gbl_ps_node_ext_cache, op); |
205 | } | 207 | } |
206 | } | 208 | } |
207 | 209 | ||
208 | 210 | ||
209 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
210 | /******************************************************************************* | ||
211 | * | ||
212 | * FUNCTION: acpi_ps_delete_parse_cache | ||
213 | * | ||
214 | * PARAMETERS: None | ||
215 | * | ||
216 | * RETURN: None | ||
217 | * | ||
218 | * DESCRIPTION: Free all objects that are on the parse cache list. | ||
219 | * | ||
220 | ******************************************************************************/ | ||
221 | |||
222 | void | ||
223 | acpi_ps_delete_parse_cache ( | ||
224 | void) | ||
225 | { | ||
226 | ACPI_FUNCTION_TRACE ("ps_delete_parse_cache"); | ||
227 | |||
228 | |||
229 | acpi_ut_delete_generic_cache (ACPI_MEM_LIST_PSNODE); | ||
230 | acpi_ut_delete_generic_cache (ACPI_MEM_LIST_PSNODE_EXT); | ||
231 | return_VOID; | ||
232 | } | ||
233 | #endif | ||
234 | |||
235 | |||
236 | /******************************************************************************* | 211 | /******************************************************************************* |
237 | * | 212 | * |
238 | * FUNCTION: Utility functions | 213 | * FUNCTION: Utility functions |
diff --git a/drivers/acpi/parser/psxface.c b/drivers/acpi/parser/psxface.c index dba893648e84..d1541fabaf0a 100644 --- a/drivers/acpi/parser/psxface.c +++ b/drivers/acpi/parser/psxface.c | |||
@@ -46,19 +46,30 @@ | |||
46 | #include <acpi/acparser.h> | 46 | #include <acpi/acparser.h> |
47 | #include <acpi/acdispat.h> | 47 | #include <acpi/acdispat.h> |
48 | #include <acpi/acinterp.h> | 48 | #include <acpi/acinterp.h> |
49 | #include <acpi/acnamesp.h> | ||
50 | 49 | ||
51 | 50 | ||
52 | #define _COMPONENT ACPI_PARSER | 51 | #define _COMPONENT ACPI_PARSER |
53 | ACPI_MODULE_NAME ("psxface") | 52 | ACPI_MODULE_NAME ("psxface") |
54 | 53 | ||
54 | /* Local Prototypes */ | ||
55 | |||
56 | static acpi_status | ||
57 | acpi_ps_execute_pass ( | ||
58 | struct acpi_parameter_info *info); | ||
59 | |||
60 | static void | ||
61 | acpi_ps_update_parameter_list ( | ||
62 | struct acpi_parameter_info *info, | ||
63 | u16 action); | ||
64 | |||
55 | 65 | ||
56 | /******************************************************************************* | 66 | /******************************************************************************* |
57 | * | 67 | * |
58 | * FUNCTION: acpi_psx_execute | 68 | * FUNCTION: acpi_ps_execute_method |
59 | * | 69 | * |
60 | * PARAMETERS: Info - Method info block, contains: | 70 | * PARAMETERS: Info - Method info block, contains: |
61 | * Node - Method Node to execute | 71 | * Node - Method Node to execute |
72 | * obj_desc - Method object | ||
62 | * Parameters - List of parameters to pass to the method, | 73 | * Parameters - List of parameters to pass to the method, |
63 | * terminated by NULL. Params itself may be | 74 | * terminated by NULL. Params itself may be |
64 | * NULL if no parameters are being passed. | 75 | * NULL if no parameters are being passed. |
@@ -67,6 +78,7 @@ | |||
67 | * parameter_type - Type of Parameter list | 78 | * parameter_type - Type of Parameter list |
68 | * return_object - Where to put method's return value (if | 79 | * return_object - Where to put method's return value (if |
69 | * any). If NULL, no value is returned. | 80 | * any). If NULL, no value is returned. |
81 | * pass_number - Parse or execute pass | ||
70 | * | 82 | * |
71 | * RETURN: Status | 83 | * RETURN: Status |
72 | * | 84 | * |
@@ -75,171 +87,194 @@ | |||
75 | ******************************************************************************/ | 87 | ******************************************************************************/ |
76 | 88 | ||
77 | acpi_status | 89 | acpi_status |
78 | acpi_psx_execute ( | 90 | acpi_ps_execute_method ( |
79 | struct acpi_parameter_info *info) | 91 | struct acpi_parameter_info *info) |
80 | { | 92 | { |
81 | acpi_status status; | 93 | acpi_status status; |
82 | union acpi_operand_object *obj_desc; | ||
83 | u32 i; | ||
84 | union acpi_parse_object *op; | ||
85 | struct acpi_walk_state *walk_state; | ||
86 | 94 | ||
87 | 95 | ||
88 | ACPI_FUNCTION_TRACE ("psx_execute"); | 96 | ACPI_FUNCTION_TRACE ("ps_execute_method"); |
89 | 97 | ||
90 | 98 | ||
91 | /* Validate the Node and get the attached object */ | 99 | /* Validate the Info and method Node */ |
92 | 100 | ||
93 | if (!info || !info->node) { | 101 | if (!info || !info->node) { |
94 | return_ACPI_STATUS (AE_NULL_ENTRY); | 102 | return_ACPI_STATUS (AE_NULL_ENTRY); |
95 | } | 103 | } |
96 | 104 | ||
97 | obj_desc = acpi_ns_get_attached_object (info->node); | ||
98 | if (!obj_desc) { | ||
99 | return_ACPI_STATUS (AE_NULL_OBJECT); | ||
100 | } | ||
101 | |||
102 | /* Init for new method, wait on concurrency semaphore */ | 105 | /* Init for new method, wait on concurrency semaphore */ |
103 | 106 | ||
104 | status = acpi_ds_begin_method_execution (info->node, obj_desc, NULL); | 107 | status = acpi_ds_begin_method_execution (info->node, info->obj_desc, NULL); |
105 | if (ACPI_FAILURE (status)) { | 108 | if (ACPI_FAILURE (status)) { |
106 | return_ACPI_STATUS (status); | 109 | return_ACPI_STATUS (status); |
107 | } | 110 | } |
108 | 111 | ||
109 | if ((info->parameter_type == ACPI_PARAM_ARGS) && | ||
110 | (info->parameters)) { | ||
111 | /* | ||
112 | * The caller "owns" the parameters, so give each one an extra | ||
113 | * reference | ||
114 | */ | ||
115 | for (i = 0; info->parameters[i]; i++) { | ||
116 | acpi_ut_add_reference (info->parameters[i]); | ||
117 | } | ||
118 | } | ||
119 | |||
120 | /* | ||
121 | * 1) Perform the first pass parse of the method to enter any | ||
122 | * named objects that it creates into the namespace | ||
123 | */ | ||
124 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | ||
125 | "**** Begin Method Parse **** Entry=%p obj=%p\n", | ||
126 | info->node, obj_desc)); | ||
127 | |||
128 | /* Create and init a Root Node */ | ||
129 | |||
130 | op = acpi_ps_create_scope_op (); | ||
131 | if (!op) { | ||
132 | status = AE_NO_MEMORY; | ||
133 | goto cleanup1; | ||
134 | } | ||
135 | |||
136 | /* | 112 | /* |
137 | * Get a new owner_id for objects created by this method. Namespace | 113 | * Get a new owner_id for objects created by this method. Namespace |
138 | * objects (such as Operation Regions) can be created during the | 114 | * objects (such as Operation Regions) can be created during the |
139 | * first pass parse. | 115 | * first pass parse. |
140 | */ | 116 | */ |
141 | obj_desc->method.owning_id = acpi_ut_allocate_owner_id (ACPI_OWNER_TYPE_METHOD); | 117 | status = acpi_ut_allocate_owner_id (&info->obj_desc->method.owner_id); |
142 | |||
143 | /* Create and initialize a new walk state */ | ||
144 | |||
145 | walk_state = acpi_ds_create_walk_state (obj_desc->method.owning_id, | ||
146 | NULL, NULL, NULL); | ||
147 | if (!walk_state) { | ||
148 | status = AE_NO_MEMORY; | ||
149 | goto cleanup2; | ||
150 | } | ||
151 | |||
152 | status = acpi_ds_init_aml_walk (walk_state, op, info->node, | ||
153 | obj_desc->method.aml_start, | ||
154 | obj_desc->method.aml_length, NULL, 1); | ||
155 | if (ACPI_FAILURE (status)) { | 118 | if (ACPI_FAILURE (status)) { |
156 | goto cleanup3; | 119 | return_ACPI_STATUS (status); |
157 | } | 120 | } |
158 | 121 | ||
159 | /* Parse the AML */ | 122 | /* |
123 | * The caller "owns" the parameters, so give each one an extra | ||
124 | * reference | ||
125 | */ | ||
126 | acpi_ps_update_parameter_list (info, REF_INCREMENT); | ||
160 | 127 | ||
161 | status = acpi_ps_parse_aml (walk_state); | 128 | /* |
162 | acpi_ps_delete_parse_tree (op); | 129 | * 1) Perform the first pass parse of the method to enter any |
130 | * named objects that it creates into the namespace | ||
131 | */ | ||
132 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | ||
133 | "**** Begin Method Parse **** Entry=%p obj=%p\n", | ||
134 | info->node, info->obj_desc)); | ||
135 | |||
136 | info->pass_number = 1; | ||
137 | status = acpi_ps_execute_pass (info); | ||
163 | if (ACPI_FAILURE (status)) { | 138 | if (ACPI_FAILURE (status)) { |
164 | goto cleanup1; /* Walk state is already deleted */ | 139 | goto cleanup; |
165 | } | 140 | } |
166 | 141 | ||
167 | /* | 142 | /* |
168 | * 2) Execute the method. Performs second pass parse simultaneously | 143 | * 2) Execute the method. Performs second pass parse simultaneously |
169 | */ | 144 | */ |
170 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, | 145 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, |
171 | "**** Begin Method Execution **** Entry=%p obj=%p\n", | 146 | "**** Begin Method Execution **** Entry=%p obj=%p\n", |
172 | info->node, obj_desc)); | 147 | info->node, info->obj_desc)); |
173 | 148 | ||
174 | /* Create and init a Root Node */ | 149 | info->pass_number = 3; |
150 | status = acpi_ps_execute_pass (info); | ||
175 | 151 | ||
176 | op = acpi_ps_create_scope_op (); | 152 | |
177 | if (!op) { | 153 | cleanup: |
178 | status = AE_NO_MEMORY; | 154 | if (info->obj_desc->method.owner_id) { |
179 | goto cleanup1; | 155 | acpi_ut_release_owner_id (&info->obj_desc->method.owner_id); |
180 | } | 156 | } |
181 | 157 | ||
182 | /* Init new op with the method name and pointer back to the NS node */ | 158 | /* Take away the extra reference that we gave the parameters above */ |
183 | 159 | ||
184 | acpi_ps_set_name (op, info->node->name.integer); | 160 | acpi_ps_update_parameter_list (info, REF_DECREMENT); |
185 | op->common.node = info->node; | ||
186 | 161 | ||
187 | /* Create and initialize a new walk state */ | 162 | /* Exit now if error above */ |
188 | 163 | ||
189 | walk_state = acpi_ds_create_walk_state (0, NULL, NULL, NULL); | 164 | if (ACPI_FAILURE (status)) { |
190 | if (!walk_state) { | 165 | return_ACPI_STATUS (status); |
191 | status = AE_NO_MEMORY; | ||
192 | goto cleanup2; | ||
193 | } | 166 | } |
194 | 167 | ||
195 | status = acpi_ds_init_aml_walk (walk_state, op, info->node, | 168 | /* |
196 | obj_desc->method.aml_start, | 169 | * If the method has returned an object, signal this to the caller with |
197 | obj_desc->method.aml_length, info, 3); | 170 | * a control exception code |
198 | if (ACPI_FAILURE (status)) { | 171 | */ |
199 | goto cleanup3; | 172 | if (info->return_object) { |
173 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Method returned obj_desc=%p\n", | ||
174 | info->return_object)); | ||
175 | ACPI_DUMP_STACK_ENTRY (info->return_object); | ||
176 | |||
177 | status = AE_CTRL_RETURN_VALUE; | ||
200 | } | 178 | } |
201 | 179 | ||
202 | /* The walk of the parse tree is where we actually execute the method */ | 180 | return_ACPI_STATUS (status); |
181 | } | ||
203 | 182 | ||
204 | status = acpi_ps_parse_aml (walk_state); | ||
205 | goto cleanup2; /* Walk state already deleted */ | ||
206 | 183 | ||
184 | /******************************************************************************* | ||
185 | * | ||
186 | * FUNCTION: acpi_ps_update_parameter_list | ||
187 | * | ||
188 | * PARAMETERS: Info - See struct acpi_parameter_info | ||
189 | * (Used: parameter_type and Parameters) | ||
190 | * Action - Add or Remove reference | ||
191 | * | ||
192 | * RETURN: Status | ||
193 | * | ||
194 | * DESCRIPTION: Update reference count on all method parameter objects | ||
195 | * | ||
196 | ******************************************************************************/ | ||
207 | 197 | ||
208 | cleanup3: | 198 | static void |
209 | acpi_ds_delete_walk_state (walk_state); | 199 | acpi_ps_update_parameter_list ( |
200 | struct acpi_parameter_info *info, | ||
201 | u16 action) | ||
202 | { | ||
203 | acpi_native_uint i; | ||
210 | 204 | ||
211 | cleanup2: | ||
212 | acpi_ps_delete_parse_tree (op); | ||
213 | 205 | ||
214 | cleanup1: | ||
215 | if ((info->parameter_type == ACPI_PARAM_ARGS) && | 206 | if ((info->parameter_type == ACPI_PARAM_ARGS) && |
216 | (info->parameters)) { | 207 | (info->parameters)) { |
217 | /* Take away the extra reference that we gave the parameters above */ | 208 | /* Update reference count for each parameter */ |
218 | 209 | ||
219 | for (i = 0; info->parameters[i]; i++) { | 210 | for (i = 0; info->parameters[i]; i++) { |
220 | /* Ignore errors, just do them all */ | 211 | /* Ignore errors, just do them all */ |
221 | 212 | ||
222 | (void) acpi_ut_update_object_reference ( | 213 | (void) acpi_ut_update_object_reference (info->parameters[i], action); |
223 | info->parameters[i], REF_DECREMENT); | ||
224 | } | 214 | } |
225 | } | 215 | } |
216 | } | ||
226 | 217 | ||
227 | if (ACPI_FAILURE (status)) { | 218 | |
228 | return_ACPI_STATUS (status); | 219 | /******************************************************************************* |
220 | * | ||
221 | * FUNCTION: acpi_ps_execute_pass | ||
222 | * | ||
223 | * PARAMETERS: Info - See struct acpi_parameter_info | ||
224 | * (Used: pass_number, Node, and obj_desc) | ||
225 | * | ||
226 | * RETURN: Status | ||
227 | * | ||
228 | * DESCRIPTION: Single AML pass: Parse or Execute a control method | ||
229 | * | ||
230 | ******************************************************************************/ | ||
231 | |||
232 | static acpi_status | ||
233 | acpi_ps_execute_pass ( | ||
234 | struct acpi_parameter_info *info) | ||
235 | { | ||
236 | acpi_status status; | ||
237 | union acpi_parse_object *op; | ||
238 | struct acpi_walk_state *walk_state; | ||
239 | |||
240 | |||
241 | ACPI_FUNCTION_TRACE ("ps_execute_pass"); | ||
242 | |||
243 | |||
244 | /* Create and init a Root Node */ | ||
245 | |||
246 | op = acpi_ps_create_scope_op (); | ||
247 | if (!op) { | ||
248 | return_ACPI_STATUS (AE_NO_MEMORY); | ||
229 | } | 249 | } |
230 | 250 | ||
231 | /* | 251 | /* Create and initialize a new walk state */ |
232 | * If the method has returned an object, signal this to the caller with | ||
233 | * a control exception code | ||
234 | */ | ||
235 | if (info->return_object) { | ||
236 | ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Method returned obj_desc=%p\n", | ||
237 | info->return_object)); | ||
238 | ACPI_DUMP_STACK_ENTRY (info->return_object); | ||
239 | 252 | ||
240 | status = AE_CTRL_RETURN_VALUE; | 253 | walk_state = acpi_ds_create_walk_state ( |
254 | info->obj_desc->method.owner_id, NULL, NULL, NULL); | ||
255 | if (!walk_state) { | ||
256 | status = AE_NO_MEMORY; | ||
257 | goto cleanup; | ||
258 | } | ||
259 | |||
260 | status = acpi_ds_init_aml_walk (walk_state, op, info->node, | ||
261 | info->obj_desc->method.aml_start, | ||
262 | info->obj_desc->method.aml_length, | ||
263 | info->pass_number == 1 ? NULL : info, | ||
264 | info->pass_number); | ||
265 | if (ACPI_FAILURE (status)) { | ||
266 | acpi_ds_delete_walk_state (walk_state); | ||
267 | goto cleanup; | ||
241 | } | 268 | } |
242 | 269 | ||
270 | /* Parse the AML */ | ||
271 | |||
272 | status = acpi_ps_parse_aml (walk_state); | ||
273 | |||
274 | /* Walk state was deleted by parse_aml */ | ||
275 | |||
276 | cleanup: | ||
277 | acpi_ps_delete_parse_tree (op); | ||
243 | return_ACPI_STATUS (status); | 278 | return_ACPI_STATUS (status); |
244 | } | 279 | } |
245 | 280 | ||
diff --git a/drivers/acpi/resources/rsdump.c b/drivers/acpi/resources/rsdump.c index 1935dab2ab51..2c3bb8c35741 100644 --- a/drivers/acpi/resources/rsdump.c +++ b/drivers/acpi/resources/rsdump.c | |||
@@ -48,6 +48,9 @@ | |||
48 | #define _COMPONENT ACPI_RESOURCES | 48 | #define _COMPONENT ACPI_RESOURCES |
49 | ACPI_MODULE_NAME ("rsdump") | 49 | ACPI_MODULE_NAME ("rsdump") |
50 | 50 | ||
51 | |||
52 | #if defined(ACPI_DEBUG_OUTPUT) || defined(ACPI_DEBUGGER) | ||
53 | |||
51 | /* Local prototypes */ | 54 | /* Local prototypes */ |
52 | 55 | ||
53 | static void | 56 | static void |
@@ -103,7 +106,6 @@ acpi_rs_dump_vendor_specific ( | |||
103 | union acpi_resource_data *data); | 106 | union acpi_resource_data *data); |
104 | 107 | ||
105 | 108 | ||
106 | #if defined(ACPI_DEBUG_OUTPUT) || defined(ACPI_DEBUGGER) | ||
107 | /******************************************************************************* | 109 | /******************************************************************************* |
108 | * | 110 | * |
109 | * FUNCTION: acpi_rs_dump_irq | 111 | * FUNCTION: acpi_rs_dump_irq |
diff --git a/drivers/acpi/tables/tbconvrt.c b/drivers/acpi/tables/tbconvrt.c index 92e0c31539be..d4ff71f5fe5d 100644 --- a/drivers/acpi/tables/tbconvrt.c +++ b/drivers/acpi/tables/tbconvrt.c | |||
@@ -97,7 +97,9 @@ acpi_tb_get_table_count ( | |||
97 | ACPI_FUNCTION_ENTRY (); | 97 | ACPI_FUNCTION_ENTRY (); |
98 | 98 | ||
99 | 99 | ||
100 | if (RSDP->revision < 2) { | 100 | /* RSDT pointers are 32 bits, XSDT pointers are 64 bits */ |
101 | |||
102 | if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { | ||
101 | pointer_size = sizeof (u32); | 103 | pointer_size = sizeof (u32); |
102 | } | 104 | } |
103 | else { | 105 | else { |
@@ -158,7 +160,9 @@ acpi_tb_convert_to_xsdt ( | |||
158 | /* Copy the table pointers */ | 160 | /* Copy the table pointers */ |
159 | 161 | ||
160 | for (i = 0; i < acpi_gbl_rsdt_table_count; i++) { | 162 | for (i = 0; i < acpi_gbl_rsdt_table_count; i++) { |
161 | if (acpi_gbl_RSDP->revision < 2) { | 163 | /* RSDT pointers are 32 bits, XSDT pointers are 64 bits */ |
164 | |||
165 | if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { | ||
162 | ACPI_STORE_ADDRESS (new_table->table_offset_entry[i], | 166 | ACPI_STORE_ADDRESS (new_table->table_offset_entry[i], |
163 | (ACPI_CAST_PTR (struct rsdt_descriptor_rev1, | 167 | (ACPI_CAST_PTR (struct rsdt_descriptor_rev1, |
164 | table_info->pointer))->table_offset_entry[i]); | 168 | table_info->pointer))->table_offset_entry[i]); |
diff --git a/drivers/acpi/tables/tbinstal.c b/drivers/acpi/tables/tbinstal.c index 629b64c8193d..698799901f55 100644 --- a/drivers/acpi/tables/tbinstal.c +++ b/drivers/acpi/tables/tbinstal.c | |||
@@ -124,9 +124,7 @@ acpi_tb_match_signature ( | |||
124 | * | 124 | * |
125 | * RETURN: Status | 125 | * RETURN: Status |
126 | * | 126 | * |
127 | * DESCRIPTION: Load and validate all tables other than the RSDT. The RSDT must | 127 | * DESCRIPTION: Install the table into the global data structures. |
128 | * already be loaded and validated. | ||
129 | * Install the table into the global data structs. | ||
130 | * | 128 | * |
131 | ******************************************************************************/ | 129 | ******************************************************************************/ |
132 | 130 | ||
@@ -136,6 +134,7 @@ acpi_tb_install_table ( | |||
136 | { | 134 | { |
137 | acpi_status status; | 135 | acpi_status status; |
138 | 136 | ||
137 | |||
139 | ACPI_FUNCTION_TRACE ("tb_install_table"); | 138 | ACPI_FUNCTION_TRACE ("tb_install_table"); |
140 | 139 | ||
141 | 140 | ||
@@ -143,22 +142,33 @@ acpi_tb_install_table ( | |||
143 | 142 | ||
144 | status = acpi_ut_acquire_mutex (ACPI_MTX_TABLES); | 143 | status = acpi_ut_acquire_mutex (ACPI_MTX_TABLES); |
145 | if (ACPI_FAILURE (status)) { | 144 | if (ACPI_FAILURE (status)) { |
146 | ACPI_REPORT_ERROR (("Could not acquire table mutex for [%4.4s], %s\n", | 145 | ACPI_REPORT_ERROR (("Could not acquire table mutex, %s\n", |
147 | table_info->pointer->signature, acpi_format_exception (status))); | 146 | acpi_format_exception (status))); |
148 | return_ACPI_STATUS (status); | 147 | return_ACPI_STATUS (status); |
149 | } | 148 | } |
150 | 149 | ||
150 | /* | ||
151 | * Ignore a table that is already installed. For example, some BIOS | ||
152 | * ASL code will repeatedly attempt to load the same SSDT. | ||
153 | */ | ||
154 | status = acpi_tb_is_table_installed (table_info); | ||
155 | if (ACPI_FAILURE (status)) { | ||
156 | goto unlock_and_exit; | ||
157 | } | ||
158 | |||
151 | /* Install the table into the global data structure */ | 159 | /* Install the table into the global data structure */ |
152 | 160 | ||
153 | status = acpi_tb_init_table_descriptor (table_info->type, table_info); | 161 | status = acpi_tb_init_table_descriptor (table_info->type, table_info); |
154 | if (ACPI_FAILURE (status)) { | 162 | if (ACPI_FAILURE (status)) { |
155 | ACPI_REPORT_ERROR (("Could not install ACPI table [%4.4s], %s\n", | 163 | ACPI_REPORT_ERROR (("Could not install table [%4.4s], %s\n", |
156 | table_info->pointer->signature, acpi_format_exception (status))); | 164 | table_info->pointer->signature, acpi_format_exception (status))); |
157 | } | 165 | } |
158 | 166 | ||
159 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "%s located at %p\n", | 167 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "%s located at %p\n", |
160 | acpi_gbl_table_data[table_info->type].name, table_info->pointer)); | 168 | acpi_gbl_table_data[table_info->type].name, table_info->pointer)); |
161 | 169 | ||
170 | |||
171 | unlock_and_exit: | ||
162 | (void) acpi_ut_release_mutex (ACPI_MTX_TABLES); | 172 | (void) acpi_ut_release_mutex (ACPI_MTX_TABLES); |
163 | return_ACPI_STATUS (status); | 173 | return_ACPI_STATUS (status); |
164 | } | 174 | } |
@@ -251,6 +261,7 @@ acpi_tb_init_table_descriptor ( | |||
251 | { | 261 | { |
252 | struct acpi_table_list *list_head; | 262 | struct acpi_table_list *list_head; |
253 | struct acpi_table_desc *table_desc; | 263 | struct acpi_table_desc *table_desc; |
264 | acpi_status status; | ||
254 | 265 | ||
255 | 266 | ||
256 | ACPI_FUNCTION_TRACE_U32 ("tb_init_table_descriptor", table_type); | 267 | ACPI_FUNCTION_TRACE_U32 ("tb_init_table_descriptor", table_type); |
@@ -263,6 +274,13 @@ acpi_tb_init_table_descriptor ( | |||
263 | return_ACPI_STATUS (AE_NO_MEMORY); | 274 | return_ACPI_STATUS (AE_NO_MEMORY); |
264 | } | 275 | } |
265 | 276 | ||
277 | /* Get a new owner ID for the table */ | ||
278 | |||
279 | status = acpi_ut_allocate_owner_id (&table_desc->owner_id); | ||
280 | if (ACPI_FAILURE (status)) { | ||
281 | return_ACPI_STATUS (status); | ||
282 | } | ||
283 | |||
266 | /* Install the table into the global data structure */ | 284 | /* Install the table into the global data structure */ |
267 | 285 | ||
268 | list_head = &acpi_gbl_table_lists[table_type]; | 286 | list_head = &acpi_gbl_table_lists[table_type]; |
@@ -325,8 +343,6 @@ acpi_tb_init_table_descriptor ( | |||
325 | table_desc->aml_start = (u8 *) (table_desc->pointer + 1), | 343 | table_desc->aml_start = (u8 *) (table_desc->pointer + 1), |
326 | table_desc->aml_length = (u32) (table_desc->length - | 344 | table_desc->aml_length = (u32) (table_desc->length - |
327 | (u32) sizeof (struct acpi_table_header)); | 345 | (u32) sizeof (struct acpi_table_header)); |
328 | table_desc->table_id = acpi_ut_allocate_owner_id ( | ||
329 | ACPI_OWNER_TYPE_TABLE); | ||
330 | table_desc->loaded_into_namespace = FALSE; | 346 | table_desc->loaded_into_namespace = FALSE; |
331 | 347 | ||
332 | /* | 348 | /* |
@@ -339,7 +355,7 @@ acpi_tb_init_table_descriptor ( | |||
339 | 355 | ||
340 | /* Return Data */ | 356 | /* Return Data */ |
341 | 357 | ||
342 | table_info->table_id = table_desc->table_id; | 358 | table_info->owner_id = table_desc->owner_id; |
343 | table_info->installed_desc = table_desc; | 359 | table_info->installed_desc = table_desc; |
344 | 360 | ||
345 | return_ACPI_STATUS (AE_OK); | 361 | return_ACPI_STATUS (AE_OK); |
diff --git a/drivers/acpi/tables/tbrsdt.c b/drivers/acpi/tables/tbrsdt.c index b7ffe39c3626..069d498465d0 100644 --- a/drivers/acpi/tables/tbrsdt.c +++ b/drivers/acpi/tables/tbrsdt.c | |||
@@ -96,32 +96,13 @@ acpi_tb_verify_rsdp ( | |||
96 | return_ACPI_STATUS (AE_BAD_PARAMETER); | 96 | return_ACPI_STATUS (AE_BAD_PARAMETER); |
97 | } | 97 | } |
98 | 98 | ||
99 | /* | 99 | /* Verify RSDP signature and checksum */ |
100 | * The signature and checksum must both be correct | ||
101 | */ | ||
102 | if (ACPI_STRNCMP ((char *) rsdp, RSDP_SIG, sizeof (RSDP_SIG)-1) != 0) { | ||
103 | /* Nope, BAD Signature */ | ||
104 | |||
105 | status = AE_BAD_SIGNATURE; | ||
106 | goto cleanup; | ||
107 | } | ||
108 | |||
109 | /* Check the standard checksum */ | ||
110 | 100 | ||
111 | if (acpi_tb_checksum (rsdp, ACPI_RSDP_CHECKSUM_LENGTH) != 0) { | 101 | status = acpi_tb_validate_rsdp (rsdp); |
112 | status = AE_BAD_CHECKSUM; | 102 | if (ACPI_FAILURE (status)) { |
113 | goto cleanup; | 103 | goto cleanup; |
114 | } | 104 | } |
115 | 105 | ||
116 | /* Check extended checksum if table version >= 2 */ | ||
117 | |||
118 | if (rsdp->revision >= 2) { | ||
119 | if (acpi_tb_checksum (rsdp, ACPI_RSDP_XCHECKSUM_LENGTH) != 0) { | ||
120 | status = AE_BAD_CHECKSUM; | ||
121 | goto cleanup; | ||
122 | } | ||
123 | } | ||
124 | |||
125 | /* The RSDP supplied is OK */ | 106 | /* The RSDP supplied is OK */ |
126 | 107 | ||
127 | table_info.pointer = ACPI_CAST_PTR (struct acpi_table_header, rsdp); | 108 | table_info.pointer = ACPI_CAST_PTR (struct acpi_table_header, rsdp); |
@@ -159,8 +140,8 @@ cleanup: | |||
159 | * | 140 | * |
160 | * RETURN: None, Address | 141 | * RETURN: None, Address |
161 | * | 142 | * |
162 | * DESCRIPTION: Extract the address of the RSDT or XSDT, depending on the | 143 | * DESCRIPTION: Extract the address of either the RSDT or XSDT, depending on the |
163 | * version of the RSDP | 144 | * version of the RSDP and whether the XSDT pointer is valid |
164 | * | 145 | * |
165 | ******************************************************************************/ | 146 | ******************************************************************************/ |
166 | 147 | ||
@@ -174,16 +155,19 @@ acpi_tb_get_rsdt_address ( | |||
174 | 155 | ||
175 | out_address->pointer_type = acpi_gbl_table_flags | ACPI_LOGICAL_ADDRESSING; | 156 | out_address->pointer_type = acpi_gbl_table_flags | ACPI_LOGICAL_ADDRESSING; |
176 | 157 | ||
177 | /* | 158 | /* Use XSDT if it is present */ |
178 | * For RSDP revision 0 or 1, we use the RSDT. | 159 | |
179 | * For RSDP revision 2 (and above), we use the XSDT | 160 | if ((acpi_gbl_RSDP->revision >= 2) && |
180 | */ | 161 | acpi_gbl_RSDP->xsdt_physical_address) { |
181 | if (acpi_gbl_RSDP->revision < 2) { | ||
182 | out_address->pointer.value = acpi_gbl_RSDP->rsdt_physical_address; | ||
183 | } | ||
184 | else { | ||
185 | out_address->pointer.value = | 162 | out_address->pointer.value = |
186 | acpi_gbl_RSDP->xsdt_physical_address; | 163 | acpi_gbl_RSDP->xsdt_physical_address; |
164 | acpi_gbl_root_table_type = ACPI_TABLE_TYPE_XSDT; | ||
165 | } | ||
166 | else { | ||
167 | /* No XSDT, use the RSDT */ | ||
168 | |||
169 | out_address->pointer.value = acpi_gbl_RSDP->rsdt_physical_address; | ||
170 | acpi_gbl_root_table_type = ACPI_TABLE_TYPE_RSDT; | ||
187 | } | 171 | } |
188 | } | 172 | } |
189 | 173 | ||
@@ -211,10 +195,9 @@ acpi_tb_validate_rsdt ( | |||
211 | 195 | ||
212 | 196 | ||
213 | /* | 197 | /* |
214 | * For RSDP revision 0 or 1, we use the RSDT. | 198 | * Search for appropriate signature, RSDT or XSDT |
215 | * For RSDP revision 2 and above, we use the XSDT | ||
216 | */ | 199 | */ |
217 | if (acpi_gbl_RSDP->revision < 2) { | 200 | if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { |
218 | no_match = ACPI_STRNCMP ((char *) table_ptr, RSDT_SIG, | 201 | no_match = ACPI_STRNCMP ((char *) table_ptr, RSDT_SIG, |
219 | sizeof (RSDT_SIG) -1); | 202 | sizeof (RSDT_SIG) -1); |
220 | } | 203 | } |
@@ -236,11 +219,11 @@ acpi_tb_validate_rsdt ( | |||
236 | acpi_gbl_RSDP->rsdt_physical_address, | 219 | acpi_gbl_RSDP->rsdt_physical_address, |
237 | (void *) (acpi_native_uint) acpi_gbl_RSDP->rsdt_physical_address)); | 220 | (void *) (acpi_native_uint) acpi_gbl_RSDP->rsdt_physical_address)); |
238 | 221 | ||
239 | if (acpi_gbl_RSDP->revision < 2) { | 222 | if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { |
240 | ACPI_REPORT_ERROR (("Looking for RSDT (RSDP->Rev < 2)\n")) | 223 | ACPI_REPORT_ERROR (("Looking for RSDT\n")) |
241 | } | 224 | } |
242 | else { | 225 | else { |
243 | ACPI_REPORT_ERROR (("Looking for XSDT (RSDP->Rev >= 2)\n")) | 226 | ACPI_REPORT_ERROR (("Looking for XSDT\n")) |
244 | } | 227 | } |
245 | 228 | ||
246 | ACPI_DUMP_BUFFER ((char *) table_ptr, 48); | 229 | ACPI_DUMP_BUFFER ((char *) table_ptr, 48); |
diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index e69d01d443d2..6fc1e36e6042 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c | |||
@@ -61,6 +61,67 @@ acpi_tb_handle_to_object ( | |||
61 | 61 | ||
62 | /******************************************************************************* | 62 | /******************************************************************************* |
63 | * | 63 | * |
64 | * FUNCTION: acpi_tb_is_table_installed | ||
65 | * | ||
66 | * PARAMETERS: new_table_desc - Descriptor for new table being installed | ||
67 | * | ||
68 | * RETURN: Status - AE_ALREADY_EXISTS if the table is already installed | ||
69 | * | ||
70 | * DESCRIPTION: Determine if an ACPI table is already installed | ||
71 | * | ||
72 | * MUTEX: Table data structures should be locked | ||
73 | * | ||
74 | ******************************************************************************/ | ||
75 | |||
76 | acpi_status | ||
77 | acpi_tb_is_table_installed ( | ||
78 | struct acpi_table_desc *new_table_desc) | ||
79 | { | ||
80 | struct acpi_table_desc *table_desc; | ||
81 | |||
82 | |||
83 | ACPI_FUNCTION_TRACE ("tb_is_table_installed"); | ||
84 | |||
85 | |||
86 | /* Get the list descriptor and first table descriptor */ | ||
87 | |||
88 | table_desc = acpi_gbl_table_lists[new_table_desc->type].next; | ||
89 | |||
90 | /* Examine all installed tables of this type */ | ||
91 | |||
92 | while (table_desc) { | ||
93 | /* Compare Revision and oem_table_id */ | ||
94 | |||
95 | if ((table_desc->loaded_into_namespace) && | ||
96 | (table_desc->pointer->revision == | ||
97 | new_table_desc->pointer->revision) && | ||
98 | (!ACPI_MEMCMP (table_desc->pointer->oem_table_id, | ||
99 | new_table_desc->pointer->oem_table_id, 8))) { | ||
100 | /* This table is already installed */ | ||
101 | |||
102 | ACPI_DEBUG_PRINT ((ACPI_DB_TABLES, | ||
103 | "Table [%4.4s] already installed: Rev %X oem_table_id [%8.8s]\n", | ||
104 | new_table_desc->pointer->signature, | ||
105 | new_table_desc->pointer->revision, | ||
106 | new_table_desc->pointer->oem_table_id)); | ||
107 | |||
108 | new_table_desc->owner_id = table_desc->owner_id; | ||
109 | new_table_desc->installed_desc = table_desc; | ||
110 | |||
111 | return_ACPI_STATUS (AE_ALREADY_EXISTS); | ||
112 | } | ||
113 | |||
114 | /* Get next table on the list */ | ||
115 | |||
116 | table_desc = table_desc->next; | ||
117 | } | ||
118 | |||
119 | return_ACPI_STATUS (AE_OK); | ||
120 | } | ||
121 | |||
122 | |||
123 | /******************************************************************************* | ||
124 | * | ||
64 | * FUNCTION: acpi_tb_validate_table_header | 125 | * FUNCTION: acpi_tb_validate_table_header |
65 | * | 126 | * |
66 | * PARAMETERS: table_header - Logical pointer to the table | 127 | * PARAMETERS: table_header - Logical pointer to the table |
@@ -157,7 +218,7 @@ acpi_tb_verify_table_checksum ( | |||
157 | 218 | ||
158 | /* Compute the checksum on the table */ | 219 | /* Compute the checksum on the table */ |
159 | 220 | ||
160 | checksum = acpi_tb_checksum (table_header, table_header->length); | 221 | checksum = acpi_tb_generate_checksum (table_header, table_header->length); |
161 | 222 | ||
162 | /* Return the appropriate exception */ | 223 | /* Return the appropriate exception */ |
163 | 224 | ||
@@ -175,7 +236,7 @@ acpi_tb_verify_table_checksum ( | |||
175 | 236 | ||
176 | /******************************************************************************* | 237 | /******************************************************************************* |
177 | * | 238 | * |
178 | * FUNCTION: acpi_tb_checksum | 239 | * FUNCTION: acpi_tb_generate_checksum |
179 | * | 240 | * |
180 | * PARAMETERS: Buffer - Buffer to checksum | 241 | * PARAMETERS: Buffer - Buffer to checksum |
181 | * Length - Size of the buffer | 242 | * Length - Size of the buffer |
@@ -187,7 +248,7 @@ acpi_tb_verify_table_checksum ( | |||
187 | ******************************************************************************/ | 248 | ******************************************************************************/ |
188 | 249 | ||
189 | u8 | 250 | u8 |
190 | acpi_tb_checksum ( | 251 | acpi_tb_generate_checksum ( |
191 | void *buffer, | 252 | void *buffer, |
192 | u32 length) | 253 | u32 length) |
193 | { | 254 | { |
diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 0c0b9085dbeb..e18a05d1b9b3 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c | |||
@@ -182,10 +182,23 @@ acpi_load_table ( | |||
182 | return_ACPI_STATUS (status); | 182 | return_ACPI_STATUS (status); |
183 | } | 183 | } |
184 | 184 | ||
185 | /* Check signature for a valid table type */ | ||
186 | |||
187 | status = acpi_tb_recognize_table (&table_info, ACPI_TABLE_ALL); | ||
188 | if (ACPI_FAILURE (status)) { | ||
189 | return_ACPI_STATUS (status); | ||
190 | } | ||
191 | |||
185 | /* Install the new table into the local data structures */ | 192 | /* Install the new table into the local data structures */ |
186 | 193 | ||
187 | status = acpi_tb_install_table (&table_info); | 194 | status = acpi_tb_install_table (&table_info); |
188 | if (ACPI_FAILURE (status)) { | 195 | if (ACPI_FAILURE (status)) { |
196 | if (status == AE_ALREADY_EXISTS) { | ||
197 | /* Table already exists, no error */ | ||
198 | |||
199 | status = AE_OK; | ||
200 | } | ||
201 | |||
189 | /* Free table allocated by acpi_tb_get_table_body */ | 202 | /* Free table allocated by acpi_tb_get_table_body */ |
190 | 203 | ||
191 | acpi_tb_delete_single_table (&table_info); | 204 | acpi_tb_delete_single_table (&table_info); |
@@ -260,8 +273,8 @@ acpi_unload_table ( | |||
260 | * "Scope" operator. Thus, we need to track ownership by an ID, not | 273 | * "Scope" operator. Thus, we need to track ownership by an ID, not |
261 | * simply a position within the hierarchy | 274 | * simply a position within the hierarchy |
262 | */ | 275 | */ |
263 | acpi_ns_delete_namespace_by_owner (table_desc->table_id); | 276 | acpi_ns_delete_namespace_by_owner (table_desc->owner_id); |
264 | 277 | acpi_ut_release_owner_id (&table_desc->owner_id); | |
265 | table_desc = table_desc->next; | 278 | table_desc = table_desc->next; |
266 | } | 279 | } |
267 | 280 | ||
diff --git a/drivers/acpi/tables/tbxfroot.c b/drivers/acpi/tables/tbxfroot.c index dc3c3f6a9f62..87dccdda9ae2 100644 --- a/drivers/acpi/tables/tbxfroot.c +++ b/drivers/acpi/tables/tbxfroot.c | |||
@@ -65,6 +65,51 @@ acpi_tb_scan_memory_for_rsdp ( | |||
65 | 65 | ||
66 | /******************************************************************************* | 66 | /******************************************************************************* |
67 | * | 67 | * |
68 | * FUNCTION: acpi_tb_validate_rsdp | ||
69 | * | ||
70 | * PARAMETERS: Rsdp - Pointer to unvalidated RSDP | ||
71 | * | ||
72 | * RETURN: Status | ||
73 | * | ||
74 | * DESCRIPTION: Validate the RSDP (ptr) | ||
75 | * | ||
76 | ******************************************************************************/ | ||
77 | |||
78 | acpi_status | ||
79 | acpi_tb_validate_rsdp ( | ||
80 | struct rsdp_descriptor *rsdp) | ||
81 | { | ||
82 | ACPI_FUNCTION_ENTRY (); | ||
83 | |||
84 | |||
85 | /* | ||
86 | * The signature and checksum must both be correct | ||
87 | */ | ||
88 | if (ACPI_STRNCMP ((char *) rsdp, RSDP_SIG, sizeof (RSDP_SIG)-1) != 0) { | ||
89 | /* Nope, BAD Signature */ | ||
90 | |||
91 | return (AE_BAD_SIGNATURE); | ||
92 | } | ||
93 | |||
94 | /* Check the standard checksum */ | ||
95 | |||
96 | if (acpi_tb_generate_checksum (rsdp, ACPI_RSDP_CHECKSUM_LENGTH) != 0) { | ||
97 | return (AE_BAD_CHECKSUM); | ||
98 | } | ||
99 | |||
100 | /* Check extended checksum if table version >= 2 */ | ||
101 | |||
102 | if ((rsdp->revision >= 2) && | ||
103 | (acpi_tb_generate_checksum (rsdp, ACPI_RSDP_XCHECKSUM_LENGTH) != 0)) { | ||
104 | return (AE_BAD_CHECKSUM); | ||
105 | } | ||
106 | |||
107 | return (AE_OK); | ||
108 | } | ||
109 | |||
110 | |||
111 | /******************************************************************************* | ||
112 | * | ||
68 | * FUNCTION: acpi_tb_find_table | 113 | * FUNCTION: acpi_tb_find_table |
69 | * | 114 | * |
70 | * PARAMETERS: Signature - String with ACPI table signature | 115 | * PARAMETERS: Signature - String with ACPI table signature |
@@ -218,19 +263,11 @@ acpi_get_firmware_table ( | |||
218 | acpi_gbl_RSDP = address.pointer.logical; | 263 | acpi_gbl_RSDP = address.pointer.logical; |
219 | } | 264 | } |
220 | 265 | ||
221 | /* The signature and checksum must both be correct */ | 266 | /* The RDSP signature and checksum must both be correct */ |
222 | |||
223 | if (ACPI_STRNCMP ((char *) acpi_gbl_RSDP, RSDP_SIG, | ||
224 | sizeof (RSDP_SIG)-1) != 0) { | ||
225 | /* Nope, BAD Signature */ | ||
226 | |||
227 | return_ACPI_STATUS (AE_BAD_SIGNATURE); | ||
228 | } | ||
229 | |||
230 | if (acpi_tb_checksum (acpi_gbl_RSDP, ACPI_RSDP_CHECKSUM_LENGTH) != 0) { | ||
231 | /* Nope, BAD Checksum */ | ||
232 | 267 | ||
233 | return_ACPI_STATUS (AE_BAD_CHECKSUM); | 268 | status = acpi_tb_validate_rsdp (acpi_gbl_RSDP); |
269 | if (ACPI_FAILURE (status)) { | ||
270 | return_ACPI_STATUS (status); | ||
234 | } | 271 | } |
235 | } | 272 | } |
236 | 273 | ||
@@ -287,9 +324,11 @@ acpi_get_firmware_table ( | |||
287 | * requested table | 324 | * requested table |
288 | */ | 325 | */ |
289 | for (i = 0, j = 0; i < table_count; i++) { | 326 | for (i = 0, j = 0; i < table_count; i++) { |
290 | /* Get the next table pointer, handle RSDT vs. XSDT */ | 327 | /* |
291 | 328 | * Get the next table pointer, handle RSDT vs. XSDT | |
292 | if (acpi_gbl_RSDP->revision < 2) { | 329 | * RSDT pointers are 32 bits, XSDT pointers are 64 bits |
330 | */ | ||
331 | if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { | ||
293 | address.pointer.value = (ACPI_CAST_PTR ( | 332 | address.pointer.value = (ACPI_CAST_PTR ( |
294 | RSDT_DESCRIPTOR, rsdt_info->pointer))->table_offset_entry[i]; | 333 | RSDT_DESCRIPTOR, rsdt_info->pointer))->table_offset_entry[i]; |
295 | } | 334 | } |
@@ -331,8 +370,10 @@ acpi_get_firmware_table ( | |||
331 | 370 | ||
332 | 371 | ||
333 | cleanup: | 372 | cleanup: |
334 | acpi_os_unmap_memory (rsdt_info->pointer, | 373 | if (rsdt_info->pointer) { |
335 | (acpi_size) rsdt_info->pointer->length); | 374 | acpi_os_unmap_memory (rsdt_info->pointer, |
375 | (acpi_size) rsdt_info->pointer->length); | ||
376 | } | ||
336 | ACPI_MEM_FREE (rsdt_info); | 377 | ACPI_MEM_FREE (rsdt_info); |
337 | 378 | ||
338 | if (header) { | 379 | if (header) { |
@@ -410,9 +451,9 @@ acpi_tb_scan_memory_for_rsdp ( | |||
410 | u8 *start_address, | 451 | u8 *start_address, |
411 | u32 length) | 452 | u32 length) |
412 | { | 453 | { |
454 | acpi_status status; | ||
413 | u8 *mem_rover; | 455 | u8 *mem_rover; |
414 | u8 *end_address; | 456 | u8 *end_address; |
415 | u8 checksum; | ||
416 | 457 | ||
417 | 458 | ||
418 | ACPI_FUNCTION_TRACE ("tb_scan_memory_for_rsdp"); | 459 | ACPI_FUNCTION_TRACE ("tb_scan_memory_for_rsdp"); |
@@ -424,45 +465,25 @@ acpi_tb_scan_memory_for_rsdp ( | |||
424 | 465 | ||
425 | for (mem_rover = start_address; mem_rover < end_address; | 466 | for (mem_rover = start_address; mem_rover < end_address; |
426 | mem_rover += ACPI_RSDP_SCAN_STEP) { | 467 | mem_rover += ACPI_RSDP_SCAN_STEP) { |
427 | /* The signature and checksum must both be correct */ | 468 | /* The RSDP signature and checksum must both be correct */ |
428 | |||
429 | if (ACPI_STRNCMP ((char *) mem_rover, | ||
430 | RSDP_SIG, sizeof (RSDP_SIG) - 1) != 0) { | ||
431 | /* No signature match, keep looking */ | ||
432 | |||
433 | continue; | ||
434 | } | ||
435 | |||
436 | /* Signature matches, check the appropriate checksum */ | ||
437 | |||
438 | if ((ACPI_CAST_PTR (struct rsdp_descriptor, mem_rover))->revision < 2) { | ||
439 | /* ACPI version 1.0 */ | ||
440 | 469 | ||
441 | checksum = acpi_tb_checksum (mem_rover, ACPI_RSDP_CHECKSUM_LENGTH); | 470 | status = acpi_tb_validate_rsdp (ACPI_CAST_PTR (struct rsdp_descriptor, mem_rover)); |
442 | } | 471 | if (ACPI_SUCCESS (status)) { |
443 | else { | 472 | /* Sig and checksum valid, we have found a real RSDP */ |
444 | /* Post ACPI 1.0, use extended_checksum */ | ||
445 | |||
446 | checksum = acpi_tb_checksum (mem_rover, ACPI_RSDP_XCHECKSUM_LENGTH); | ||
447 | } | ||
448 | |||
449 | if (checksum == 0) { | ||
450 | /* Checksum valid, we have found a valid RSDP */ | ||
451 | 473 | ||
452 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, | 474 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, |
453 | "RSDP located at physical address %p\n", mem_rover)); | 475 | "RSDP located at physical address %p\n", mem_rover)); |
454 | return_PTR (mem_rover); | 476 | return_PTR (mem_rover); |
455 | } | 477 | } |
456 | 478 | ||
457 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, | 479 | /* No sig match or bad checksum, keep searching */ |
458 | "Found an RSDP at physical address %p, but it has a bad checksum\n", | ||
459 | mem_rover)); | ||
460 | } | 480 | } |
461 | 481 | ||
462 | /* Searched entire block, no RSDP was found */ | 482 | /* Searched entire block, no RSDP was found */ |
463 | 483 | ||
464 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, | 484 | ACPI_DEBUG_PRINT ((ACPI_DB_INFO, |
465 | "Searched entire block, no valid RSDP was found.\n")); | 485 | "Searched entire block from %p, valid RSDP was not found\n", |
486 | start_address)); | ||
466 | return_PTR (NULL); | 487 | return_PTR (NULL); |
467 | } | 488 | } |
468 | 489 | ||
@@ -550,7 +571,7 @@ acpi_tb_find_rsdp ( | |||
550 | acpi_os_unmap_memory (table_ptr, ACPI_EBDA_WINDOW_SIZE); | 571 | acpi_os_unmap_memory (table_ptr, ACPI_EBDA_WINDOW_SIZE); |
551 | 572 | ||
552 | if (mem_rover) { | 573 | if (mem_rover) { |
553 | /* Found it, return the physical address */ | 574 | /* Return the physical address */ |
554 | 575 | ||
555 | physical_address += ACPI_PTR_DIFF (mem_rover, table_ptr); | 576 | physical_address += ACPI_PTR_DIFF (mem_rover, table_ptr); |
556 | 577 | ||
@@ -579,7 +600,7 @@ acpi_tb_find_rsdp ( | |||
579 | acpi_os_unmap_memory (table_ptr, ACPI_HI_RSDP_WINDOW_SIZE); | 600 | acpi_os_unmap_memory (table_ptr, ACPI_HI_RSDP_WINDOW_SIZE); |
580 | 601 | ||
581 | if (mem_rover) { | 602 | if (mem_rover) { |
582 | /* Found it, return the physical address */ | 603 | /* Return the physical address */ |
583 | 604 | ||
584 | physical_address = | 605 | physical_address = |
585 | ACPI_HI_RSDP_WINDOW_BASE + ACPI_PTR_DIFF (mem_rover, table_ptr); | 606 | ACPI_HI_RSDP_WINDOW_BASE + ACPI_PTR_DIFF (mem_rover, table_ptr); |
@@ -610,7 +631,7 @@ acpi_tb_find_rsdp ( | |||
610 | ACPI_PHYSADDR_TO_PTR (physical_address), | 631 | ACPI_PHYSADDR_TO_PTR (physical_address), |
611 | ACPI_EBDA_WINDOW_SIZE); | 632 | ACPI_EBDA_WINDOW_SIZE); |
612 | if (mem_rover) { | 633 | if (mem_rover) { |
613 | /* Found it, return the physical address */ | 634 | /* Return the physical address */ |
614 | 635 | ||
615 | table_info->physical_address = ACPI_TO_INTEGER (mem_rover); | 636 | table_info->physical_address = ACPI_TO_INTEGER (mem_rover); |
616 | return_ACPI_STATUS (AE_OK); | 637 | return_ACPI_STATUS (AE_OK); |
@@ -630,8 +651,9 @@ acpi_tb_find_rsdp ( | |||
630 | } | 651 | } |
631 | } | 652 | } |
632 | 653 | ||
633 | /* RSDP signature was not found */ | 654 | /* A valid RSDP was not found */ |
634 | 655 | ||
656 | ACPI_REPORT_ERROR (("No valid RSDP was found\n")); | ||
635 | return_ACPI_STATUS (AE_NOT_FOUND); | 657 | return_ACPI_STATUS (AE_NOT_FOUND); |
636 | } | 658 | } |
637 | 659 | ||
diff --git a/drivers/acpi/utilities/Makefile b/drivers/acpi/utilities/Makefile index 939c447dd52a..e87108b7338a 100644 --- a/drivers/acpi/utilities/Makefile +++ b/drivers/acpi/utilities/Makefile | |||
@@ -3,6 +3,6 @@ | |||
3 | # | 3 | # |
4 | 4 | ||
5 | obj-y := utalloc.o utdebug.o uteval.o utinit.o utmisc.o utxface.o \ | 5 | obj-y := utalloc.o utdebug.o uteval.o utinit.o utmisc.o utxface.o \ |
6 | utcopy.o utdelete.o utglobal.o utmath.o utobject.o | 6 | utcopy.o utdelete.o utglobal.o utmath.o utobject.o utstate.o utmutex.o utobject.o utcache.o |
7 | 7 | ||
8 | EXTRA_CFLAGS += $(ACPI_CFLAGS) | 8 | EXTRA_CFLAGS += $(ACPI_CFLAGS) |
diff --git a/drivers/acpi/utilities/utalloc.c b/drivers/acpi/utilities/utalloc.c index c4e7f989a2bd..78270f50e625 100644 --- a/drivers/acpi/utilities/utalloc.c +++ b/drivers/acpi/utilities/utalloc.c | |||
@@ -1,6 +1,6 @@ | |||
1 | /****************************************************************************** | 1 | /****************************************************************************** |
2 | * | 2 | * |
3 | * Module Name: utalloc - local cache and memory allocation routines | 3 | * Module Name: utalloc - local memory allocation routines |
4 | * | 4 | * |
5 | *****************************************************************************/ | 5 | *****************************************************************************/ |
6 | 6 | ||
@@ -52,12 +52,10 @@ | |||
52 | #ifdef ACPI_DBG_TRACK_ALLOCATIONS | 52 | #ifdef ACPI_DBG_TRACK_ALLOCATIONS |
53 | static struct acpi_debug_mem_block * | 53 | static struct acpi_debug_mem_block * |
54 | acpi_ut_find_allocation ( | 54 | acpi_ut_find_allocation ( |
55 | u32 list_id, | ||
56 | void *allocation); | 55 | void *allocation); |
57 | 56 | ||
58 | static acpi_status | 57 | static acpi_status |
59 | acpi_ut_track_allocation ( | 58 | acpi_ut_track_allocation ( |
60 | u32 list_id, | ||
61 | struct acpi_debug_mem_block *address, | 59 | struct acpi_debug_mem_block *address, |
62 | acpi_size size, | 60 | acpi_size size, |
63 | u8 alloc_type, | 61 | u8 alloc_type, |
@@ -67,206 +65,118 @@ acpi_ut_track_allocation ( | |||
67 | 65 | ||
68 | static acpi_status | 66 | static acpi_status |
69 | acpi_ut_remove_allocation ( | 67 | acpi_ut_remove_allocation ( |
70 | u32 list_id, | ||
71 | struct acpi_debug_mem_block *address, | 68 | struct acpi_debug_mem_block *address, |
72 | u32 component, | 69 | u32 component, |
73 | char *module, | 70 | char *module, |
74 | u32 line); | 71 | u32 line); |
75 | #endif /* ACPI_DBG_TRACK_ALLOCATIONS */ | 72 | #endif /* ACPI_DBG_TRACK_ALLOCATIONS */ |
76 | 73 | ||
77 | 74 | #ifdef ACPI_DBG_TRACK_ALLOCATIONS | |
78 | /******************************************************************************* | 75 | static acpi_status |
79 | * | 76 | acpi_ut_create_list ( |
80 | * FUNCTION: acpi_ut_release_to_cache | 77 | char *list_name, |
81 | * | 78 | u16 object_size, |
82 | * PARAMETERS: list_id - Memory list/cache ID | 79 | struct acpi_memory_list **return_cache); |
83 | * Object - The object to be released | ||
84 | * | ||
85 | * RETURN: None | ||
86 | * | ||
87 | * DESCRIPTION: Release an object to the specified cache. If cache is full, | ||
88 | * the object is deleted. | ||
89 | * | ||
90 | ******************************************************************************/ | ||
91 | |||
92 | void | ||
93 | acpi_ut_release_to_cache ( | ||
94 | u32 list_id, | ||
95 | void *object) | ||
96 | { | ||
97 | struct acpi_memory_list *cache_info; | ||
98 | |||
99 | |||
100 | ACPI_FUNCTION_ENTRY (); | ||
101 | |||
102 | |||
103 | cache_info = &acpi_gbl_memory_lists[list_id]; | ||
104 | |||
105 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
106 | |||
107 | /* If walk cache is full, just free this wallkstate object */ | ||
108 | |||
109 | if (cache_info->cache_depth >= cache_info->max_cache_depth) { | ||
110 | ACPI_MEM_FREE (object); | ||
111 | ACPI_MEM_TRACKING (cache_info->total_freed++); | ||
112 | } | ||
113 | |||
114 | /* Otherwise put this object back into the cache */ | ||
115 | |||
116 | else { | ||
117 | if (ACPI_FAILURE (acpi_ut_acquire_mutex (ACPI_MTX_CACHES))) { | ||
118 | return; | ||
119 | } | ||
120 | |||
121 | /* Mark the object as cached */ | ||
122 | |||
123 | ACPI_MEMSET (object, 0xCA, cache_info->object_size); | ||
124 | ACPI_SET_DESCRIPTOR_TYPE (object, ACPI_DESC_TYPE_CACHED); | ||
125 | |||
126 | /* Put the object at the head of the cache list */ | ||
127 | |||
128 | * (ACPI_CAST_INDIRECT_PTR (char, | ||
129 | &(((char *) object)[cache_info->link_offset]))) = cache_info->list_head; | ||
130 | cache_info->list_head = object; | ||
131 | cache_info->cache_depth++; | ||
132 | |||
133 | (void) acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
134 | } | ||
135 | |||
136 | #else | ||
137 | |||
138 | /* Object cache is disabled; just free the object */ | ||
139 | |||
140 | ACPI_MEM_FREE (object); | ||
141 | ACPI_MEM_TRACKING (cache_info->total_freed++); | ||
142 | #endif | 80 | #endif |
143 | } | ||
144 | 81 | ||
145 | 82 | ||
146 | /******************************************************************************* | 83 | /******************************************************************************* |
147 | * | 84 | * |
148 | * FUNCTION: acpi_ut_acquire_from_cache | 85 | * FUNCTION: acpi_ut_create_caches |
149 | * | 86 | * |
150 | * PARAMETERS: list_id - Memory list ID | 87 | * PARAMETERS: None |
151 | * | 88 | * |
152 | * RETURN: A requested object. NULL if the object could not be | 89 | * RETURN: Status |
153 | * allocated. | ||
154 | * | 90 | * |
155 | * DESCRIPTION: Get an object from the specified cache. If cache is empty, | 91 | * DESCRIPTION: Create all local caches |
156 | * the object is allocated. | ||
157 | * | 92 | * |
158 | ******************************************************************************/ | 93 | ******************************************************************************/ |
159 | 94 | ||
160 | void * | 95 | acpi_status |
161 | acpi_ut_acquire_from_cache ( | 96 | acpi_ut_create_caches ( |
162 | u32 list_id) | 97 | void) |
163 | { | 98 | { |
164 | struct acpi_memory_list *cache_info; | 99 | acpi_status status; |
165 | void *object; | ||
166 | |||
167 | |||
168 | ACPI_FUNCTION_NAME ("ut_acquire_from_cache"); | ||
169 | 100 | ||
170 | 101 | ||
171 | cache_info = &acpi_gbl_memory_lists[list_id]; | 102 | #ifdef ACPI_DBG_TRACK_ALLOCATIONS |
172 | 103 | ||
173 | #ifdef ACPI_ENABLE_OBJECT_CACHE | 104 | /* Memory allocation lists */ |
174 | 105 | ||
175 | if (ACPI_FAILURE (acpi_ut_acquire_mutex (ACPI_MTX_CACHES))) { | 106 | status = acpi_ut_create_list ("Acpi-Global", 0, |
176 | return (NULL); | 107 | &acpi_gbl_global_list); |
108 | if (ACPI_FAILURE (status)) { | ||
109 | return (status); | ||
177 | } | 110 | } |
178 | 111 | ||
179 | ACPI_MEM_TRACKING (cache_info->cache_requests++); | 112 | status = acpi_ut_create_list ("Acpi-Namespace", sizeof (struct acpi_namespace_node), |
180 | 113 | &acpi_gbl_ns_node_list); | |
181 | /* Check the cache first */ | 114 | if (ACPI_FAILURE (status)) { |
182 | 115 | return (status); | |
183 | if (cache_info->list_head) { | 116 | } |
184 | /* There is an object available, use it */ | ||
185 | |||
186 | object = cache_info->list_head; | ||
187 | cache_info->list_head = *(ACPI_CAST_INDIRECT_PTR (char, | ||
188 | &(((char *) object)[cache_info->link_offset]))); | ||
189 | |||
190 | ACPI_MEM_TRACKING (cache_info->cache_hits++); | ||
191 | cache_info->cache_depth--; | ||
192 | |||
193 | #ifdef ACPI_DBG_TRACK_ALLOCATIONS | ||
194 | ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Object %p from %s\n", | ||
195 | object, acpi_gbl_memory_lists[list_id].list_name)); | ||
196 | #endif | 117 | #endif |
197 | 118 | ||
198 | if (ACPI_FAILURE (acpi_ut_release_mutex (ACPI_MTX_CACHES))) { | 119 | /* Object Caches, for frequently used objects */ |
199 | return (NULL); | ||
200 | } | ||
201 | |||
202 | /* Clear (zero) the previously used Object */ | ||
203 | 120 | ||
204 | ACPI_MEMSET (object, 0, cache_info->object_size); | 121 | status = acpi_os_create_cache ("acpi_state", sizeof (union acpi_generic_state), |
122 | ACPI_MAX_STATE_CACHE_DEPTH, &acpi_gbl_state_cache); | ||
123 | if (ACPI_FAILURE (status)) { | ||
124 | return (status); | ||
205 | } | 125 | } |
206 | 126 | ||
207 | else { | 127 | status = acpi_os_create_cache ("acpi_parse", sizeof (struct acpi_parse_obj_common), |
208 | /* The cache is empty, create a new object */ | 128 | ACPI_MAX_PARSE_CACHE_DEPTH, &acpi_gbl_ps_node_cache); |
209 | 129 | if (ACPI_FAILURE (status)) { | |
210 | /* Avoid deadlock with ACPI_MEM_CALLOCATE */ | 130 | return (status); |
211 | |||
212 | if (ACPI_FAILURE (acpi_ut_release_mutex (ACPI_MTX_CACHES))) { | ||
213 | return (NULL); | ||
214 | } | ||
215 | |||
216 | object = ACPI_MEM_CALLOCATE (cache_info->object_size); | ||
217 | ACPI_MEM_TRACKING (cache_info->total_allocated++); | ||
218 | } | 131 | } |
219 | 132 | ||
220 | #else | 133 | status = acpi_os_create_cache ("acpi_parse_ext", sizeof (struct acpi_parse_obj_named), |
221 | 134 | ACPI_MAX_EXTPARSE_CACHE_DEPTH, &acpi_gbl_ps_node_ext_cache); | |
222 | /* Object cache is disabled; just allocate the object */ | 135 | if (ACPI_FAILURE (status)) { |
136 | return (status); | ||
137 | } | ||
223 | 138 | ||
224 | object = ACPI_MEM_CALLOCATE (cache_info->object_size); | 139 | status = acpi_os_create_cache ("acpi_operand", sizeof (union acpi_operand_object), |
225 | ACPI_MEM_TRACKING (cache_info->total_allocated++); | 140 | ACPI_MAX_OBJECT_CACHE_DEPTH, &acpi_gbl_operand_cache); |
226 | #endif | 141 | if (ACPI_FAILURE (status)) { |
142 | return (status); | ||
143 | } | ||
227 | 144 | ||
228 | return (object); | 145 | return (AE_OK); |
229 | } | 146 | } |
230 | 147 | ||
231 | 148 | ||
232 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
233 | /******************************************************************************* | 149 | /******************************************************************************* |
234 | * | 150 | * |
235 | * FUNCTION: acpi_ut_delete_generic_cache | 151 | * FUNCTION: acpi_ut_delete_caches |
236 | * | 152 | * |
237 | * PARAMETERS: list_id - Memory list ID | 153 | * PARAMETERS: None |
238 | * | 154 | * |
239 | * RETURN: None | 155 | * RETURN: Status |
240 | * | 156 | * |
241 | * DESCRIPTION: Free all objects within the requested cache. | 157 | * DESCRIPTION: Purge and delete all local caches |
242 | * | 158 | * |
243 | ******************************************************************************/ | 159 | ******************************************************************************/ |
244 | 160 | ||
245 | void | 161 | acpi_status |
246 | acpi_ut_delete_generic_cache ( | 162 | acpi_ut_delete_caches ( |
247 | u32 list_id) | 163 | void) |
248 | { | 164 | { |
249 | struct acpi_memory_list *cache_info; | ||
250 | char *next; | ||
251 | 165 | ||
166 | (void) acpi_os_delete_cache (acpi_gbl_state_cache); | ||
167 | acpi_gbl_state_cache = NULL; | ||
252 | 168 | ||
253 | ACPI_FUNCTION_ENTRY (); | 169 | (void) acpi_os_delete_cache (acpi_gbl_operand_cache); |
254 | 170 | acpi_gbl_operand_cache = NULL; | |
255 | 171 | ||
256 | cache_info = &acpi_gbl_memory_lists[list_id]; | 172 | (void) acpi_os_delete_cache (acpi_gbl_ps_node_cache); |
257 | while (cache_info->list_head) { | 173 | acpi_gbl_ps_node_cache = NULL; |
258 | /* Delete one cached state object */ | ||
259 | 174 | ||
260 | next = *(ACPI_CAST_INDIRECT_PTR (char, | 175 | (void) acpi_os_delete_cache (acpi_gbl_ps_node_ext_cache); |
261 | &(((char *) cache_info->list_head)[cache_info->link_offset]))); | 176 | acpi_gbl_ps_node_ext_cache = NULL; |
262 | ACPI_MEM_FREE (cache_info->list_head); | ||
263 | 177 | ||
264 | cache_info->list_head = next; | 178 | return (AE_OK); |
265 | cache_info->cache_depth--; | ||
266 | } | ||
267 | } | 179 | } |
268 | #endif | ||
269 | |||
270 | 180 | ||
271 | /******************************************************************************* | 181 | /******************************************************************************* |
272 | * | 182 | * |
@@ -500,6 +410,43 @@ acpi_ut_callocate ( | |||
500 | * occurs in the body of acpi_ut_free. | 410 | * occurs in the body of acpi_ut_free. |
501 | */ | 411 | */ |
502 | 412 | ||
413 | /******************************************************************************* | ||
414 | * | ||
415 | * FUNCTION: acpi_ut_create_list | ||
416 | * | ||
417 | * PARAMETERS: cache_name - Ascii name for the cache | ||
418 | * object_size - Size of each cached object | ||
419 | * return_cache - Where the new cache object is returned | ||
420 | * | ||
421 | * RETURN: Status | ||
422 | * | ||
423 | * DESCRIPTION: Create a local memory list for tracking purposed | ||
424 | * | ||
425 | ******************************************************************************/ | ||
426 | |||
427 | static acpi_status | ||
428 | acpi_ut_create_list ( | ||
429 | char *list_name, | ||
430 | u16 object_size, | ||
431 | struct acpi_memory_list **return_cache) | ||
432 | { | ||
433 | struct acpi_memory_list *cache; | ||
434 | |||
435 | |||
436 | cache = acpi_os_allocate (sizeof (struct acpi_memory_list)); | ||
437 | if (!cache) { | ||
438 | return (AE_NO_MEMORY); | ||
439 | } | ||
440 | |||
441 | ACPI_MEMSET (cache, 0, sizeof (struct acpi_memory_list)); | ||
442 | |||
443 | cache->list_name = list_name; | ||
444 | cache->object_size = object_size; | ||
445 | |||
446 | *return_cache = cache; | ||
447 | return (AE_OK); | ||
448 | } | ||
449 | |||
503 | 450 | ||
504 | /******************************************************************************* | 451 | /******************************************************************************* |
505 | * | 452 | * |
@@ -533,15 +480,15 @@ acpi_ut_allocate_and_track ( | |||
533 | return (NULL); | 480 | return (NULL); |
534 | } | 481 | } |
535 | 482 | ||
536 | status = acpi_ut_track_allocation (ACPI_MEM_LIST_GLOBAL, allocation, size, | 483 | status = acpi_ut_track_allocation (allocation, size, |
537 | ACPI_MEM_MALLOC, component, module, line); | 484 | ACPI_MEM_MALLOC, component, module, line); |
538 | if (ACPI_FAILURE (status)) { | 485 | if (ACPI_FAILURE (status)) { |
539 | acpi_os_free (allocation); | 486 | acpi_os_free (allocation); |
540 | return (NULL); | 487 | return (NULL); |
541 | } | 488 | } |
542 | 489 | ||
543 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].total_allocated++; | 490 | acpi_gbl_global_list->total_allocated++; |
544 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].current_total_size += (u32) size; | 491 | acpi_gbl_global_list->current_total_size += (u32) size; |
545 | 492 | ||
546 | return ((void *) &allocation->user_space); | 493 | return ((void *) &allocation->user_space); |
547 | } | 494 | } |
@@ -583,15 +530,15 @@ acpi_ut_callocate_and_track ( | |||
583 | return (NULL); | 530 | return (NULL); |
584 | } | 531 | } |
585 | 532 | ||
586 | status = acpi_ut_track_allocation (ACPI_MEM_LIST_GLOBAL, allocation, size, | 533 | status = acpi_ut_track_allocation (allocation, size, |
587 | ACPI_MEM_CALLOC, component, module, line); | 534 | ACPI_MEM_CALLOC, component, module, line); |
588 | if (ACPI_FAILURE (status)) { | 535 | if (ACPI_FAILURE (status)) { |
589 | acpi_os_free (allocation); | 536 | acpi_os_free (allocation); |
590 | return (NULL); | 537 | return (NULL); |
591 | } | 538 | } |
592 | 539 | ||
593 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].total_allocated++; | 540 | acpi_gbl_global_list->total_allocated++; |
594 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].current_total_size += (u32) size; | 541 | acpi_gbl_global_list->current_total_size += (u32) size; |
595 | 542 | ||
596 | return ((void *) &allocation->user_space); | 543 | return ((void *) &allocation->user_space); |
597 | } | 544 | } |
@@ -636,10 +583,10 @@ acpi_ut_free_and_track ( | |||
636 | debug_block = ACPI_CAST_PTR (struct acpi_debug_mem_block, | 583 | debug_block = ACPI_CAST_PTR (struct acpi_debug_mem_block, |
637 | (((char *) allocation) - sizeof (struct acpi_debug_mem_header))); | 584 | (((char *) allocation) - sizeof (struct acpi_debug_mem_header))); |
638 | 585 | ||
639 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].total_freed++; | 586 | acpi_gbl_global_list->total_freed++; |
640 | acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].current_total_size -= debug_block->size; | 587 | acpi_gbl_global_list->current_total_size -= debug_block->size; |
641 | 588 | ||
642 | status = acpi_ut_remove_allocation (ACPI_MEM_LIST_GLOBAL, debug_block, | 589 | status = acpi_ut_remove_allocation (debug_block, |
643 | component, module, line); | 590 | component, module, line); |
644 | if (ACPI_FAILURE (status)) { | 591 | if (ACPI_FAILURE (status)) { |
645 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Could not free memory, %s\n", | 592 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Could not free memory, %s\n", |
@@ -658,8 +605,7 @@ acpi_ut_free_and_track ( | |||
658 | * | 605 | * |
659 | * FUNCTION: acpi_ut_find_allocation | 606 | * FUNCTION: acpi_ut_find_allocation |
660 | * | 607 | * |
661 | * PARAMETERS: list_id - Memory list to search | 608 | * PARAMETERS: Allocation - Address of allocated memory |
662 | * Allocation - Address of allocated memory | ||
663 | * | 609 | * |
664 | * RETURN: A list element if found; NULL otherwise. | 610 | * RETURN: A list element if found; NULL otherwise. |
665 | * | 611 | * |
@@ -669,7 +615,6 @@ acpi_ut_free_and_track ( | |||
669 | 615 | ||
670 | static struct acpi_debug_mem_block * | 616 | static struct acpi_debug_mem_block * |
671 | acpi_ut_find_allocation ( | 617 | acpi_ut_find_allocation ( |
672 | u32 list_id, | ||
673 | void *allocation) | 618 | void *allocation) |
674 | { | 619 | { |
675 | struct acpi_debug_mem_block *element; | 620 | struct acpi_debug_mem_block *element; |
@@ -678,11 +623,7 @@ acpi_ut_find_allocation ( | |||
678 | ACPI_FUNCTION_ENTRY (); | 623 | ACPI_FUNCTION_ENTRY (); |
679 | 624 | ||
680 | 625 | ||
681 | if (list_id > ACPI_MEM_LIST_MAX) { | 626 | element = acpi_gbl_global_list->list_head; |
682 | return (NULL); | ||
683 | } | ||
684 | |||
685 | element = acpi_gbl_memory_lists[list_id].list_head; | ||
686 | 627 | ||
687 | /* Search for the address. */ | 628 | /* Search for the address. */ |
688 | 629 | ||
@@ -702,8 +643,7 @@ acpi_ut_find_allocation ( | |||
702 | * | 643 | * |
703 | * FUNCTION: acpi_ut_track_allocation | 644 | * FUNCTION: acpi_ut_track_allocation |
704 | * | 645 | * |
705 | * PARAMETERS: list_id - Memory list to search | 646 | * PARAMETERS: Allocation - Address of allocated memory |
706 | * Allocation - Address of allocated memory | ||
707 | * Size - Size of the allocation | 647 | * Size - Size of the allocation |
708 | * alloc_type - MEM_MALLOC or MEM_CALLOC | 648 | * alloc_type - MEM_MALLOC or MEM_CALLOC |
709 | * Component - Component type of caller | 649 | * Component - Component type of caller |
@@ -718,7 +658,6 @@ acpi_ut_find_allocation ( | |||
718 | 658 | ||
719 | static acpi_status | 659 | static acpi_status |
720 | acpi_ut_track_allocation ( | 660 | acpi_ut_track_allocation ( |
721 | u32 list_id, | ||
722 | struct acpi_debug_mem_block *allocation, | 661 | struct acpi_debug_mem_block *allocation, |
723 | acpi_size size, | 662 | acpi_size size, |
724 | u8 alloc_type, | 663 | u8 alloc_type, |
@@ -734,11 +673,7 @@ acpi_ut_track_allocation ( | |||
734 | ACPI_FUNCTION_TRACE_PTR ("ut_track_allocation", allocation); | 673 | ACPI_FUNCTION_TRACE_PTR ("ut_track_allocation", allocation); |
735 | 674 | ||
736 | 675 | ||
737 | if (list_id > ACPI_MEM_LIST_MAX) { | 676 | mem_list = acpi_gbl_global_list; |
738 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
739 | } | ||
740 | |||
741 | mem_list = &acpi_gbl_memory_lists[list_id]; | ||
742 | status = acpi_ut_acquire_mutex (ACPI_MTX_MEMORY); | 677 | status = acpi_ut_acquire_mutex (ACPI_MTX_MEMORY); |
743 | if (ACPI_FAILURE (status)) { | 678 | if (ACPI_FAILURE (status)) { |
744 | return_ACPI_STATUS (status); | 679 | return_ACPI_STATUS (status); |
@@ -748,8 +683,7 @@ acpi_ut_track_allocation ( | |||
748 | * Search list for this address to make sure it is not already on the list. | 683 | * Search list for this address to make sure it is not already on the list. |
749 | * This will catch several kinds of problems. | 684 | * This will catch several kinds of problems. |
750 | */ | 685 | */ |
751 | 686 | element = acpi_ut_find_allocation (allocation); | |
752 | element = acpi_ut_find_allocation (list_id, allocation); | ||
753 | if (element) { | 687 | if (element) { |
754 | ACPI_REPORT_ERROR (( | 688 | ACPI_REPORT_ERROR (( |
755 | "ut_track_allocation: Allocation already present in list! (%p)\n", | 689 | "ut_track_allocation: Allocation already present in list! (%p)\n", |
@@ -793,8 +727,7 @@ unlock_and_exit: | |||
793 | * | 727 | * |
794 | * FUNCTION: acpi_ut_remove_allocation | 728 | * FUNCTION: acpi_ut_remove_allocation |
795 | * | 729 | * |
796 | * PARAMETERS: list_id - Memory list to search | 730 | * PARAMETERS: Allocation - Address of allocated memory |
797 | * Allocation - Address of allocated memory | ||
798 | * Component - Component type of caller | 731 | * Component - Component type of caller |
799 | * Module - Source file name of caller | 732 | * Module - Source file name of caller |
800 | * Line - Line number of caller | 733 | * Line - Line number of caller |
@@ -807,7 +740,6 @@ unlock_and_exit: | |||
807 | 740 | ||
808 | static acpi_status | 741 | static acpi_status |
809 | acpi_ut_remove_allocation ( | 742 | acpi_ut_remove_allocation ( |
810 | u32 list_id, | ||
811 | struct acpi_debug_mem_block *allocation, | 743 | struct acpi_debug_mem_block *allocation, |
812 | u32 component, | 744 | u32 component, |
813 | char *module, | 745 | char *module, |
@@ -820,11 +752,7 @@ acpi_ut_remove_allocation ( | |||
820 | ACPI_FUNCTION_TRACE ("ut_remove_allocation"); | 752 | ACPI_FUNCTION_TRACE ("ut_remove_allocation"); |
821 | 753 | ||
822 | 754 | ||
823 | if (list_id > ACPI_MEM_LIST_MAX) { | 755 | mem_list = acpi_gbl_global_list; |
824 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
825 | } | ||
826 | |||
827 | mem_list = &acpi_gbl_memory_lists[list_id]; | ||
828 | if (NULL == mem_list->list_head) { | 756 | if (NULL == mem_list->list_head) { |
829 | /* No allocations! */ | 757 | /* No allocations! */ |
830 | 758 | ||
@@ -959,7 +887,7 @@ acpi_ut_dump_allocations ( | |||
959 | return; | 887 | return; |
960 | } | 888 | } |
961 | 889 | ||
962 | element = acpi_gbl_memory_lists[0].list_head; | 890 | element = acpi_gbl_global_list->list_head; |
963 | while (element) { | 891 | while (element) { |
964 | if ((element->component & component) && | 892 | if ((element->component & component) && |
965 | ((module == NULL) || (0 == ACPI_STRCMP (module, element->module)))) { | 893 | ((module == NULL) || (0 == ACPI_STRCMP (module, element->module)))) { |
diff --git a/drivers/acpi/utilities/utcache.c b/drivers/acpi/utilities/utcache.c new file mode 100644 index 000000000000..c0df0585c683 --- /dev/null +++ b/drivers/acpi/utilities/utcache.c | |||
@@ -0,0 +1,328 @@ | |||
1 | /****************************************************************************** | ||
2 | * | ||
3 | * Module Name: utcache - local cache allocation routines | ||
4 | * | ||
5 | *****************************************************************************/ | ||
6 | |||
7 | /* | ||
8 | * Copyright (C) 2000 - 2005, R. Byron Moore | ||
9 | * All rights reserved. | ||
10 | * | ||
11 | * Redistribution and use in source and binary forms, with or without | ||
12 | * modification, are permitted provided that the following conditions | ||
13 | * are met: | ||
14 | * 1. Redistributions of source code must retain the above copyright | ||
15 | * notice, this list of conditions, and the following disclaimer, | ||
16 | * without modification. | ||
17 | * 2. Redistributions in binary form must reproduce at minimum a disclaimer | ||
18 | * substantially similar to the "NO WARRANTY" disclaimer below | ||
19 | * ("Disclaimer") and any redistribution must be conditioned upon | ||
20 | * including a substantially similar Disclaimer requirement for further | ||
21 | * binary redistribution. | ||
22 | * 3. Neither the names of the above-listed copyright holders nor the names | ||
23 | * of any contributors may be used to endorse or promote products derived | ||
24 | * from this software without specific prior written permission. | ||
25 | * | ||
26 | * Alternatively, this software may be distributed under the terms of the | ||
27 | * GNU General Public License ("GPL") version 2 as published by the Free | ||
28 | * Software Foundation. | ||
29 | * | ||
30 | * NO WARRANTY | ||
31 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
32 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
33 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR | ||
34 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
35 | * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
36 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
37 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
38 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
39 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING | ||
40 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | ||
41 | * POSSIBILITY OF SUCH DAMAGES. | ||
42 | */ | ||
43 | |||
44 | |||
45 | #include <acpi/acpi.h> | ||
46 | |||
47 | #define _COMPONENT ACPI_UTILITIES | ||
48 | ACPI_MODULE_NAME ("utcache") | ||
49 | |||
50 | |||
51 | #ifdef ACPI_USE_LOCAL_CACHE | ||
52 | /******************************************************************************* | ||
53 | * | ||
54 | * FUNCTION: acpi_os_create_cache | ||
55 | * | ||
56 | * PARAMETERS: cache_name - Ascii name for the cache | ||
57 | * object_size - Size of each cached object | ||
58 | * max_depth - Maximum depth of the cache (in objects) | ||
59 | * return_cache - Where the new cache object is returned | ||
60 | * | ||
61 | * RETURN: Status | ||
62 | * | ||
63 | * DESCRIPTION: Create a cache object | ||
64 | * | ||
65 | ******************************************************************************/ | ||
66 | |||
67 | acpi_status | ||
68 | acpi_os_create_cache ( | ||
69 | char *cache_name, | ||
70 | u16 object_size, | ||
71 | u16 max_depth, | ||
72 | struct acpi_memory_list **return_cache) | ||
73 | { | ||
74 | struct acpi_memory_list *cache; | ||
75 | |||
76 | |||
77 | ACPI_FUNCTION_ENTRY (); | ||
78 | |||
79 | |||
80 | if (!cache_name || !return_cache || (object_size < 16)) { | ||
81 | return (AE_BAD_PARAMETER); | ||
82 | } | ||
83 | |||
84 | /* Create the cache object */ | ||
85 | |||
86 | cache = acpi_os_allocate (sizeof (struct acpi_memory_list)); | ||
87 | if (!cache) { | ||
88 | return (AE_NO_MEMORY); | ||
89 | } | ||
90 | |||
91 | /* Populate the cache object and return it */ | ||
92 | |||
93 | ACPI_MEMSET (cache, 0, sizeof (struct acpi_memory_list)); | ||
94 | cache->link_offset = 8; | ||
95 | cache->list_name = cache_name; | ||
96 | cache->object_size = object_size; | ||
97 | cache->max_depth = max_depth; | ||
98 | |||
99 | *return_cache = cache; | ||
100 | return (AE_OK); | ||
101 | } | ||
102 | |||
103 | |||
104 | /******************************************************************************* | ||
105 | * | ||
106 | * FUNCTION: acpi_os_purge_cache | ||
107 | * | ||
108 | * PARAMETERS: Cache - Handle to cache object | ||
109 | * | ||
110 | * RETURN: Status | ||
111 | * | ||
112 | * DESCRIPTION: Free all objects within the requested cache. | ||
113 | * | ||
114 | ******************************************************************************/ | ||
115 | |||
116 | acpi_status | ||
117 | acpi_os_purge_cache ( | ||
118 | struct acpi_memory_list *cache) | ||
119 | { | ||
120 | char *next; | ||
121 | |||
122 | |||
123 | ACPI_FUNCTION_ENTRY (); | ||
124 | |||
125 | |||
126 | if (!cache) { | ||
127 | return (AE_BAD_PARAMETER); | ||
128 | } | ||
129 | |||
130 | /* Walk the list of objects in this cache */ | ||
131 | |||
132 | while (cache->list_head) { | ||
133 | /* Delete and unlink one cached state object */ | ||
134 | |||
135 | next = *(ACPI_CAST_INDIRECT_PTR (char, | ||
136 | &(((char *) cache->list_head)[cache->link_offset]))); | ||
137 | ACPI_MEM_FREE (cache->list_head); | ||
138 | |||
139 | cache->list_head = next; | ||
140 | cache->current_depth--; | ||
141 | } | ||
142 | |||
143 | return (AE_OK); | ||
144 | } | ||
145 | |||
146 | |||
147 | /******************************************************************************* | ||
148 | * | ||
149 | * FUNCTION: acpi_os_delete_cache | ||
150 | * | ||
151 | * PARAMETERS: Cache - Handle to cache object | ||
152 | * | ||
153 | * RETURN: Status | ||
154 | * | ||
155 | * DESCRIPTION: Free all objects within the requested cache and delete the | ||
156 | * cache object. | ||
157 | * | ||
158 | ******************************************************************************/ | ||
159 | |||
160 | acpi_status | ||
161 | acpi_os_delete_cache ( | ||
162 | struct acpi_memory_list *cache) | ||
163 | { | ||
164 | acpi_status status; | ||
165 | |||
166 | |||
167 | ACPI_FUNCTION_ENTRY (); | ||
168 | |||
169 | |||
170 | /* Purge all objects in the cache */ | ||
171 | |||
172 | status = acpi_os_purge_cache (cache); | ||
173 | if (ACPI_FAILURE (status)) { | ||
174 | return (status); | ||
175 | } | ||
176 | |||
177 | /* Now we can delete the cache object */ | ||
178 | |||
179 | acpi_os_free (cache); | ||
180 | return (AE_OK); | ||
181 | } | ||
182 | |||
183 | |||
184 | /******************************************************************************* | ||
185 | * | ||
186 | * FUNCTION: acpi_os_release_object | ||
187 | * | ||
188 | * PARAMETERS: Cache - Handle to cache object | ||
189 | * Object - The object to be released | ||
190 | * | ||
191 | * RETURN: None | ||
192 | * | ||
193 | * DESCRIPTION: Release an object to the specified cache. If cache is full, | ||
194 | * the object is deleted. | ||
195 | * | ||
196 | ******************************************************************************/ | ||
197 | |||
198 | acpi_status | ||
199 | acpi_os_release_object ( | ||
200 | struct acpi_memory_list *cache, | ||
201 | void *object) | ||
202 | { | ||
203 | acpi_status status; | ||
204 | |||
205 | |||
206 | ACPI_FUNCTION_ENTRY (); | ||
207 | |||
208 | |||
209 | if (!cache || !object) { | ||
210 | return (AE_BAD_PARAMETER); | ||
211 | } | ||
212 | |||
213 | /* If cache is full, just free this object */ | ||
214 | |||
215 | if (cache->current_depth >= cache->max_depth) { | ||
216 | ACPI_MEM_FREE (object); | ||
217 | ACPI_MEM_TRACKING (cache->total_freed++); | ||
218 | } | ||
219 | |||
220 | /* Otherwise put this object back into the cache */ | ||
221 | |||
222 | else { | ||
223 | status = acpi_ut_acquire_mutex (ACPI_MTX_CACHES); | ||
224 | if (ACPI_FAILURE (status)) { | ||
225 | return (status); | ||
226 | } | ||
227 | |||
228 | /* Mark the object as cached */ | ||
229 | |||
230 | ACPI_MEMSET (object, 0xCA, cache->object_size); | ||
231 | ACPI_SET_DESCRIPTOR_TYPE (object, ACPI_DESC_TYPE_CACHED); | ||
232 | |||
233 | /* Put the object at the head of the cache list */ | ||
234 | |||
235 | * (ACPI_CAST_INDIRECT_PTR (char, | ||
236 | &(((char *) object)[cache->link_offset]))) = cache->list_head; | ||
237 | cache->list_head = object; | ||
238 | cache->current_depth++; | ||
239 | |||
240 | (void) acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
241 | } | ||
242 | |||
243 | return (AE_OK); | ||
244 | } | ||
245 | |||
246 | |||
247 | /******************************************************************************* | ||
248 | * | ||
249 | * FUNCTION: acpi_os_acquire_object | ||
250 | * | ||
251 | * PARAMETERS: Cache - Handle to cache object | ||
252 | * | ||
253 | * RETURN: the acquired object. NULL on error | ||
254 | * | ||
255 | * DESCRIPTION: Get an object from the specified cache. If cache is empty, | ||
256 | * the object is allocated. | ||
257 | * | ||
258 | ******************************************************************************/ | ||
259 | |||
260 | void * | ||
261 | acpi_os_acquire_object ( | ||
262 | struct acpi_memory_list *cache) | ||
263 | { | ||
264 | acpi_status status; | ||
265 | void *object; | ||
266 | |||
267 | |||
268 | ACPI_FUNCTION_NAME ("os_acquire_object"); | ||
269 | |||
270 | |||
271 | if (!cache) { | ||
272 | return (NULL); | ||
273 | } | ||
274 | |||
275 | status = acpi_ut_acquire_mutex (ACPI_MTX_CACHES); | ||
276 | if (ACPI_FAILURE (status)) { | ||
277 | return (NULL); | ||
278 | } | ||
279 | |||
280 | ACPI_MEM_TRACKING (cache->requests++); | ||
281 | |||
282 | /* Check the cache first */ | ||
283 | |||
284 | if (cache->list_head) { | ||
285 | /* There is an object available, use it */ | ||
286 | |||
287 | object = cache->list_head; | ||
288 | cache->list_head = *(ACPI_CAST_INDIRECT_PTR (char, | ||
289 | &(((char *) object)[cache->link_offset]))); | ||
290 | |||
291 | cache->current_depth--; | ||
292 | |||
293 | ACPI_MEM_TRACKING (cache->hits++); | ||
294 | ACPI_MEM_TRACKING (ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, | ||
295 | "Object %p from %s cache\n", object, cache->list_name))); | ||
296 | |||
297 | status = acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
298 | if (ACPI_FAILURE (status)) { | ||
299 | return (NULL); | ||
300 | } | ||
301 | |||
302 | /* Clear (zero) the previously used Object */ | ||
303 | |||
304 | ACPI_MEMSET (object, 0, cache->object_size); | ||
305 | } | ||
306 | else { | ||
307 | /* The cache is empty, create a new object */ | ||
308 | |||
309 | ACPI_MEM_TRACKING (cache->total_allocated++); | ||
310 | |||
311 | /* Avoid deadlock with ACPI_MEM_CALLOCATE */ | ||
312 | |||
313 | status = acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
314 | if (ACPI_FAILURE (status)) { | ||
315 | return (NULL); | ||
316 | } | ||
317 | |||
318 | object = ACPI_MEM_CALLOCATE (cache->object_size); | ||
319 | if (!object) { | ||
320 | return (NULL); | ||
321 | } | ||
322 | } | ||
323 | |||
324 | return (object); | ||
325 | } | ||
326 | #endif /* ACPI_USE_LOCAL_CACHE */ | ||
327 | |||
328 | |||
diff --git a/drivers/acpi/utilities/utcopy.c b/drivers/acpi/utilities/utcopy.c index 11e884957162..31c30a32e5c9 100644 --- a/drivers/acpi/utilities/utcopy.c +++ b/drivers/acpi/utilities/utcopy.c | |||
@@ -694,58 +694,50 @@ acpi_ut_copy_simple_object ( | |||
694 | dest_desc->common.reference_count = reference_count; | 694 | dest_desc->common.reference_count = reference_count; |
695 | dest_desc->common.next_object = next_object; | 695 | dest_desc->common.next_object = next_object; |
696 | 696 | ||
697 | /* New object is not static, regardless of source */ | ||
698 | |||
699 | dest_desc->common.flags &= ~AOPOBJ_STATIC_POINTER; | ||
700 | |||
697 | /* Handle the objects with extra data */ | 701 | /* Handle the objects with extra data */ |
698 | 702 | ||
699 | switch (ACPI_GET_OBJECT_TYPE (dest_desc)) { | 703 | switch (ACPI_GET_OBJECT_TYPE (dest_desc)) { |
700 | case ACPI_TYPE_BUFFER: | 704 | case ACPI_TYPE_BUFFER: |
701 | |||
702 | dest_desc->buffer.node = NULL; | ||
703 | dest_desc->common.flags = source_desc->common.flags; | ||
704 | |||
705 | /* | 705 | /* |
706 | * Allocate and copy the actual buffer if and only if: | 706 | * Allocate and copy the actual buffer if and only if: |
707 | * 1) There is a valid buffer pointer | 707 | * 1) There is a valid buffer pointer |
708 | * 2) The buffer is not static (not in an ACPI table) (in this case, | 708 | * 2) The buffer has a length > 0 |
709 | * the actual pointer was already copied above) | ||
710 | */ | 709 | */ |
711 | if ((source_desc->buffer.pointer) && | 710 | if ((source_desc->buffer.pointer) && |
712 | (!(source_desc->common.flags & AOPOBJ_STATIC_POINTER))) { | 711 | (source_desc->buffer.length)) { |
713 | dest_desc->buffer.pointer = NULL; | 712 | dest_desc->buffer.pointer = |
714 | 713 | ACPI_MEM_ALLOCATE (source_desc->buffer.length); | |
715 | /* Create an actual buffer only if length > 0 */ | 714 | if (!dest_desc->buffer.pointer) { |
716 | 715 | return (AE_NO_MEMORY); | |
717 | if (source_desc->buffer.length) { | 716 | } |
718 | dest_desc->buffer.pointer = | ||
719 | ACPI_MEM_ALLOCATE (source_desc->buffer.length); | ||
720 | if (!dest_desc->buffer.pointer) { | ||
721 | return (AE_NO_MEMORY); | ||
722 | } | ||
723 | 717 | ||
724 | /* Copy the actual buffer data */ | 718 | /* Copy the actual buffer data */ |
725 | 719 | ||
726 | ACPI_MEMCPY (dest_desc->buffer.pointer, | 720 | ACPI_MEMCPY (dest_desc->buffer.pointer, |
727 | source_desc->buffer.pointer, | 721 | source_desc->buffer.pointer, |
728 | source_desc->buffer.length); | 722 | source_desc->buffer.length); |
729 | } | ||
730 | } | 723 | } |
731 | break; | 724 | break; |
732 | 725 | ||
733 | case ACPI_TYPE_STRING: | 726 | case ACPI_TYPE_STRING: |
734 | |||
735 | /* | 727 | /* |
736 | * Allocate and copy the actual string if and only if: | 728 | * Allocate and copy the actual string if and only if: |
737 | * 1) There is a valid string pointer | 729 | * 1) There is a valid string pointer |
738 | * 2) The string is not static (not in an ACPI table) (in this case, | 730 | * (Pointer to a NULL string is allowed) |
739 | * the actual pointer was already copied above) | ||
740 | */ | 731 | */ |
741 | if ((source_desc->string.pointer) && | 732 | if (source_desc->string.pointer) { |
742 | (!(source_desc->common.flags & AOPOBJ_STATIC_POINTER))) { | ||
743 | dest_desc->string.pointer = | 733 | dest_desc->string.pointer = |
744 | ACPI_MEM_ALLOCATE ((acpi_size) source_desc->string.length + 1); | 734 | ACPI_MEM_ALLOCATE ((acpi_size) source_desc->string.length + 1); |
745 | if (!dest_desc->string.pointer) { | 735 | if (!dest_desc->string.pointer) { |
746 | return (AE_NO_MEMORY); | 736 | return (AE_NO_MEMORY); |
747 | } | 737 | } |
748 | 738 | ||
739 | /* Copy the actual string data */ | ||
740 | |||
749 | ACPI_MEMCPY (dest_desc->string.pointer, source_desc->string.pointer, | 741 | ACPI_MEMCPY (dest_desc->string.pointer, source_desc->string.pointer, |
750 | (acpi_size) source_desc->string.length + 1); | 742 | (acpi_size) source_desc->string.length + 1); |
751 | } | 743 | } |
diff --git a/drivers/acpi/utilities/utdebug.c b/drivers/acpi/utilities/utdebug.c index 794c7df3f2ad..c27cbb7f5c54 100644 --- a/drivers/acpi/utilities/utdebug.c +++ b/drivers/acpi/utilities/utdebug.c | |||
@@ -55,6 +55,12 @@ static u32 acpi_gbl_prev_thread_id = 0xFFFFFFFF; | |||
55 | static char *acpi_gbl_fn_entry_str = "----Entry"; | 55 | static char *acpi_gbl_fn_entry_str = "----Entry"; |
56 | static char *acpi_gbl_fn_exit_str = "----Exit-"; | 56 | static char *acpi_gbl_fn_exit_str = "----Exit-"; |
57 | 57 | ||
58 | /* Local prototypes */ | ||
59 | |||
60 | static const char * | ||
61 | acpi_ut_trim_function_name ( | ||
62 | const char *function_name); | ||
63 | |||
58 | 64 | ||
59 | /******************************************************************************* | 65 | /******************************************************************************* |
60 | * | 66 | * |
@@ -72,7 +78,7 @@ void | |||
72 | acpi_ut_init_stack_ptr_trace ( | 78 | acpi_ut_init_stack_ptr_trace ( |
73 | void) | 79 | void) |
74 | { | 80 | { |
75 | u32 current_sp; | 81 | u32 current_sp; |
76 | 82 | ||
77 | 83 | ||
78 | acpi_gbl_entry_stack_pointer = ACPI_PTR_DIFF (¤t_sp, NULL); | 84 | acpi_gbl_entry_stack_pointer = ACPI_PTR_DIFF (¤t_sp, NULL); |
@@ -95,7 +101,7 @@ void | |||
95 | acpi_ut_track_stack_ptr ( | 101 | acpi_ut_track_stack_ptr ( |
96 | void) | 102 | void) |
97 | { | 103 | { |
98 | acpi_size current_sp; | 104 | acpi_size current_sp; |
99 | 105 | ||
100 | 106 | ||
101 | current_sp = ACPI_PTR_DIFF (¤t_sp, NULL); | 107 | current_sp = ACPI_PTR_DIFF (¤t_sp, NULL); |
@@ -112,14 +118,50 @@ acpi_ut_track_stack_ptr ( | |||
112 | 118 | ||
113 | /******************************************************************************* | 119 | /******************************************************************************* |
114 | * | 120 | * |
121 | * FUNCTION: acpi_ut_trim_function_name | ||
122 | * | ||
123 | * PARAMETERS: function_name - Ascii string containing a procedure name | ||
124 | * | ||
125 | * RETURN: Updated pointer to the function name | ||
126 | * | ||
127 | * DESCRIPTION: Remove the "Acpi" prefix from the function name, if present. | ||
128 | * This allows compiler macros such as __FUNCTION__ to be used | ||
129 | * with no change to the debug output. | ||
130 | * | ||
131 | ******************************************************************************/ | ||
132 | |||
133 | static const char * | ||
134 | acpi_ut_trim_function_name ( | ||
135 | const char *function_name) | ||
136 | { | ||
137 | |||
138 | /* All Function names are longer than 4 chars, check is safe */ | ||
139 | |||
140 | if (*(ACPI_CAST_PTR (u32, function_name)) == ACPI_FUNCTION_PREFIX1) { | ||
141 | /* This is the case where the original source has not been modified */ | ||
142 | |||
143 | return (function_name + 4); | ||
144 | } | ||
145 | |||
146 | if (*(ACPI_CAST_PTR (u32, function_name)) == ACPI_FUNCTION_PREFIX2) { | ||
147 | /* This is the case where the source has been 'linuxized' */ | ||
148 | |||
149 | return (function_name + 5); | ||
150 | } | ||
151 | |||
152 | return (function_name); | ||
153 | } | ||
154 | |||
155 | |||
156 | /******************************************************************************* | ||
157 | * | ||
115 | * FUNCTION: acpi_ut_debug_print | 158 | * FUNCTION: acpi_ut_debug_print |
116 | * | 159 | * |
117 | * PARAMETERS: requested_debug_level - Requested debug print level | 160 | * PARAMETERS: requested_debug_level - Requested debug print level |
118 | * line_number - Caller's line number (for error output) | 161 | * line_number - Caller's line number (for error output) |
119 | * dbg_info - Contains: | 162 | * function_name - Caller's procedure name |
120 | * proc_name - Caller's procedure name | 163 | * module_name - Caller's module name |
121 | * module_name - Caller's module name | 164 | * component_id - Caller's component ID |
122 | * component_id - Caller's component ID | ||
123 | * Format - Printf format field | 165 | * Format - Printf format field |
124 | * ... - Optional printf arguments | 166 | * ... - Optional printf arguments |
125 | * | 167 | * |
@@ -134,7 +176,9 @@ void ACPI_INTERNAL_VAR_XFACE | |||
134 | acpi_ut_debug_print ( | 176 | acpi_ut_debug_print ( |
135 | u32 requested_debug_level, | 177 | u32 requested_debug_level, |
136 | u32 line_number, | 178 | u32 line_number, |
137 | struct acpi_debug_print_info *dbg_info, | 179 | const char *function_name, |
180 | char *module_name, | ||
181 | u32 component_id, | ||
138 | char *format, | 182 | char *format, |
139 | ...) | 183 | ...) |
140 | { | 184 | { |
@@ -146,7 +190,7 @@ acpi_ut_debug_print ( | |||
146 | * Stay silent if the debug level or component ID is disabled | 190 | * Stay silent if the debug level or component ID is disabled |
147 | */ | 191 | */ |
148 | if (!(requested_debug_level & acpi_dbg_level) || | 192 | if (!(requested_debug_level & acpi_dbg_level) || |
149 | !(dbg_info->component_id & acpi_dbg_layer)) { | 193 | !(component_id & acpi_dbg_layer)) { |
150 | return; | 194 | return; |
151 | } | 195 | } |
152 | 196 | ||
@@ -169,14 +213,14 @@ acpi_ut_debug_print ( | |||
169 | * Display the module name, current line number, thread ID (if requested), | 213 | * Display the module name, current line number, thread ID (if requested), |
170 | * current procedure nesting level, and the current procedure name | 214 | * current procedure nesting level, and the current procedure name |
171 | */ | 215 | */ |
172 | acpi_os_printf ("%8s-%04ld ", dbg_info->module_name, line_number); | 216 | acpi_os_printf ("%8s-%04ld ", module_name, line_number); |
173 | 217 | ||
174 | if (ACPI_LV_THREADS & acpi_dbg_level) { | 218 | if (ACPI_LV_THREADS & acpi_dbg_level) { |
175 | acpi_os_printf ("[%04lX] ", thread_id); | 219 | acpi_os_printf ("[%04lX] ", thread_id); |
176 | } | 220 | } |
177 | 221 | ||
178 | acpi_os_printf ("[%02ld] %-22.22s: ", | 222 | acpi_os_printf ("[%02ld] %-22.22s: ", |
179 | acpi_gbl_nesting_level, dbg_info->proc_name); | 223 | acpi_gbl_nesting_level, acpi_ut_trim_function_name (function_name)); |
180 | 224 | ||
181 | va_start (args, format); | 225 | va_start (args, format); |
182 | acpi_os_vprintf (format, args); | 226 | acpi_os_vprintf (format, args); |
@@ -190,10 +234,9 @@ EXPORT_SYMBOL(acpi_ut_debug_print); | |||
190 | * | 234 | * |
191 | * PARAMETERS: requested_debug_level - Requested debug print level | 235 | * PARAMETERS: requested_debug_level - Requested debug print level |
192 | * line_number - Caller's line number | 236 | * line_number - Caller's line number |
193 | * dbg_info - Contains: | 237 | * function_name - Caller's procedure name |
194 | * proc_name - Caller's procedure name | 238 | * module_name - Caller's module name |
195 | * module_name - Caller's module name | 239 | * component_id - Caller's component ID |
196 | * component_id - Caller's component ID | ||
197 | * Format - Printf format field | 240 | * Format - Printf format field |
198 | * ... - Optional printf arguments | 241 | * ... - Optional printf arguments |
199 | * | 242 | * |
@@ -208,7 +251,9 @@ void ACPI_INTERNAL_VAR_XFACE | |||
208 | acpi_ut_debug_print_raw ( | 251 | acpi_ut_debug_print_raw ( |
209 | u32 requested_debug_level, | 252 | u32 requested_debug_level, |
210 | u32 line_number, | 253 | u32 line_number, |
211 | struct acpi_debug_print_info *dbg_info, | 254 | const char *function_name, |
255 | char *module_name, | ||
256 | u32 component_id, | ||
212 | char *format, | 257 | char *format, |
213 | ...) | 258 | ...) |
214 | { | 259 | { |
@@ -216,7 +261,7 @@ acpi_ut_debug_print_raw ( | |||
216 | 261 | ||
217 | 262 | ||
218 | if (!(requested_debug_level & acpi_dbg_level) || | 263 | if (!(requested_debug_level & acpi_dbg_level) || |
219 | !(dbg_info->component_id & acpi_dbg_layer)) { | 264 | !(component_id & acpi_dbg_layer)) { |
220 | return; | 265 | return; |
221 | } | 266 | } |
222 | 267 | ||
@@ -231,10 +276,9 @@ EXPORT_SYMBOL(acpi_ut_debug_print_raw); | |||
231 | * FUNCTION: acpi_ut_trace | 276 | * FUNCTION: acpi_ut_trace |
232 | * | 277 | * |
233 | * PARAMETERS: line_number - Caller's line number | 278 | * PARAMETERS: line_number - Caller's line number |
234 | * dbg_info - Contains: | 279 | * function_name - Caller's procedure name |
235 | * proc_name - Caller's procedure name | 280 | * module_name - Caller's module name |
236 | * module_name - Caller's module name | 281 | * component_id - Caller's component ID |
237 | * component_id - Caller's component ID | ||
238 | * | 282 | * |
239 | * RETURN: None | 283 | * RETURN: None |
240 | * | 284 | * |
@@ -246,14 +290,17 @@ EXPORT_SYMBOL(acpi_ut_debug_print_raw); | |||
246 | void | 290 | void |
247 | acpi_ut_trace ( | 291 | acpi_ut_trace ( |
248 | u32 line_number, | 292 | u32 line_number, |
249 | struct acpi_debug_print_info *dbg_info) | 293 | const char *function_name, |
294 | char *module_name, | ||
295 | u32 component_id) | ||
250 | { | 296 | { |
251 | 297 | ||
252 | acpi_gbl_nesting_level++; | 298 | acpi_gbl_nesting_level++; |
253 | acpi_ut_track_stack_ptr (); | 299 | acpi_ut_track_stack_ptr (); |
254 | 300 | ||
255 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 301 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
256 | "%s\n", acpi_gbl_fn_entry_str); | 302 | line_number, function_name, module_name, component_id, |
303 | "%s\n", acpi_gbl_fn_entry_str); | ||
257 | } | 304 | } |
258 | EXPORT_SYMBOL(acpi_ut_trace); | 305 | EXPORT_SYMBOL(acpi_ut_trace); |
259 | 306 | ||
@@ -263,10 +310,9 @@ EXPORT_SYMBOL(acpi_ut_trace); | |||
263 | * FUNCTION: acpi_ut_trace_ptr | 310 | * FUNCTION: acpi_ut_trace_ptr |
264 | * | 311 | * |
265 | * PARAMETERS: line_number - Caller's line number | 312 | * PARAMETERS: line_number - Caller's line number |
266 | * dbg_info - Contains: | 313 | * function_name - Caller's procedure name |
267 | * proc_name - Caller's procedure name | 314 | * module_name - Caller's module name |
268 | * module_name - Caller's module name | 315 | * component_id - Caller's component ID |
269 | * component_id - Caller's component ID | ||
270 | * Pointer - Pointer to display | 316 | * Pointer - Pointer to display |
271 | * | 317 | * |
272 | * RETURN: None | 318 | * RETURN: None |
@@ -279,14 +325,17 @@ EXPORT_SYMBOL(acpi_ut_trace); | |||
279 | void | 325 | void |
280 | acpi_ut_trace_ptr ( | 326 | acpi_ut_trace_ptr ( |
281 | u32 line_number, | 327 | u32 line_number, |
282 | struct acpi_debug_print_info *dbg_info, | 328 | const char *function_name, |
329 | char *module_name, | ||
330 | u32 component_id, | ||
283 | void *pointer) | 331 | void *pointer) |
284 | { | 332 | { |
285 | acpi_gbl_nesting_level++; | 333 | acpi_gbl_nesting_level++; |
286 | acpi_ut_track_stack_ptr (); | 334 | acpi_ut_track_stack_ptr (); |
287 | 335 | ||
288 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 336 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
289 | "%s %p\n", acpi_gbl_fn_entry_str, pointer); | 337 | line_number, function_name, module_name, component_id, |
338 | "%s %p\n", acpi_gbl_fn_entry_str, pointer); | ||
290 | } | 339 | } |
291 | 340 | ||
292 | 341 | ||
@@ -295,10 +344,9 @@ acpi_ut_trace_ptr ( | |||
295 | * FUNCTION: acpi_ut_trace_str | 344 | * FUNCTION: acpi_ut_trace_str |
296 | * | 345 | * |
297 | * PARAMETERS: line_number - Caller's line number | 346 | * PARAMETERS: line_number - Caller's line number |
298 | * dbg_info - Contains: | 347 | * function_name - Caller's procedure name |
299 | * proc_name - Caller's procedure name | 348 | * module_name - Caller's module name |
300 | * module_name - Caller's module name | 349 | * component_id - Caller's component ID |
301 | * component_id - Caller's component ID | ||
302 | * String - Additional string to display | 350 | * String - Additional string to display |
303 | * | 351 | * |
304 | * RETURN: None | 352 | * RETURN: None |
@@ -311,15 +359,18 @@ acpi_ut_trace_ptr ( | |||
311 | void | 359 | void |
312 | acpi_ut_trace_str ( | 360 | acpi_ut_trace_str ( |
313 | u32 line_number, | 361 | u32 line_number, |
314 | struct acpi_debug_print_info *dbg_info, | 362 | const char *function_name, |
363 | char *module_name, | ||
364 | u32 component_id, | ||
315 | char *string) | 365 | char *string) |
316 | { | 366 | { |
317 | 367 | ||
318 | acpi_gbl_nesting_level++; | 368 | acpi_gbl_nesting_level++; |
319 | acpi_ut_track_stack_ptr (); | 369 | acpi_ut_track_stack_ptr (); |
320 | 370 | ||
321 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 371 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
322 | "%s %s\n", acpi_gbl_fn_entry_str, string); | 372 | line_number, function_name, module_name, component_id, |
373 | "%s %s\n", acpi_gbl_fn_entry_str, string); | ||
323 | } | 374 | } |
324 | 375 | ||
325 | 376 | ||
@@ -328,10 +379,9 @@ acpi_ut_trace_str ( | |||
328 | * FUNCTION: acpi_ut_trace_u32 | 379 | * FUNCTION: acpi_ut_trace_u32 |
329 | * | 380 | * |
330 | * PARAMETERS: line_number - Caller's line number | 381 | * PARAMETERS: line_number - Caller's line number |
331 | * dbg_info - Contains: | 382 | * function_name - Caller's procedure name |
332 | * proc_name - Caller's procedure name | 383 | * module_name - Caller's module name |
333 | * module_name - Caller's module name | 384 | * component_id - Caller's component ID |
334 | * component_id - Caller's component ID | ||
335 | * Integer - Integer to display | 385 | * Integer - Integer to display |
336 | * | 386 | * |
337 | * RETURN: None | 387 | * RETURN: None |
@@ -344,15 +394,18 @@ acpi_ut_trace_str ( | |||
344 | void | 394 | void |
345 | acpi_ut_trace_u32 ( | 395 | acpi_ut_trace_u32 ( |
346 | u32 line_number, | 396 | u32 line_number, |
347 | struct acpi_debug_print_info *dbg_info, | 397 | const char *function_name, |
398 | char *module_name, | ||
399 | u32 component_id, | ||
348 | u32 integer) | 400 | u32 integer) |
349 | { | 401 | { |
350 | 402 | ||
351 | acpi_gbl_nesting_level++; | 403 | acpi_gbl_nesting_level++; |
352 | acpi_ut_track_stack_ptr (); | 404 | acpi_ut_track_stack_ptr (); |
353 | 405 | ||
354 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 406 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
355 | "%s %08X\n", acpi_gbl_fn_entry_str, integer); | 407 | line_number, function_name, module_name, component_id, |
408 | "%s %08X\n", acpi_gbl_fn_entry_str, integer); | ||
356 | } | 409 | } |
357 | 410 | ||
358 | 411 | ||
@@ -361,10 +414,9 @@ acpi_ut_trace_u32 ( | |||
361 | * FUNCTION: acpi_ut_exit | 414 | * FUNCTION: acpi_ut_exit |
362 | * | 415 | * |
363 | * PARAMETERS: line_number - Caller's line number | 416 | * PARAMETERS: line_number - Caller's line number |
364 | * dbg_info - Contains: | 417 | * function_name - Caller's procedure name |
365 | * proc_name - Caller's procedure name | 418 | * module_name - Caller's module name |
366 | * module_name - Caller's module name | 419 | * component_id - Caller's component ID |
367 | * component_id - Caller's component ID | ||
368 | * | 420 | * |
369 | * RETURN: None | 421 | * RETURN: None |
370 | * | 422 | * |
@@ -376,11 +428,14 @@ acpi_ut_trace_u32 ( | |||
376 | void | 428 | void |
377 | acpi_ut_exit ( | 429 | acpi_ut_exit ( |
378 | u32 line_number, | 430 | u32 line_number, |
379 | struct acpi_debug_print_info *dbg_info) | 431 | const char *function_name, |
432 | char *module_name, | ||
433 | u32 component_id) | ||
380 | { | 434 | { |
381 | 435 | ||
382 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 436 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
383 | "%s\n", acpi_gbl_fn_exit_str); | 437 | line_number, function_name, module_name, component_id, |
438 | "%s\n", acpi_gbl_fn_exit_str); | ||
384 | 439 | ||
385 | acpi_gbl_nesting_level--; | 440 | acpi_gbl_nesting_level--; |
386 | } | 441 | } |
@@ -392,10 +447,9 @@ EXPORT_SYMBOL(acpi_ut_exit); | |||
392 | * FUNCTION: acpi_ut_status_exit | 447 | * FUNCTION: acpi_ut_status_exit |
393 | * | 448 | * |
394 | * PARAMETERS: line_number - Caller's line number | 449 | * PARAMETERS: line_number - Caller's line number |
395 | * dbg_info - Contains: | 450 | * function_name - Caller's procedure name |
396 | * proc_name - Caller's procedure name | 451 | * module_name - Caller's module name |
397 | * module_name - Caller's module name | 452 | * component_id - Caller's component ID |
398 | * component_id - Caller's component ID | ||
399 | * Status - Exit status code | 453 | * Status - Exit status code |
400 | * | 454 | * |
401 | * RETURN: None | 455 | * RETURN: None |
@@ -408,19 +462,23 @@ EXPORT_SYMBOL(acpi_ut_exit); | |||
408 | void | 462 | void |
409 | acpi_ut_status_exit ( | 463 | acpi_ut_status_exit ( |
410 | u32 line_number, | 464 | u32 line_number, |
411 | struct acpi_debug_print_info *dbg_info, | 465 | const char *function_name, |
466 | char *module_name, | ||
467 | u32 component_id, | ||
412 | acpi_status status) | 468 | acpi_status status) |
413 | { | 469 | { |
414 | 470 | ||
415 | if (ACPI_SUCCESS (status)) { | 471 | if (ACPI_SUCCESS (status)) { |
416 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 472 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
417 | "%s %s\n", acpi_gbl_fn_exit_str, | 473 | line_number, function_name, module_name, component_id, |
418 | acpi_format_exception (status)); | 474 | "%s %s\n", acpi_gbl_fn_exit_str, |
475 | acpi_format_exception (status)); | ||
419 | } | 476 | } |
420 | else { | 477 | else { |
421 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 478 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
422 | "%s ****Exception****: %s\n", acpi_gbl_fn_exit_str, | 479 | line_number, function_name, module_name, component_id, |
423 | acpi_format_exception (status)); | 480 | "%s ****Exception****: %s\n", acpi_gbl_fn_exit_str, |
481 | acpi_format_exception (status)); | ||
424 | } | 482 | } |
425 | 483 | ||
426 | acpi_gbl_nesting_level--; | 484 | acpi_gbl_nesting_level--; |
@@ -433,10 +491,9 @@ EXPORT_SYMBOL(acpi_ut_status_exit); | |||
433 | * FUNCTION: acpi_ut_value_exit | 491 | * FUNCTION: acpi_ut_value_exit |
434 | * | 492 | * |
435 | * PARAMETERS: line_number - Caller's line number | 493 | * PARAMETERS: line_number - Caller's line number |
436 | * dbg_info - Contains: | 494 | * function_name - Caller's procedure name |
437 | * proc_name - Caller's procedure name | 495 | * module_name - Caller's module name |
438 | * module_name - Caller's module name | 496 | * component_id - Caller's component ID |
439 | * component_id - Caller's component ID | ||
440 | * Value - Value to be printed with exit msg | 497 | * Value - Value to be printed with exit msg |
441 | * | 498 | * |
442 | * RETURN: None | 499 | * RETURN: None |
@@ -449,13 +506,16 @@ EXPORT_SYMBOL(acpi_ut_status_exit); | |||
449 | void | 506 | void |
450 | acpi_ut_value_exit ( | 507 | acpi_ut_value_exit ( |
451 | u32 line_number, | 508 | u32 line_number, |
452 | struct acpi_debug_print_info *dbg_info, | 509 | const char *function_name, |
510 | char *module_name, | ||
511 | u32 component_id, | ||
453 | acpi_integer value) | 512 | acpi_integer value) |
454 | { | 513 | { |
455 | 514 | ||
456 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 515 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
457 | "%s %8.8X%8.8X\n", acpi_gbl_fn_exit_str, | 516 | line_number, function_name, module_name, component_id, |
458 | ACPI_FORMAT_UINT64 (value)); | 517 | "%s %8.8X%8.8X\n", acpi_gbl_fn_exit_str, |
518 | ACPI_FORMAT_UINT64 (value)); | ||
459 | 519 | ||
460 | acpi_gbl_nesting_level--; | 520 | acpi_gbl_nesting_level--; |
461 | } | 521 | } |
@@ -467,10 +527,9 @@ EXPORT_SYMBOL(acpi_ut_value_exit); | |||
467 | * FUNCTION: acpi_ut_ptr_exit | 527 | * FUNCTION: acpi_ut_ptr_exit |
468 | * | 528 | * |
469 | * PARAMETERS: line_number - Caller's line number | 529 | * PARAMETERS: line_number - Caller's line number |
470 | * dbg_info - Contains: | 530 | * function_name - Caller's procedure name |
471 | * proc_name - Caller's procedure name | 531 | * module_name - Caller's module name |
472 | * module_name - Caller's module name | 532 | * component_id - Caller's component ID |
473 | * component_id - Caller's component ID | ||
474 | * Ptr - Pointer to display | 533 | * Ptr - Pointer to display |
475 | * | 534 | * |
476 | * RETURN: None | 535 | * RETURN: None |
@@ -483,12 +542,15 @@ EXPORT_SYMBOL(acpi_ut_value_exit); | |||
483 | void | 542 | void |
484 | acpi_ut_ptr_exit ( | 543 | acpi_ut_ptr_exit ( |
485 | u32 line_number, | 544 | u32 line_number, |
486 | struct acpi_debug_print_info *dbg_info, | 545 | const char *function_name, |
546 | char *module_name, | ||
547 | u32 component_id, | ||
487 | u8 *ptr) | 548 | u8 *ptr) |
488 | { | 549 | { |
489 | 550 | ||
490 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, line_number, dbg_info, | 551 | acpi_ut_debug_print (ACPI_LV_FUNCTIONS, |
491 | "%s %p\n", acpi_gbl_fn_exit_str, ptr); | 552 | line_number, function_name, module_name, component_id, |
553 | "%s %p\n", acpi_gbl_fn_exit_str, ptr); | ||
492 | 554 | ||
493 | acpi_gbl_nesting_level--; | 555 | acpi_gbl_nesting_level--; |
494 | } | 556 | } |
@@ -549,7 +611,7 @@ acpi_ut_dump_buffer ( | |||
549 | /* Dump fill spaces */ | 611 | /* Dump fill spaces */ |
550 | 612 | ||
551 | acpi_os_printf ("%*s", ((display * 2) + 1), " "); | 613 | acpi_os_printf ("%*s", ((display * 2) + 1), " "); |
552 | j += display; | 614 | j += (acpi_native_uint) display; |
553 | continue; | 615 | continue; |
554 | } | 616 | } |
555 | 617 | ||
@@ -584,12 +646,12 @@ acpi_ut_dump_buffer ( | |||
584 | break; | 646 | break; |
585 | } | 647 | } |
586 | 648 | ||
587 | j += display; | 649 | j += (acpi_native_uint) display; |
588 | } | 650 | } |
589 | 651 | ||
590 | /* | 652 | /* |
591 | * Print the ASCII equivalent characters | 653 | * Print the ASCII equivalent characters but watch out for the bad |
592 | * But watch out for the bad unprintable ones... | 654 | * unprintable ones (printable chars are 0x20 through 0x7E) |
593 | */ | 655 | */ |
594 | acpi_os_printf (" "); | 656 | acpi_os_printf (" "); |
595 | for (j = 0; j < 16; j++) { | 657 | for (j = 0; j < 16; j++) { |
@@ -599,9 +661,7 @@ acpi_ut_dump_buffer ( | |||
599 | } | 661 | } |
600 | 662 | ||
601 | buf_char = buffer[i + j]; | 663 | buf_char = buffer[i + j]; |
602 | if ((buf_char > 0x1F && buf_char < 0x2E) || | 664 | if (ACPI_IS_PRINT (buf_char)) { |
603 | (buf_char > 0x2F && buf_char < 0x61) || | ||
604 | (buf_char > 0x60 && buf_char < 0x7F)) { | ||
605 | acpi_os_printf ("%c", buf_char); | 665 | acpi_os_printf ("%c", buf_char); |
606 | } | 666 | } |
607 | else { | 667 | else { |
diff --git a/drivers/acpi/utilities/utdelete.c b/drivers/acpi/utilities/utdelete.c index bc5403022681..eeafb324c504 100644 --- a/drivers/acpi/utilities/utdelete.c +++ b/drivers/acpi/utilities/utdelete.c | |||
@@ -435,35 +435,24 @@ acpi_ut_update_object_reference ( | |||
435 | union acpi_operand_object *object, | 435 | union acpi_operand_object *object, |
436 | u16 action) | 436 | u16 action) |
437 | { | 437 | { |
438 | acpi_status status; | 438 | acpi_status status = AE_OK; |
439 | u32 i; | 439 | union acpi_generic_state *state_list = NULL; |
440 | union acpi_generic_state *state_list = NULL; | 440 | union acpi_operand_object *next_object = NULL; |
441 | union acpi_generic_state *state; | 441 | union acpi_generic_state *state; |
442 | union acpi_operand_object *tmp; | 442 | acpi_native_uint i; |
443 | |||
444 | ACPI_FUNCTION_TRACE_PTR ("ut_update_object_reference", object); | ||
445 | 443 | ||
446 | 444 | ||
447 | /* Ignore a null object ptr */ | 445 | ACPI_FUNCTION_TRACE_PTR ("ut_update_object_reference", object); |
448 | |||
449 | if (!object) { | ||
450 | return_ACPI_STATUS (AE_OK); | ||
451 | } | ||
452 | 446 | ||
453 | /* Make sure that this isn't a namespace handle */ | ||
454 | 447 | ||
455 | if (ACPI_GET_DESCRIPTOR_TYPE (object) == ACPI_DESC_TYPE_NAMED) { | 448 | while (object) { |
456 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, | 449 | /* Make sure that this isn't a namespace handle */ |
457 | "Object %p is NS handle\n", object)); | ||
458 | return_ACPI_STATUS (AE_OK); | ||
459 | } | ||
460 | 450 | ||
461 | state = acpi_ut_create_update_state (object, action); | 451 | if (ACPI_GET_DESCRIPTOR_TYPE (object) == ACPI_DESC_TYPE_NAMED) { |
462 | 452 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, | |
463 | while (state) { | 453 | "Object %p is NS handle\n", object)); |
464 | object = state->update.object; | 454 | return_ACPI_STATUS (AE_OK); |
465 | action = state->update.value; | 455 | } |
466 | acpi_ut_delete_generic_state (state); | ||
467 | 456 | ||
468 | /* | 457 | /* |
469 | * All sub-objects must have their reference count incremented also. | 458 | * All sub-objects must have their reference count incremented also. |
@@ -472,24 +461,14 @@ acpi_ut_update_object_reference ( | |||
472 | switch (ACPI_GET_OBJECT_TYPE (object)) { | 461 | switch (ACPI_GET_OBJECT_TYPE (object)) { |
473 | case ACPI_TYPE_DEVICE: | 462 | case ACPI_TYPE_DEVICE: |
474 | 463 | ||
475 | tmp = object->device.system_notify; | 464 | acpi_ut_update_ref_count (object->device.system_notify, action); |
476 | if (tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | 465 | acpi_ut_update_ref_count (object->device.device_notify, action); |
477 | object->device.system_notify = NULL; | ||
478 | acpi_ut_update_ref_count (tmp, action); | ||
479 | |||
480 | tmp = object->device.device_notify; | ||
481 | if (tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
482 | object->device.device_notify = NULL; | ||
483 | acpi_ut_update_ref_count (tmp, action); | ||
484 | |||
485 | break; | 466 | break; |
486 | 467 | ||
487 | |||
488 | case ACPI_TYPE_PACKAGE: | 468 | case ACPI_TYPE_PACKAGE: |
489 | |||
490 | /* | 469 | /* |
491 | * We must update all the sub-objects of the package | 470 | * We must update all the sub-objects of the package, |
492 | * (Each of whom may have their own sub-objects, etc. | 471 | * each of whom may have their own sub-objects. |
493 | */ | 472 | */ |
494 | for (i = 0; i < object->package.count; i++) { | 473 | for (i = 0; i < object->package.count; i++) { |
495 | /* | 474 | /* |
@@ -502,111 +481,52 @@ acpi_ut_update_object_reference ( | |||
502 | if (ACPI_FAILURE (status)) { | 481 | if (ACPI_FAILURE (status)) { |
503 | goto error_exit; | 482 | goto error_exit; |
504 | } | 483 | } |
505 | |||
506 | tmp = object->package.elements[i]; | ||
507 | if (tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
508 | object->package.elements[i] = NULL; | ||
509 | } | 484 | } |
510 | break; | 485 | break; |
511 | 486 | ||
512 | |||
513 | case ACPI_TYPE_BUFFER_FIELD: | 487 | case ACPI_TYPE_BUFFER_FIELD: |
514 | 488 | ||
515 | status = acpi_ut_create_update_state_and_push ( | 489 | next_object = object->buffer_field.buffer_obj; |
516 | object->buffer_field.buffer_obj, action, &state_list); | ||
517 | if (ACPI_FAILURE (status)) { | ||
518 | goto error_exit; | ||
519 | } | ||
520 | |||
521 | tmp = object->buffer_field.buffer_obj; | ||
522 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
523 | object->buffer_field.buffer_obj = NULL; | ||
524 | break; | 490 | break; |
525 | 491 | ||
526 | |||
527 | case ACPI_TYPE_LOCAL_REGION_FIELD: | 492 | case ACPI_TYPE_LOCAL_REGION_FIELD: |
528 | 493 | ||
529 | status = acpi_ut_create_update_state_and_push ( | 494 | next_object = object->field.region_obj; |
530 | object->field.region_obj, action, &state_list); | 495 | break; |
531 | if (ACPI_FAILURE (status)) { | ||
532 | goto error_exit; | ||
533 | } | ||
534 | |||
535 | tmp = object->field.region_obj; | ||
536 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
537 | object->field.region_obj = NULL; | ||
538 | break; | ||
539 | |||
540 | 496 | ||
541 | case ACPI_TYPE_LOCAL_BANK_FIELD: | 497 | case ACPI_TYPE_LOCAL_BANK_FIELD: |
542 | 498 | ||
543 | status = acpi_ut_create_update_state_and_push ( | 499 | next_object = object->bank_field.bank_obj; |
544 | object->bank_field.bank_obj, action, &state_list); | ||
545 | if (ACPI_FAILURE (status)) { | ||
546 | goto error_exit; | ||
547 | } | ||
548 | |||
549 | tmp = object->bank_field.bank_obj; | ||
550 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
551 | object->bank_field.bank_obj = NULL; | ||
552 | |||
553 | status = acpi_ut_create_update_state_and_push ( | 500 | status = acpi_ut_create_update_state_and_push ( |
554 | object->bank_field.region_obj, action, &state_list); | 501 | object->bank_field.region_obj, action, &state_list); |
555 | if (ACPI_FAILURE (status)) { | 502 | if (ACPI_FAILURE (status)) { |
556 | goto error_exit; | 503 | goto error_exit; |
557 | } | 504 | } |
558 | |||
559 | tmp = object->bank_field.region_obj; | ||
560 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
561 | object->bank_field.region_obj = NULL; | ||
562 | break; | 505 | break; |
563 | 506 | ||
564 | |||
565 | case ACPI_TYPE_LOCAL_INDEX_FIELD: | 507 | case ACPI_TYPE_LOCAL_INDEX_FIELD: |
566 | 508 | ||
567 | status = acpi_ut_create_update_state_and_push ( | 509 | next_object = object->index_field.index_obj; |
568 | object->index_field.index_obj, action, &state_list); | ||
569 | if (ACPI_FAILURE (status)) { | ||
570 | goto error_exit; | ||
571 | } | ||
572 | |||
573 | tmp = object->index_field.index_obj; | ||
574 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
575 | object->index_field.index_obj = NULL; | ||
576 | |||
577 | status = acpi_ut_create_update_state_and_push ( | 510 | status = acpi_ut_create_update_state_and_push ( |
578 | object->index_field.data_obj, action, &state_list); | 511 | object->index_field.data_obj, action, &state_list); |
579 | if (ACPI_FAILURE (status)) { | 512 | if (ACPI_FAILURE (status)) { |
580 | goto error_exit; | 513 | goto error_exit; |
581 | } | 514 | } |
582 | |||
583 | tmp = object->index_field.data_obj; | ||
584 | if ( tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT) | ||
585 | object->index_field.data_obj = NULL; | ||
586 | break; | 515 | break; |
587 | 516 | ||
588 | |||
589 | case ACPI_TYPE_LOCAL_REFERENCE: | 517 | case ACPI_TYPE_LOCAL_REFERENCE: |
590 | |||
591 | /* | 518 | /* |
592 | * The target of an Index (a package, string, or buffer) must track | 519 | * The target of an Index (a package, string, or buffer) must track |
593 | * changes to the ref count of the index. | 520 | * changes to the ref count of the index. |
594 | */ | 521 | */ |
595 | if (object->reference.opcode == AML_INDEX_OP) { | 522 | if (object->reference.opcode == AML_INDEX_OP) { |
596 | status = acpi_ut_create_update_state_and_push ( | 523 | next_object = object->reference.object; |
597 | object->reference.object, action, &state_list); | ||
598 | if (ACPI_FAILURE (status)) { | ||
599 | goto error_exit; | ||
600 | } | ||
601 | } | 524 | } |
602 | break; | 525 | break; |
603 | 526 | ||
604 | |||
605 | case ACPI_TYPE_REGION: | 527 | case ACPI_TYPE_REGION: |
606 | default: | 528 | default: |
607 | 529 | break;/* No subobjects */ | |
608 | /* No subobjects */ | ||
609 | break; | ||
610 | } | 530 | } |
611 | 531 | ||
612 | /* | 532 | /* |
@@ -615,15 +535,23 @@ acpi_ut_update_object_reference ( | |||
615 | * main object to be deleted. | 535 | * main object to be deleted. |
616 | */ | 536 | */ |
617 | acpi_ut_update_ref_count (object, action); | 537 | acpi_ut_update_ref_count (object, action); |
538 | object = NULL; | ||
618 | 539 | ||
619 | /* Move on to the next object to be updated */ | 540 | /* Move on to the next object to be updated */ |
620 | 541 | ||
621 | state = acpi_ut_pop_generic_state (&state_list); | 542 | if (next_object) { |
543 | object = next_object; | ||
544 | next_object = NULL; | ||
545 | } | ||
546 | else if (state_list) { | ||
547 | state = acpi_ut_pop_generic_state (&state_list); | ||
548 | object = state->update.object; | ||
549 | acpi_ut_delete_generic_state (state); | ||
550 | } | ||
622 | } | 551 | } |
623 | 552 | ||
624 | return_ACPI_STATUS (AE_OK); | 553 | return_ACPI_STATUS (AE_OK); |
625 | 554 | ||
626 | |||
627 | error_exit: | 555 | error_exit: |
628 | 556 | ||
629 | ACPI_REPORT_ERROR (("Could not update object reference count, %s\n", | 557 | ACPI_REPORT_ERROR (("Could not update object reference count, %s\n", |
diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 4146019b543f..0e4161c81076 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c | |||
@@ -738,73 +738,6 @@ acpi_ut_valid_object_type ( | |||
738 | 738 | ||
739 | /******************************************************************************* | 739 | /******************************************************************************* |
740 | * | 740 | * |
741 | * FUNCTION: acpi_ut_allocate_owner_id | ||
742 | * | ||
743 | * PARAMETERS: id_type - Type of ID (method or table) | ||
744 | * | ||
745 | * DESCRIPTION: Allocate a table or method owner id | ||
746 | * | ||
747 | * NOTE: this algorithm has a wraparound problem at 64_k method invocations, and | ||
748 | * should be revisited (TBD) | ||
749 | * | ||
750 | ******************************************************************************/ | ||
751 | |||
752 | acpi_owner_id | ||
753 | acpi_ut_allocate_owner_id ( | ||
754 | u32 id_type) | ||
755 | { | ||
756 | acpi_owner_id owner_id = 0xFFFF; | ||
757 | |||
758 | |||
759 | ACPI_FUNCTION_TRACE ("ut_allocate_owner_id"); | ||
760 | |||
761 | |||
762 | if (ACPI_FAILURE (acpi_ut_acquire_mutex (ACPI_MTX_CACHES))) | ||
763 | { | ||
764 | return (0); | ||
765 | } | ||
766 | |||
767 | switch (id_type) | ||
768 | { | ||
769 | case ACPI_OWNER_TYPE_TABLE: | ||
770 | |||
771 | owner_id = acpi_gbl_next_table_owner_id; | ||
772 | acpi_gbl_next_table_owner_id++; | ||
773 | |||
774 | /* Check for wraparound */ | ||
775 | |||
776 | if (acpi_gbl_next_table_owner_id == ACPI_FIRST_METHOD_ID) | ||
777 | { | ||
778 | acpi_gbl_next_table_owner_id = ACPI_FIRST_TABLE_ID; | ||
779 | ACPI_REPORT_WARNING (("Table owner ID wraparound\n")); | ||
780 | } | ||
781 | break; | ||
782 | |||
783 | |||
784 | case ACPI_OWNER_TYPE_METHOD: | ||
785 | |||
786 | owner_id = acpi_gbl_next_method_owner_id; | ||
787 | acpi_gbl_next_method_owner_id++; | ||
788 | |||
789 | if (acpi_gbl_next_method_owner_id == ACPI_FIRST_TABLE_ID) | ||
790 | { | ||
791 | /* Check for wraparound */ | ||
792 | |||
793 | acpi_gbl_next_method_owner_id = ACPI_FIRST_METHOD_ID; | ||
794 | } | ||
795 | break; | ||
796 | |||
797 | default: | ||
798 | break; | ||
799 | } | ||
800 | |||
801 | (void) acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
802 | return_VALUE (owner_id); | ||
803 | } | ||
804 | |||
805 | |||
806 | /******************************************************************************* | ||
807 | * | ||
808 | * FUNCTION: acpi_ut_init_globals | 741 | * FUNCTION: acpi_ut_init_globals |
809 | * | 742 | * |
810 | * PARAMETERS: None | 743 | * PARAMETERS: None |
@@ -820,42 +753,20 @@ void | |||
820 | acpi_ut_init_globals ( | 753 | acpi_ut_init_globals ( |
821 | void) | 754 | void) |
822 | { | 755 | { |
756 | acpi_status status; | ||
823 | u32 i; | 757 | u32 i; |
824 | 758 | ||
825 | 759 | ||
826 | ACPI_FUNCTION_TRACE ("ut_init_globals"); | 760 | ACPI_FUNCTION_TRACE ("ut_init_globals"); |
827 | 761 | ||
828 | 762 | ||
829 | /* Memory allocation and cache lists */ | 763 | /* Create all memory caches */ |
830 | |||
831 | ACPI_MEMSET (acpi_gbl_memory_lists, 0, sizeof (struct acpi_memory_list) * ACPI_NUM_MEM_LISTS); | ||
832 | 764 | ||
833 | acpi_gbl_memory_lists[ACPI_MEM_LIST_STATE].link_offset = (u16) ACPI_PTR_DIFF (&(((union acpi_generic_state *) NULL)->common.next), NULL); | 765 | status = acpi_ut_create_caches (); |
834 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE].link_offset = (u16) ACPI_PTR_DIFF (&(((union acpi_parse_object *) NULL)->common.next), NULL); | 766 | if (ACPI_FAILURE (status)) |
835 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE_EXT].link_offset = (u16) ACPI_PTR_DIFF (&(((union acpi_parse_object *) NULL)->common.next), NULL); | 767 | { |
836 | acpi_gbl_memory_lists[ACPI_MEM_LIST_OPERAND].link_offset = (u16) ACPI_PTR_DIFF (&(((union acpi_operand_object *) NULL)->cache.next), NULL); | 768 | return; |
837 | acpi_gbl_memory_lists[ACPI_MEM_LIST_WALK].link_offset = (u16) ACPI_PTR_DIFF (&(((struct acpi_walk_state *) NULL)->next), NULL); | 769 | } |
838 | |||
839 | acpi_gbl_memory_lists[ACPI_MEM_LIST_NSNODE].object_size = sizeof (struct acpi_namespace_node); | ||
840 | acpi_gbl_memory_lists[ACPI_MEM_LIST_STATE].object_size = sizeof (union acpi_generic_state); | ||
841 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE].object_size = sizeof (struct acpi_parse_obj_common); | ||
842 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE_EXT].object_size = sizeof (struct acpi_parse_obj_named); | ||
843 | acpi_gbl_memory_lists[ACPI_MEM_LIST_OPERAND].object_size = sizeof (union acpi_operand_object); | ||
844 | acpi_gbl_memory_lists[ACPI_MEM_LIST_WALK].object_size = sizeof (struct acpi_walk_state); | ||
845 | |||
846 | acpi_gbl_memory_lists[ACPI_MEM_LIST_STATE].max_cache_depth = ACPI_MAX_STATE_CACHE_DEPTH; | ||
847 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE].max_cache_depth = ACPI_MAX_PARSE_CACHE_DEPTH; | ||
848 | acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE_EXT].max_cache_depth = ACPI_MAX_EXTPARSE_CACHE_DEPTH; | ||
849 | acpi_gbl_memory_lists[ACPI_MEM_LIST_OPERAND].max_cache_depth = ACPI_MAX_OBJECT_CACHE_DEPTH; | ||
850 | acpi_gbl_memory_lists[ACPI_MEM_LIST_WALK].max_cache_depth = ACPI_MAX_WALK_CACHE_DEPTH; | ||
851 | |||
852 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_GLOBAL].list_name = "Global Memory Allocation"); | ||
853 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_NSNODE].list_name = "Namespace Nodes"); | ||
854 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_STATE].list_name = "State Object Cache"); | ||
855 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE].list_name = "Parse Node Cache"); | ||
856 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_PSNODE_EXT].list_name = "Extended Parse Node Cache"); | ||
857 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_OPERAND].list_name = "Operand Object Cache"); | ||
858 | ACPI_MEM_TRACKING (acpi_gbl_memory_lists[ACPI_MEM_LIST_WALK].list_name = "Tree Walk Node Cache"); | ||
859 | 770 | ||
860 | /* ACPI table structure */ | 771 | /* ACPI table structure */ |
861 | 772 | ||
@@ -870,7 +781,7 @@ acpi_ut_init_globals ( | |||
870 | for (i = 0; i < NUM_MUTEX; i++) | 781 | for (i = 0; i < NUM_MUTEX; i++) |
871 | { | 782 | { |
872 | acpi_gbl_mutex_info[i].mutex = NULL; | 783 | acpi_gbl_mutex_info[i].mutex = NULL; |
873 | acpi_gbl_mutex_info[i].owner_id = ACPI_MUTEX_NOT_ACQUIRED; | 784 | acpi_gbl_mutex_info[i].thread_id = ACPI_MUTEX_NOT_ACQUIRED; |
874 | acpi_gbl_mutex_info[i].use_count = 0; | 785 | acpi_gbl_mutex_info[i].use_count = 0; |
875 | } | 786 | } |
876 | 787 | ||
@@ -911,8 +822,7 @@ acpi_ut_init_globals ( | |||
911 | acpi_gbl_ns_lookup_count = 0; | 822 | acpi_gbl_ns_lookup_count = 0; |
912 | acpi_gbl_ps_find_count = 0; | 823 | acpi_gbl_ps_find_count = 0; |
913 | acpi_gbl_acpi_hardware_present = TRUE; | 824 | acpi_gbl_acpi_hardware_present = TRUE; |
914 | acpi_gbl_next_table_owner_id = ACPI_FIRST_TABLE_ID; | 825 | acpi_gbl_owner_id_mask = 0; |
915 | acpi_gbl_next_method_owner_id = ACPI_FIRST_METHOD_ID; | ||
916 | acpi_gbl_debugger_configuration = DEBUGGER_THREADING; | 826 | acpi_gbl_debugger_configuration = DEBUGGER_THREADING; |
917 | acpi_gbl_db_output_flags = ACPI_DB_CONSOLE_OUTPUT; | 827 | acpi_gbl_db_output_flags = ACPI_DB_CONSOLE_OUTPUT; |
918 | 828 | ||
diff --git a/drivers/acpi/utilities/utinit.c b/drivers/acpi/utilities/utinit.c index 7f3713889ff0..fd7ceba83229 100644 --- a/drivers/acpi/utilities/utinit.c +++ b/drivers/acpi/utilities/utinit.c | |||
@@ -264,7 +264,7 @@ acpi_ut_subsystem_shutdown ( | |||
264 | 264 | ||
265 | /* Purge the local caches */ | 265 | /* Purge the local caches */ |
266 | 266 | ||
267 | (void) acpi_purge_cached_objects (); | 267 | (void) acpi_ut_delete_caches (); |
268 | 268 | ||
269 | /* Debug only - display leftover memory allocation, if any */ | 269 | /* Debug only - display leftover memory allocation, if any */ |
270 | 270 | ||
diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index f6de4ed3d527..1d350b302a34 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c | |||
@@ -49,15 +49,121 @@ | |||
49 | #define _COMPONENT ACPI_UTILITIES | 49 | #define _COMPONENT ACPI_UTILITIES |
50 | ACPI_MODULE_NAME ("utmisc") | 50 | ACPI_MODULE_NAME ("utmisc") |
51 | 51 | ||
52 | /* Local prototypes */ | ||
53 | 52 | ||
54 | static acpi_status | 53 | /******************************************************************************* |
55 | acpi_ut_create_mutex ( | 54 | * |
56 | acpi_mutex_handle mutex_id); | 55 | * FUNCTION: acpi_ut_allocate_owner_id |
56 | * | ||
57 | * PARAMETERS: owner_id - Where the new owner ID is returned | ||
58 | * | ||
59 | * RETURN: Status | ||
60 | * | ||
61 | * DESCRIPTION: Allocate a table or method owner ID. The owner ID is used to | ||
62 | * track objects created by the table or method, to be deleted | ||
63 | * when the method exits or the table is unloaded. | ||
64 | * | ||
65 | ******************************************************************************/ | ||
66 | |||
67 | acpi_status | ||
68 | acpi_ut_allocate_owner_id ( | ||
69 | acpi_owner_id *owner_id) | ||
70 | { | ||
71 | acpi_native_uint i; | ||
72 | acpi_status status; | ||
73 | |||
74 | |||
75 | ACPI_FUNCTION_TRACE ("ut_allocate_owner_id"); | ||
57 | 76 | ||
58 | static acpi_status | 77 | |
59 | acpi_ut_delete_mutex ( | 78 | /* Mutex for the global ID mask */ |
60 | acpi_mutex_handle mutex_id); | 79 | |
80 | status = acpi_ut_acquire_mutex (ACPI_MTX_CACHES); | ||
81 | if (ACPI_FAILURE (status)) { | ||
82 | return_ACPI_STATUS (status); | ||
83 | } | ||
84 | |||
85 | /* Find a free owner ID */ | ||
86 | |||
87 | for (i = 0; i < 32; i++) { | ||
88 | if (!(acpi_gbl_owner_id_mask & (1 << i))) { | ||
89 | acpi_gbl_owner_id_mask |= (1 << i); | ||
90 | *owner_id = (acpi_owner_id) (i + 1); | ||
91 | goto exit; | ||
92 | } | ||
93 | } | ||
94 | |||
95 | /* | ||
96 | * If we are here, all owner_ids have been allocated. This probably should | ||
97 | * not happen since the IDs are reused after deallocation. The IDs are | ||
98 | * allocated upon table load (one per table) and method execution, and | ||
99 | * they are released when a table is unloaded or a method completes | ||
100 | * execution. | ||
101 | */ | ||
102 | *owner_id = 0; | ||
103 | status = AE_OWNER_ID_LIMIT; | ||
104 | ACPI_REPORT_ERROR (( | ||
105 | "Could not allocate new owner_id (32 max), AE_OWNER_ID_LIMIT\n")); | ||
106 | |||
107 | exit: | ||
108 | (void) acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
109 | return_ACPI_STATUS (status); | ||
110 | } | ||
111 | |||
112 | |||
113 | /******************************************************************************* | ||
114 | * | ||
115 | * FUNCTION: acpi_ut_release_owner_id | ||
116 | * | ||
117 | * PARAMETERS: owner_id_ptr - Pointer to a previously allocated owner_iD | ||
118 | * | ||
119 | * RETURN: None. No error is returned because we are either exiting a | ||
120 | * control method or unloading a table. Either way, we would | ||
121 | * ignore any error anyway. | ||
122 | * | ||
123 | * DESCRIPTION: Release a table or method owner ID. Valid IDs are 1 - 32 | ||
124 | * | ||
125 | ******************************************************************************/ | ||
126 | |||
127 | void | ||
128 | acpi_ut_release_owner_id ( | ||
129 | acpi_owner_id *owner_id_ptr) | ||
130 | { | ||
131 | acpi_owner_id owner_id = *owner_id_ptr; | ||
132 | acpi_status status; | ||
133 | |||
134 | |||
135 | ACPI_FUNCTION_TRACE ("ut_release_owner_id"); | ||
136 | |||
137 | |||
138 | /* Always clear the input owner_id (zero is an invalid ID) */ | ||
139 | |||
140 | *owner_id_ptr = 0; | ||
141 | |||
142 | /* Zero is not a valid owner_iD */ | ||
143 | |||
144 | if ((owner_id == 0) || (owner_id > 32)) { | ||
145 | ACPI_REPORT_ERROR (("Invalid owner_id: %2.2X\n", owner_id)); | ||
146 | return_VOID; | ||
147 | } | ||
148 | |||
149 | /* Mutex for the global ID mask */ | ||
150 | |||
151 | status = acpi_ut_acquire_mutex (ACPI_MTX_CACHES); | ||
152 | if (ACPI_FAILURE (status)) { | ||
153 | return_VOID; | ||
154 | } | ||
155 | |||
156 | owner_id--; /* Normalize to zero */ | ||
157 | |||
158 | /* Free the owner ID only if it is valid */ | ||
159 | |||
160 | if (acpi_gbl_owner_id_mask & (1 << owner_id)) { | ||
161 | acpi_gbl_owner_id_mask ^= (1 << owner_id); | ||
162 | } | ||
163 | |||
164 | (void) acpi_ut_release_mutex (ACPI_MTX_CACHES); | ||
165 | return_VOID; | ||
166 | } | ||
61 | 167 | ||
62 | 168 | ||
63 | /******************************************************************************* | 169 | /******************************************************************************* |
@@ -66,7 +172,7 @@ acpi_ut_delete_mutex ( | |||
66 | * | 172 | * |
67 | * PARAMETERS: src_string - The source string to convert | 173 | * PARAMETERS: src_string - The source string to convert |
68 | * | 174 | * |
69 | * RETURN: Converted src_string (same as input pointer) | 175 | * RETURN: None |
70 | * | 176 | * |
71 | * DESCRIPTION: Convert string to uppercase | 177 | * DESCRIPTION: Convert string to uppercase |
72 | * | 178 | * |
@@ -74,7 +180,7 @@ acpi_ut_delete_mutex ( | |||
74 | * | 180 | * |
75 | ******************************************************************************/ | 181 | ******************************************************************************/ |
76 | 182 | ||
77 | char * | 183 | void |
78 | acpi_ut_strupr ( | 184 | acpi_ut_strupr ( |
79 | char *src_string) | 185 | char *src_string) |
80 | { | 186 | { |
@@ -84,13 +190,17 @@ acpi_ut_strupr ( | |||
84 | ACPI_FUNCTION_ENTRY (); | 190 | ACPI_FUNCTION_ENTRY (); |
85 | 191 | ||
86 | 192 | ||
193 | if (!src_string) { | ||
194 | return; | ||
195 | } | ||
196 | |||
87 | /* Walk entire string, uppercasing the letters */ | 197 | /* Walk entire string, uppercasing the letters */ |
88 | 198 | ||
89 | for (string = src_string; *string; string++) { | 199 | for (string = src_string; *string; string++) { |
90 | *string = (char) ACPI_TOUPPER (*string); | 200 | *string = (char) ACPI_TOUPPER (*string); |
91 | } | 201 | } |
92 | 202 | ||
93 | return (src_string); | 203 | return; |
94 | } | 204 | } |
95 | 205 | ||
96 | 206 | ||
@@ -543,320 +653,6 @@ error_exit: | |||
543 | 653 | ||
544 | /******************************************************************************* | 654 | /******************************************************************************* |
545 | * | 655 | * |
546 | * FUNCTION: acpi_ut_mutex_initialize | ||
547 | * | ||
548 | * PARAMETERS: None. | ||
549 | * | ||
550 | * RETURN: Status | ||
551 | * | ||
552 | * DESCRIPTION: Create the system mutex objects. | ||
553 | * | ||
554 | ******************************************************************************/ | ||
555 | |||
556 | acpi_status | ||
557 | acpi_ut_mutex_initialize ( | ||
558 | void) | ||
559 | { | ||
560 | u32 i; | ||
561 | acpi_status status; | ||
562 | |||
563 | |||
564 | ACPI_FUNCTION_TRACE ("ut_mutex_initialize"); | ||
565 | |||
566 | |||
567 | /* | ||
568 | * Create each of the predefined mutex objects | ||
569 | */ | ||
570 | for (i = 0; i < NUM_MUTEX; i++) { | ||
571 | status = acpi_ut_create_mutex (i); | ||
572 | if (ACPI_FAILURE (status)) { | ||
573 | return_ACPI_STATUS (status); | ||
574 | } | ||
575 | } | ||
576 | |||
577 | status = acpi_os_create_lock (&acpi_gbl_gpe_lock); | ||
578 | return_ACPI_STATUS (status); | ||
579 | } | ||
580 | |||
581 | |||
582 | /******************************************************************************* | ||
583 | * | ||
584 | * FUNCTION: acpi_ut_mutex_terminate | ||
585 | * | ||
586 | * PARAMETERS: None. | ||
587 | * | ||
588 | * RETURN: None. | ||
589 | * | ||
590 | * DESCRIPTION: Delete all of the system mutex objects. | ||
591 | * | ||
592 | ******************************************************************************/ | ||
593 | |||
594 | void | ||
595 | acpi_ut_mutex_terminate ( | ||
596 | void) | ||
597 | { | ||
598 | u32 i; | ||
599 | |||
600 | |||
601 | ACPI_FUNCTION_TRACE ("ut_mutex_terminate"); | ||
602 | |||
603 | |||
604 | /* | ||
605 | * Delete each predefined mutex object | ||
606 | */ | ||
607 | for (i = 0; i < NUM_MUTEX; i++) { | ||
608 | (void) acpi_ut_delete_mutex (i); | ||
609 | } | ||
610 | |||
611 | acpi_os_delete_lock (acpi_gbl_gpe_lock); | ||
612 | return_VOID; | ||
613 | } | ||
614 | |||
615 | |||
616 | /******************************************************************************* | ||
617 | * | ||
618 | * FUNCTION: acpi_ut_create_mutex | ||
619 | * | ||
620 | * PARAMETERS: mutex_iD - ID of the mutex to be created | ||
621 | * | ||
622 | * RETURN: Status | ||
623 | * | ||
624 | * DESCRIPTION: Create a mutex object. | ||
625 | * | ||
626 | ******************************************************************************/ | ||
627 | |||
628 | static acpi_status | ||
629 | acpi_ut_create_mutex ( | ||
630 | acpi_mutex_handle mutex_id) | ||
631 | { | ||
632 | acpi_status status = AE_OK; | ||
633 | |||
634 | |||
635 | ACPI_FUNCTION_TRACE_U32 ("ut_create_mutex", mutex_id); | ||
636 | |||
637 | |||
638 | if (mutex_id > MAX_MUTEX) { | ||
639 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
640 | } | ||
641 | |||
642 | if (!acpi_gbl_mutex_info[mutex_id].mutex) { | ||
643 | status = acpi_os_create_semaphore (1, 1, | ||
644 | &acpi_gbl_mutex_info[mutex_id].mutex); | ||
645 | acpi_gbl_mutex_info[mutex_id].owner_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
646 | acpi_gbl_mutex_info[mutex_id].use_count = 0; | ||
647 | } | ||
648 | |||
649 | return_ACPI_STATUS (status); | ||
650 | } | ||
651 | |||
652 | |||
653 | /******************************************************************************* | ||
654 | * | ||
655 | * FUNCTION: acpi_ut_delete_mutex | ||
656 | * | ||
657 | * PARAMETERS: mutex_iD - ID of the mutex to be deleted | ||
658 | * | ||
659 | * RETURN: Status | ||
660 | * | ||
661 | * DESCRIPTION: Delete a mutex object. | ||
662 | * | ||
663 | ******************************************************************************/ | ||
664 | |||
665 | static acpi_status | ||
666 | acpi_ut_delete_mutex ( | ||
667 | acpi_mutex_handle mutex_id) | ||
668 | { | ||
669 | acpi_status status; | ||
670 | |||
671 | |||
672 | ACPI_FUNCTION_TRACE_U32 ("ut_delete_mutex", mutex_id); | ||
673 | |||
674 | |||
675 | if (mutex_id > MAX_MUTEX) { | ||
676 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
677 | } | ||
678 | |||
679 | status = acpi_os_delete_semaphore (acpi_gbl_mutex_info[mutex_id].mutex); | ||
680 | |||
681 | acpi_gbl_mutex_info[mutex_id].mutex = NULL; | ||
682 | acpi_gbl_mutex_info[mutex_id].owner_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
683 | |||
684 | return_ACPI_STATUS (status); | ||
685 | } | ||
686 | |||
687 | |||
688 | /******************************************************************************* | ||
689 | * | ||
690 | * FUNCTION: acpi_ut_acquire_mutex | ||
691 | * | ||
692 | * PARAMETERS: mutex_iD - ID of the mutex to be acquired | ||
693 | * | ||
694 | * RETURN: Status | ||
695 | * | ||
696 | * DESCRIPTION: Acquire a mutex object. | ||
697 | * | ||
698 | ******************************************************************************/ | ||
699 | |||
700 | acpi_status | ||
701 | acpi_ut_acquire_mutex ( | ||
702 | acpi_mutex_handle mutex_id) | ||
703 | { | ||
704 | acpi_status status; | ||
705 | u32 this_thread_id; | ||
706 | |||
707 | |||
708 | ACPI_FUNCTION_NAME ("ut_acquire_mutex"); | ||
709 | |||
710 | |||
711 | if (mutex_id > MAX_MUTEX) { | ||
712 | return (AE_BAD_PARAMETER); | ||
713 | } | ||
714 | |||
715 | this_thread_id = acpi_os_get_thread_id (); | ||
716 | |||
717 | #ifdef ACPI_MUTEX_DEBUG | ||
718 | { | ||
719 | u32 i; | ||
720 | /* | ||
721 | * Mutex debug code, for internal debugging only. | ||
722 | * | ||
723 | * Deadlock prevention. Check if this thread owns any mutexes of value | ||
724 | * greater than or equal to this one. If so, the thread has violated | ||
725 | * the mutex ordering rule. This indicates a coding error somewhere in | ||
726 | * the ACPI subsystem code. | ||
727 | */ | ||
728 | for (i = mutex_id; i < MAX_MUTEX; i++) { | ||
729 | if (acpi_gbl_mutex_info[i].owner_id == this_thread_id) { | ||
730 | if (i == mutex_id) { | ||
731 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
732 | "Mutex [%s] already acquired by this thread [%X]\n", | ||
733 | acpi_ut_get_mutex_name (mutex_id), this_thread_id)); | ||
734 | |||
735 | return (AE_ALREADY_ACQUIRED); | ||
736 | } | ||
737 | |||
738 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
739 | "Invalid acquire order: Thread %X owns [%s], wants [%s]\n", | ||
740 | this_thread_id, acpi_ut_get_mutex_name (i), | ||
741 | acpi_ut_get_mutex_name (mutex_id))); | ||
742 | |||
743 | return (AE_ACQUIRE_DEADLOCK); | ||
744 | } | ||
745 | } | ||
746 | } | ||
747 | #endif | ||
748 | |||
749 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, | ||
750 | "Thread %X attempting to acquire Mutex [%s]\n", | ||
751 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
752 | |||
753 | status = acpi_os_wait_semaphore (acpi_gbl_mutex_info[mutex_id].mutex, | ||
754 | 1, ACPI_WAIT_FOREVER); | ||
755 | if (ACPI_SUCCESS (status)) { | ||
756 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Thread %X acquired Mutex [%s]\n", | ||
757 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
758 | |||
759 | acpi_gbl_mutex_info[mutex_id].use_count++; | ||
760 | acpi_gbl_mutex_info[mutex_id].owner_id = this_thread_id; | ||
761 | } | ||
762 | else { | ||
763 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
764 | "Thread %X could not acquire Mutex [%s] %s\n", | ||
765 | this_thread_id, acpi_ut_get_mutex_name (mutex_id), | ||
766 | acpi_format_exception (status))); | ||
767 | } | ||
768 | |||
769 | return (status); | ||
770 | } | ||
771 | |||
772 | |||
773 | /******************************************************************************* | ||
774 | * | ||
775 | * FUNCTION: acpi_ut_release_mutex | ||
776 | * | ||
777 | * PARAMETERS: mutex_iD - ID of the mutex to be released | ||
778 | * | ||
779 | * RETURN: Status | ||
780 | * | ||
781 | * DESCRIPTION: Release a mutex object. | ||
782 | * | ||
783 | ******************************************************************************/ | ||
784 | |||
785 | acpi_status | ||
786 | acpi_ut_release_mutex ( | ||
787 | acpi_mutex_handle mutex_id) | ||
788 | { | ||
789 | acpi_status status; | ||
790 | u32 i; | ||
791 | u32 this_thread_id; | ||
792 | |||
793 | |||
794 | ACPI_FUNCTION_NAME ("ut_release_mutex"); | ||
795 | |||
796 | |||
797 | this_thread_id = acpi_os_get_thread_id (); | ||
798 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, | ||
799 | "Thread %X releasing Mutex [%s]\n", this_thread_id, | ||
800 | acpi_ut_get_mutex_name (mutex_id))); | ||
801 | |||
802 | if (mutex_id > MAX_MUTEX) { | ||
803 | return (AE_BAD_PARAMETER); | ||
804 | } | ||
805 | |||
806 | /* | ||
807 | * Mutex must be acquired in order to release it! | ||
808 | */ | ||
809 | if (acpi_gbl_mutex_info[mutex_id].owner_id == ACPI_MUTEX_NOT_ACQUIRED) { | ||
810 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
811 | "Mutex [%s] is not acquired, cannot release\n", | ||
812 | acpi_ut_get_mutex_name (mutex_id))); | ||
813 | |||
814 | return (AE_NOT_ACQUIRED); | ||
815 | } | ||
816 | |||
817 | /* | ||
818 | * Deadlock prevention. Check if this thread owns any mutexes of value | ||
819 | * greater than this one. If so, the thread has violated the mutex | ||
820 | * ordering rule. This indicates a coding error somewhere in | ||
821 | * the ACPI subsystem code. | ||
822 | */ | ||
823 | for (i = mutex_id; i < MAX_MUTEX; i++) { | ||
824 | if (acpi_gbl_mutex_info[i].owner_id == this_thread_id) { | ||
825 | if (i == mutex_id) { | ||
826 | continue; | ||
827 | } | ||
828 | |||
829 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
830 | "Invalid release order: owns [%s], releasing [%s]\n", | ||
831 | acpi_ut_get_mutex_name (i), acpi_ut_get_mutex_name (mutex_id))); | ||
832 | |||
833 | return (AE_RELEASE_DEADLOCK); | ||
834 | } | ||
835 | } | ||
836 | |||
837 | /* Mark unlocked FIRST */ | ||
838 | |||
839 | acpi_gbl_mutex_info[mutex_id].owner_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
840 | |||
841 | status = acpi_os_signal_semaphore (acpi_gbl_mutex_info[mutex_id].mutex, 1); | ||
842 | |||
843 | if (ACPI_FAILURE (status)) { | ||
844 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
845 | "Thread %X could not release Mutex [%s] %s\n", | ||
846 | this_thread_id, acpi_ut_get_mutex_name (mutex_id), | ||
847 | acpi_format_exception (status))); | ||
848 | } | ||
849 | else { | ||
850 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Thread %X released Mutex [%s]\n", | ||
851 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
852 | } | ||
853 | |||
854 | return (status); | ||
855 | } | ||
856 | |||
857 | |||
858 | /******************************************************************************* | ||
859 | * | ||
860 | * FUNCTION: acpi_ut_create_update_state_and_push | 656 | * FUNCTION: acpi_ut_create_update_state_and_push |
861 | * | 657 | * |
862 | * PARAMETERS: Object - Object to be added to the new state | 658 | * PARAMETERS: Object - Object to be added to the new state |
@@ -899,361 +695,6 @@ acpi_ut_create_update_state_and_push ( | |||
899 | 695 | ||
900 | /******************************************************************************* | 696 | /******************************************************************************* |
901 | * | 697 | * |
902 | * FUNCTION: acpi_ut_create_pkg_state_and_push | ||
903 | * | ||
904 | * PARAMETERS: Object - Object to be added to the new state | ||
905 | * Action - Increment/Decrement | ||
906 | * state_list - List the state will be added to | ||
907 | * | ||
908 | * RETURN: Status | ||
909 | * | ||
910 | * DESCRIPTION: Create a new state and push it | ||
911 | * | ||
912 | ******************************************************************************/ | ||
913 | |||
914 | #ifdef ACPI_FUTURE_USAGE | ||
915 | acpi_status | ||
916 | acpi_ut_create_pkg_state_and_push ( | ||
917 | void *internal_object, | ||
918 | void *external_object, | ||
919 | u16 index, | ||
920 | union acpi_generic_state **state_list) | ||
921 | { | ||
922 | union acpi_generic_state *state; | ||
923 | |||
924 | |||
925 | ACPI_FUNCTION_ENTRY (); | ||
926 | |||
927 | |||
928 | state = acpi_ut_create_pkg_state (internal_object, external_object, index); | ||
929 | if (!state) { | ||
930 | return (AE_NO_MEMORY); | ||
931 | } | ||
932 | |||
933 | acpi_ut_push_generic_state (state_list, state); | ||
934 | return (AE_OK); | ||
935 | } | ||
936 | #endif /* ACPI_FUTURE_USAGE */ | ||
937 | |||
938 | /******************************************************************************* | ||
939 | * | ||
940 | * FUNCTION: acpi_ut_push_generic_state | ||
941 | * | ||
942 | * PARAMETERS: list_head - Head of the state stack | ||
943 | * State - State object to push | ||
944 | * | ||
945 | * RETURN: None | ||
946 | * | ||
947 | * DESCRIPTION: Push a state object onto a state stack | ||
948 | * | ||
949 | ******************************************************************************/ | ||
950 | |||
951 | void | ||
952 | acpi_ut_push_generic_state ( | ||
953 | union acpi_generic_state **list_head, | ||
954 | union acpi_generic_state *state) | ||
955 | { | ||
956 | ACPI_FUNCTION_TRACE ("ut_push_generic_state"); | ||
957 | |||
958 | |||
959 | /* Push the state object onto the front of the list (stack) */ | ||
960 | |||
961 | state->common.next = *list_head; | ||
962 | *list_head = state; | ||
963 | |||
964 | return_VOID; | ||
965 | } | ||
966 | |||
967 | |||
968 | /******************************************************************************* | ||
969 | * | ||
970 | * FUNCTION: acpi_ut_pop_generic_state | ||
971 | * | ||
972 | * PARAMETERS: list_head - Head of the state stack | ||
973 | * | ||
974 | * RETURN: The popped state object | ||
975 | * | ||
976 | * DESCRIPTION: Pop a state object from a state stack | ||
977 | * | ||
978 | ******************************************************************************/ | ||
979 | |||
980 | union acpi_generic_state * | ||
981 | acpi_ut_pop_generic_state ( | ||
982 | union acpi_generic_state **list_head) | ||
983 | { | ||
984 | union acpi_generic_state *state; | ||
985 | |||
986 | |||
987 | ACPI_FUNCTION_TRACE ("ut_pop_generic_state"); | ||
988 | |||
989 | |||
990 | /* Remove the state object at the head of the list (stack) */ | ||
991 | |||
992 | state = *list_head; | ||
993 | if (state) { | ||
994 | /* Update the list head */ | ||
995 | |||
996 | *list_head = state->common.next; | ||
997 | } | ||
998 | |||
999 | return_PTR (state); | ||
1000 | } | ||
1001 | |||
1002 | |||
1003 | /******************************************************************************* | ||
1004 | * | ||
1005 | * FUNCTION: acpi_ut_create_generic_state | ||
1006 | * | ||
1007 | * PARAMETERS: None | ||
1008 | * | ||
1009 | * RETURN: The new state object. NULL on failure. | ||
1010 | * | ||
1011 | * DESCRIPTION: Create a generic state object. Attempt to obtain one from | ||
1012 | * the global state cache; If none available, create a new one. | ||
1013 | * | ||
1014 | ******************************************************************************/ | ||
1015 | |||
1016 | union acpi_generic_state * | ||
1017 | acpi_ut_create_generic_state ( | ||
1018 | void) | ||
1019 | { | ||
1020 | union acpi_generic_state *state; | ||
1021 | |||
1022 | |||
1023 | ACPI_FUNCTION_ENTRY (); | ||
1024 | |||
1025 | |||
1026 | state = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_STATE); | ||
1027 | |||
1028 | /* Initialize */ | ||
1029 | |||
1030 | if (state) { | ||
1031 | state->common.data_type = ACPI_DESC_TYPE_STATE; | ||
1032 | } | ||
1033 | |||
1034 | return (state); | ||
1035 | } | ||
1036 | |||
1037 | |||
1038 | /******************************************************************************* | ||
1039 | * | ||
1040 | * FUNCTION: acpi_ut_create_thread_state | ||
1041 | * | ||
1042 | * PARAMETERS: None | ||
1043 | * | ||
1044 | * RETURN: New Thread State. NULL on failure | ||
1045 | * | ||
1046 | * DESCRIPTION: Create a "Thread State" - a flavor of the generic state used | ||
1047 | * to track per-thread info during method execution | ||
1048 | * | ||
1049 | ******************************************************************************/ | ||
1050 | |||
1051 | struct acpi_thread_state * | ||
1052 | acpi_ut_create_thread_state ( | ||
1053 | void) | ||
1054 | { | ||
1055 | union acpi_generic_state *state; | ||
1056 | |||
1057 | |||
1058 | ACPI_FUNCTION_TRACE ("ut_create_thread_state"); | ||
1059 | |||
1060 | |||
1061 | /* Create the generic state object */ | ||
1062 | |||
1063 | state = acpi_ut_create_generic_state (); | ||
1064 | if (!state) { | ||
1065 | return_PTR (NULL); | ||
1066 | } | ||
1067 | |||
1068 | /* Init fields specific to the update struct */ | ||
1069 | |||
1070 | state->common.data_type = ACPI_DESC_TYPE_STATE_THREAD; | ||
1071 | state->thread.thread_id = acpi_os_get_thread_id (); | ||
1072 | |||
1073 | return_PTR ((struct acpi_thread_state *) state); | ||
1074 | } | ||
1075 | |||
1076 | |||
1077 | /******************************************************************************* | ||
1078 | * | ||
1079 | * FUNCTION: acpi_ut_create_update_state | ||
1080 | * | ||
1081 | * PARAMETERS: Object - Initial Object to be installed in the state | ||
1082 | * Action - Update action to be performed | ||
1083 | * | ||
1084 | * RETURN: New state object, null on failure | ||
1085 | * | ||
1086 | * DESCRIPTION: Create an "Update State" - a flavor of the generic state used | ||
1087 | * to update reference counts and delete complex objects such | ||
1088 | * as packages. | ||
1089 | * | ||
1090 | ******************************************************************************/ | ||
1091 | |||
1092 | union acpi_generic_state * | ||
1093 | acpi_ut_create_update_state ( | ||
1094 | union acpi_operand_object *object, | ||
1095 | u16 action) | ||
1096 | { | ||
1097 | union acpi_generic_state *state; | ||
1098 | |||
1099 | |||
1100 | ACPI_FUNCTION_TRACE_PTR ("ut_create_update_state", object); | ||
1101 | |||
1102 | |||
1103 | /* Create the generic state object */ | ||
1104 | |||
1105 | state = acpi_ut_create_generic_state (); | ||
1106 | if (!state) { | ||
1107 | return_PTR (NULL); | ||
1108 | } | ||
1109 | |||
1110 | /* Init fields specific to the update struct */ | ||
1111 | |||
1112 | state->common.data_type = ACPI_DESC_TYPE_STATE_UPDATE; | ||
1113 | state->update.object = object; | ||
1114 | state->update.value = action; | ||
1115 | |||
1116 | return_PTR (state); | ||
1117 | } | ||
1118 | |||
1119 | |||
1120 | /******************************************************************************* | ||
1121 | * | ||
1122 | * FUNCTION: acpi_ut_create_pkg_state | ||
1123 | * | ||
1124 | * PARAMETERS: Object - Initial Object to be installed in the state | ||
1125 | * Action - Update action to be performed | ||
1126 | * | ||
1127 | * RETURN: New state object, null on failure | ||
1128 | * | ||
1129 | * DESCRIPTION: Create a "Package State" | ||
1130 | * | ||
1131 | ******************************************************************************/ | ||
1132 | |||
1133 | union acpi_generic_state * | ||
1134 | acpi_ut_create_pkg_state ( | ||
1135 | void *internal_object, | ||
1136 | void *external_object, | ||
1137 | u16 index) | ||
1138 | { | ||
1139 | union acpi_generic_state *state; | ||
1140 | |||
1141 | |||
1142 | ACPI_FUNCTION_TRACE_PTR ("ut_create_pkg_state", internal_object); | ||
1143 | |||
1144 | |||
1145 | /* Create the generic state object */ | ||
1146 | |||
1147 | state = acpi_ut_create_generic_state (); | ||
1148 | if (!state) { | ||
1149 | return_PTR (NULL); | ||
1150 | } | ||
1151 | |||
1152 | /* Init fields specific to the update struct */ | ||
1153 | |||
1154 | state->common.data_type = ACPI_DESC_TYPE_STATE_PACKAGE; | ||
1155 | state->pkg.source_object = (union acpi_operand_object *) internal_object; | ||
1156 | state->pkg.dest_object = external_object; | ||
1157 | state->pkg.index = index; | ||
1158 | state->pkg.num_packages = 1; | ||
1159 | |||
1160 | return_PTR (state); | ||
1161 | } | ||
1162 | |||
1163 | |||
1164 | /******************************************************************************* | ||
1165 | * | ||
1166 | * FUNCTION: acpi_ut_create_control_state | ||
1167 | * | ||
1168 | * PARAMETERS: None | ||
1169 | * | ||
1170 | * RETURN: New state object, null on failure | ||
1171 | * | ||
1172 | * DESCRIPTION: Create a "Control State" - a flavor of the generic state used | ||
1173 | * to support nested IF/WHILE constructs in the AML. | ||
1174 | * | ||
1175 | ******************************************************************************/ | ||
1176 | |||
1177 | union acpi_generic_state * | ||
1178 | acpi_ut_create_control_state ( | ||
1179 | void) | ||
1180 | { | ||
1181 | union acpi_generic_state *state; | ||
1182 | |||
1183 | |||
1184 | ACPI_FUNCTION_TRACE ("ut_create_control_state"); | ||
1185 | |||
1186 | |||
1187 | /* Create the generic state object */ | ||
1188 | |||
1189 | state = acpi_ut_create_generic_state (); | ||
1190 | if (!state) { | ||
1191 | return_PTR (NULL); | ||
1192 | } | ||
1193 | |||
1194 | /* Init fields specific to the control struct */ | ||
1195 | |||
1196 | state->common.data_type = ACPI_DESC_TYPE_STATE_CONTROL; | ||
1197 | state->common.state = ACPI_CONTROL_CONDITIONAL_EXECUTING; | ||
1198 | |||
1199 | return_PTR (state); | ||
1200 | } | ||
1201 | |||
1202 | |||
1203 | /******************************************************************************* | ||
1204 | * | ||
1205 | * FUNCTION: acpi_ut_delete_generic_state | ||
1206 | * | ||
1207 | * PARAMETERS: State - The state object to be deleted | ||
1208 | * | ||
1209 | * RETURN: None | ||
1210 | * | ||
1211 | * DESCRIPTION: Put a state object back into the global state cache. The object | ||
1212 | * is not actually freed at this time. | ||
1213 | * | ||
1214 | ******************************************************************************/ | ||
1215 | |||
1216 | void | ||
1217 | acpi_ut_delete_generic_state ( | ||
1218 | union acpi_generic_state *state) | ||
1219 | { | ||
1220 | ACPI_FUNCTION_TRACE ("ut_delete_generic_state"); | ||
1221 | |||
1222 | |||
1223 | acpi_ut_release_to_cache (ACPI_MEM_LIST_STATE, state); | ||
1224 | return_VOID; | ||
1225 | } | ||
1226 | |||
1227 | |||
1228 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
1229 | /******************************************************************************* | ||
1230 | * | ||
1231 | * FUNCTION: acpi_ut_delete_generic_state_cache | ||
1232 | * | ||
1233 | * PARAMETERS: None | ||
1234 | * | ||
1235 | * RETURN: None | ||
1236 | * | ||
1237 | * DESCRIPTION: Purge the global state object cache. Used during subsystem | ||
1238 | * termination. | ||
1239 | * | ||
1240 | ******************************************************************************/ | ||
1241 | |||
1242 | void | ||
1243 | acpi_ut_delete_generic_state_cache ( | ||
1244 | void) | ||
1245 | { | ||
1246 | ACPI_FUNCTION_TRACE ("ut_delete_generic_state_cache"); | ||
1247 | |||
1248 | |||
1249 | acpi_ut_delete_generic_cache (ACPI_MEM_LIST_STATE); | ||
1250 | return_VOID; | ||
1251 | } | ||
1252 | #endif | ||
1253 | |||
1254 | |||
1255 | /******************************************************************************* | ||
1256 | * | ||
1257 | * FUNCTION: acpi_ut_walk_package_tree | 698 | * FUNCTION: acpi_ut_walk_package_tree |
1258 | * | 699 | * |
1259 | * PARAMETERS: source_object - The package to walk | 700 | * PARAMETERS: source_object - The package to walk |
diff --git a/drivers/acpi/utilities/utmutex.c b/drivers/acpi/utilities/utmutex.c new file mode 100644 index 000000000000..0699b6be62b6 --- /dev/null +++ b/drivers/acpi/utilities/utmutex.c | |||
@@ -0,0 +1,380 @@ | |||
1 | /******************************************************************************* | ||
2 | * | ||
3 | * Module Name: utmutex - local mutex support | ||
4 | * | ||
5 | ******************************************************************************/ | ||
6 | |||
7 | /* | ||
8 | * Copyright (C) 2000 - 2005, R. Byron Moore | ||
9 | * All rights reserved. | ||
10 | * | ||
11 | * Redistribution and use in source and binary forms, with or without | ||
12 | * modification, are permitted provided that the following conditions | ||
13 | * are met: | ||
14 | * 1. Redistributions of source code must retain the above copyright | ||
15 | * notice, this list of conditions, and the following disclaimer, | ||
16 | * without modification. | ||
17 | * 2. Redistributions in binary form must reproduce at minimum a disclaimer | ||
18 | * substantially similar to the "NO WARRANTY" disclaimer below | ||
19 | * ("Disclaimer") and any redistribution must be conditioned upon | ||
20 | * including a substantially similar Disclaimer requirement for further | ||
21 | * binary redistribution. | ||
22 | * 3. Neither the names of the above-listed copyright holders nor the names | ||
23 | * of any contributors may be used to endorse or promote products derived | ||
24 | * from this software without specific prior written permission. | ||
25 | * | ||
26 | * Alternatively, this software may be distributed under the terms of the | ||
27 | * GNU General Public License ("GPL") version 2 as published by the Free | ||
28 | * Software Foundation. | ||
29 | * | ||
30 | * NO WARRANTY | ||
31 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
32 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
33 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR | ||
34 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
35 | * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
36 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
37 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
38 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
39 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING | ||
40 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | ||
41 | * POSSIBILITY OF SUCH DAMAGES. | ||
42 | */ | ||
43 | |||
44 | |||
45 | #include <acpi/acpi.h> | ||
46 | |||
47 | #define _COMPONENT ACPI_UTILITIES | ||
48 | ACPI_MODULE_NAME ("utmutex") | ||
49 | |||
50 | /* Local prototypes */ | ||
51 | |||
52 | static acpi_status | ||
53 | acpi_ut_create_mutex ( | ||
54 | acpi_mutex_handle mutex_id); | ||
55 | |||
56 | static acpi_status | ||
57 | acpi_ut_delete_mutex ( | ||
58 | acpi_mutex_handle mutex_id); | ||
59 | |||
60 | |||
61 | /******************************************************************************* | ||
62 | * | ||
63 | * FUNCTION: acpi_ut_mutex_initialize | ||
64 | * | ||
65 | * PARAMETERS: None. | ||
66 | * | ||
67 | * RETURN: Status | ||
68 | * | ||
69 | * DESCRIPTION: Create the system mutex objects. | ||
70 | * | ||
71 | ******************************************************************************/ | ||
72 | |||
73 | acpi_status | ||
74 | acpi_ut_mutex_initialize ( | ||
75 | void) | ||
76 | { | ||
77 | u32 i; | ||
78 | acpi_status status; | ||
79 | |||
80 | |||
81 | ACPI_FUNCTION_TRACE ("ut_mutex_initialize"); | ||
82 | |||
83 | |||
84 | /* | ||
85 | * Create each of the predefined mutex objects | ||
86 | */ | ||
87 | for (i = 0; i < NUM_MUTEX; i++) { | ||
88 | status = acpi_ut_create_mutex (i); | ||
89 | if (ACPI_FAILURE (status)) { | ||
90 | return_ACPI_STATUS (status); | ||
91 | } | ||
92 | } | ||
93 | |||
94 | status = acpi_os_create_lock (&acpi_gbl_gpe_lock); | ||
95 | return_ACPI_STATUS (status); | ||
96 | } | ||
97 | |||
98 | |||
99 | /******************************************************************************* | ||
100 | * | ||
101 | * FUNCTION: acpi_ut_mutex_terminate | ||
102 | * | ||
103 | * PARAMETERS: None. | ||
104 | * | ||
105 | * RETURN: None. | ||
106 | * | ||
107 | * DESCRIPTION: Delete all of the system mutex objects. | ||
108 | * | ||
109 | ******************************************************************************/ | ||
110 | |||
111 | void | ||
112 | acpi_ut_mutex_terminate ( | ||
113 | void) | ||
114 | { | ||
115 | u32 i; | ||
116 | |||
117 | |||
118 | ACPI_FUNCTION_TRACE ("ut_mutex_terminate"); | ||
119 | |||
120 | |||
121 | /* | ||
122 | * Delete each predefined mutex object | ||
123 | */ | ||
124 | for (i = 0; i < NUM_MUTEX; i++) { | ||
125 | (void) acpi_ut_delete_mutex (i); | ||
126 | } | ||
127 | |||
128 | acpi_os_delete_lock (acpi_gbl_gpe_lock); | ||
129 | return_VOID; | ||
130 | } | ||
131 | |||
132 | |||
133 | /******************************************************************************* | ||
134 | * | ||
135 | * FUNCTION: acpi_ut_create_mutex | ||
136 | * | ||
137 | * PARAMETERS: mutex_iD - ID of the mutex to be created | ||
138 | * | ||
139 | * RETURN: Status | ||
140 | * | ||
141 | * DESCRIPTION: Create a mutex object. | ||
142 | * | ||
143 | ******************************************************************************/ | ||
144 | |||
145 | static acpi_status | ||
146 | acpi_ut_create_mutex ( | ||
147 | acpi_mutex_handle mutex_id) | ||
148 | { | ||
149 | acpi_status status = AE_OK; | ||
150 | |||
151 | |||
152 | ACPI_FUNCTION_TRACE_U32 ("ut_create_mutex", mutex_id); | ||
153 | |||
154 | |||
155 | if (mutex_id > MAX_MUTEX) { | ||
156 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
157 | } | ||
158 | |||
159 | if (!acpi_gbl_mutex_info[mutex_id].mutex) { | ||
160 | status = acpi_os_create_semaphore (1, 1, | ||
161 | &acpi_gbl_mutex_info[mutex_id].mutex); | ||
162 | acpi_gbl_mutex_info[mutex_id].thread_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
163 | acpi_gbl_mutex_info[mutex_id].use_count = 0; | ||
164 | } | ||
165 | |||
166 | return_ACPI_STATUS (status); | ||
167 | } | ||
168 | |||
169 | |||
170 | /******************************************************************************* | ||
171 | * | ||
172 | * FUNCTION: acpi_ut_delete_mutex | ||
173 | * | ||
174 | * PARAMETERS: mutex_iD - ID of the mutex to be deleted | ||
175 | * | ||
176 | * RETURN: Status | ||
177 | * | ||
178 | * DESCRIPTION: Delete a mutex object. | ||
179 | * | ||
180 | ******************************************************************************/ | ||
181 | |||
182 | static acpi_status | ||
183 | acpi_ut_delete_mutex ( | ||
184 | acpi_mutex_handle mutex_id) | ||
185 | { | ||
186 | acpi_status status; | ||
187 | |||
188 | |||
189 | ACPI_FUNCTION_TRACE_U32 ("ut_delete_mutex", mutex_id); | ||
190 | |||
191 | |||
192 | if (mutex_id > MAX_MUTEX) { | ||
193 | return_ACPI_STATUS (AE_BAD_PARAMETER); | ||
194 | } | ||
195 | |||
196 | status = acpi_os_delete_semaphore (acpi_gbl_mutex_info[mutex_id].mutex); | ||
197 | |||
198 | acpi_gbl_mutex_info[mutex_id].mutex = NULL; | ||
199 | acpi_gbl_mutex_info[mutex_id].thread_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
200 | |||
201 | return_ACPI_STATUS (status); | ||
202 | } | ||
203 | |||
204 | |||
205 | /******************************************************************************* | ||
206 | * | ||
207 | * FUNCTION: acpi_ut_acquire_mutex | ||
208 | * | ||
209 | * PARAMETERS: mutex_iD - ID of the mutex to be acquired | ||
210 | * | ||
211 | * RETURN: Status | ||
212 | * | ||
213 | * DESCRIPTION: Acquire a mutex object. | ||
214 | * | ||
215 | ******************************************************************************/ | ||
216 | |||
217 | acpi_status | ||
218 | acpi_ut_acquire_mutex ( | ||
219 | acpi_mutex_handle mutex_id) | ||
220 | { | ||
221 | acpi_status status; | ||
222 | u32 this_thread_id; | ||
223 | |||
224 | |||
225 | ACPI_FUNCTION_NAME ("ut_acquire_mutex"); | ||
226 | |||
227 | |||
228 | if (mutex_id > MAX_MUTEX) { | ||
229 | return (AE_BAD_PARAMETER); | ||
230 | } | ||
231 | |||
232 | this_thread_id = acpi_os_get_thread_id (); | ||
233 | |||
234 | #ifdef ACPI_MUTEX_DEBUG | ||
235 | { | ||
236 | u32 i; | ||
237 | /* | ||
238 | * Mutex debug code, for internal debugging only. | ||
239 | * | ||
240 | * Deadlock prevention. Check if this thread owns any mutexes of value | ||
241 | * greater than or equal to this one. If so, the thread has violated | ||
242 | * the mutex ordering rule. This indicates a coding error somewhere in | ||
243 | * the ACPI subsystem code. | ||
244 | */ | ||
245 | for (i = mutex_id; i < MAX_MUTEX; i++) { | ||
246 | if (acpi_gbl_mutex_info[i].owner_id == this_thread_id) { | ||
247 | if (i == mutex_id) { | ||
248 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
249 | "Mutex [%s] already acquired by this thread [%X]\n", | ||
250 | acpi_ut_get_mutex_name (mutex_id), this_thread_id)); | ||
251 | |||
252 | return (AE_ALREADY_ACQUIRED); | ||
253 | } | ||
254 | |||
255 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
256 | "Invalid acquire order: Thread %X owns [%s], wants [%s]\n", | ||
257 | this_thread_id, acpi_ut_get_mutex_name (i), | ||
258 | acpi_ut_get_mutex_name (mutex_id))); | ||
259 | |||
260 | return (AE_ACQUIRE_DEADLOCK); | ||
261 | } | ||
262 | } | ||
263 | } | ||
264 | #endif | ||
265 | |||
266 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, | ||
267 | "Thread %X attempting to acquire Mutex [%s]\n", | ||
268 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
269 | |||
270 | status = acpi_os_wait_semaphore (acpi_gbl_mutex_info[mutex_id].mutex, | ||
271 | 1, ACPI_WAIT_FOREVER); | ||
272 | if (ACPI_SUCCESS (status)) { | ||
273 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Thread %X acquired Mutex [%s]\n", | ||
274 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
275 | |||
276 | acpi_gbl_mutex_info[mutex_id].use_count++; | ||
277 | acpi_gbl_mutex_info[mutex_id].thread_id = this_thread_id; | ||
278 | } | ||
279 | else { | ||
280 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
281 | "Thread %X could not acquire Mutex [%s] %s\n", | ||
282 | this_thread_id, acpi_ut_get_mutex_name (mutex_id), | ||
283 | acpi_format_exception (status))); | ||
284 | } | ||
285 | |||
286 | return (status); | ||
287 | } | ||
288 | |||
289 | |||
290 | /******************************************************************************* | ||
291 | * | ||
292 | * FUNCTION: acpi_ut_release_mutex | ||
293 | * | ||
294 | * PARAMETERS: mutex_iD - ID of the mutex to be released | ||
295 | * | ||
296 | * RETURN: Status | ||
297 | * | ||
298 | * DESCRIPTION: Release a mutex object. | ||
299 | * | ||
300 | ******************************************************************************/ | ||
301 | |||
302 | acpi_status | ||
303 | acpi_ut_release_mutex ( | ||
304 | acpi_mutex_handle mutex_id) | ||
305 | { | ||
306 | acpi_status status; | ||
307 | u32 this_thread_id; | ||
308 | |||
309 | |||
310 | ACPI_FUNCTION_NAME ("ut_release_mutex"); | ||
311 | |||
312 | |||
313 | this_thread_id = acpi_os_get_thread_id (); | ||
314 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, | ||
315 | "Thread %X releasing Mutex [%s]\n", this_thread_id, | ||
316 | acpi_ut_get_mutex_name (mutex_id))); | ||
317 | |||
318 | if (mutex_id > MAX_MUTEX) { | ||
319 | return (AE_BAD_PARAMETER); | ||
320 | } | ||
321 | |||
322 | /* | ||
323 | * Mutex must be acquired in order to release it! | ||
324 | */ | ||
325 | if (acpi_gbl_mutex_info[mutex_id].thread_id == ACPI_MUTEX_NOT_ACQUIRED) { | ||
326 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
327 | "Mutex [%s] is not acquired, cannot release\n", | ||
328 | acpi_ut_get_mutex_name (mutex_id))); | ||
329 | |||
330 | return (AE_NOT_ACQUIRED); | ||
331 | } | ||
332 | |||
333 | #ifdef ACPI_MUTEX_DEBUG | ||
334 | { | ||
335 | u32 i; | ||
336 | /* | ||
337 | * Mutex debug code, for internal debugging only. | ||
338 | * | ||
339 | * Deadlock prevention. Check if this thread owns any mutexes of value | ||
340 | * greater than this one. If so, the thread has violated the mutex | ||
341 | * ordering rule. This indicates a coding error somewhere in | ||
342 | * the ACPI subsystem code. | ||
343 | */ | ||
344 | for (i = mutex_id; i < MAX_MUTEX; i++) { | ||
345 | if (acpi_gbl_mutex_info[i].owner_id == this_thread_id) { | ||
346 | if (i == mutex_id) { | ||
347 | continue; | ||
348 | } | ||
349 | |||
350 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
351 | "Invalid release order: owns [%s], releasing [%s]\n", | ||
352 | acpi_ut_get_mutex_name (i), acpi_ut_get_mutex_name (mutex_id))); | ||
353 | |||
354 | return (AE_RELEASE_DEADLOCK); | ||
355 | } | ||
356 | } | ||
357 | } | ||
358 | #endif | ||
359 | |||
360 | /* Mark unlocked FIRST */ | ||
361 | |||
362 | acpi_gbl_mutex_info[mutex_id].thread_id = ACPI_MUTEX_NOT_ACQUIRED; | ||
363 | |||
364 | status = acpi_os_signal_semaphore (acpi_gbl_mutex_info[mutex_id].mutex, 1); | ||
365 | |||
366 | if (ACPI_FAILURE (status)) { | ||
367 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, | ||
368 | "Thread %X could not release Mutex [%s] %s\n", | ||
369 | this_thread_id, acpi_ut_get_mutex_name (mutex_id), | ||
370 | acpi_format_exception (status))); | ||
371 | } | ||
372 | else { | ||
373 | ACPI_DEBUG_PRINT ((ACPI_DB_MUTEX, "Thread %X released Mutex [%s]\n", | ||
374 | this_thread_id, acpi_ut_get_mutex_name (mutex_id))); | ||
375 | } | ||
376 | |||
377 | return (status); | ||
378 | } | ||
379 | |||
380 | |||
diff --git a/drivers/acpi/utilities/utobject.c b/drivers/acpi/utilities/utobject.c index cd3899b9cc5a..19178e142951 100644 --- a/drivers/acpi/utilities/utobject.c +++ b/drivers/acpi/utilities/utobject.c | |||
@@ -338,7 +338,7 @@ acpi_ut_allocate_object_desc_dbg ( | |||
338 | ACPI_FUNCTION_TRACE ("ut_allocate_object_desc_dbg"); | 338 | ACPI_FUNCTION_TRACE ("ut_allocate_object_desc_dbg"); |
339 | 339 | ||
340 | 340 | ||
341 | object = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_OPERAND); | 341 | object = acpi_os_acquire_object (acpi_gbl_operand_cache); |
342 | if (!object) { | 342 | if (!object) { |
343 | _ACPI_REPORT_ERROR (module_name, line_number, component_id, | 343 | _ACPI_REPORT_ERROR (module_name, line_number, component_id, |
344 | ("Could not allocate an object descriptor\n")); | 344 | ("Could not allocate an object descriptor\n")); |
@@ -347,7 +347,7 @@ acpi_ut_allocate_object_desc_dbg ( | |||
347 | } | 347 | } |
348 | 348 | ||
349 | /* Mark the descriptor type */ | 349 | /* Mark the descriptor type */ |
350 | 350 | memset(object, 0, sizeof(union acpi_operand_object)); | |
351 | ACPI_SET_DESCRIPTOR_TYPE (object, ACPI_DESC_TYPE_OPERAND); | 351 | ACPI_SET_DESCRIPTOR_TYPE (object, ACPI_DESC_TYPE_OPERAND); |
352 | 352 | ||
353 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "%p Size %X\n", | 353 | ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "%p Size %X\n", |
@@ -385,37 +385,9 @@ acpi_ut_delete_object_desc ( | |||
385 | return_VOID; | 385 | return_VOID; |
386 | } | 386 | } |
387 | 387 | ||
388 | acpi_ut_release_to_cache (ACPI_MEM_LIST_OPERAND, object); | 388 | (void) acpi_os_release_object (acpi_gbl_operand_cache, object); |
389 | |||
390 | return_VOID; | ||
391 | } | ||
392 | |||
393 | |||
394 | #ifdef ACPI_ENABLE_OBJECT_CACHE | ||
395 | /******************************************************************************* | ||
396 | * | ||
397 | * FUNCTION: acpi_ut_delete_object_cache | ||
398 | * | ||
399 | * PARAMETERS: None | ||
400 | * | ||
401 | * RETURN: None | ||
402 | * | ||
403 | * DESCRIPTION: Purge the global state object cache. Used during subsystem | ||
404 | * termination. | ||
405 | * | ||
406 | ******************************************************************************/ | ||
407 | |||
408 | void | ||
409 | acpi_ut_delete_object_cache ( | ||
410 | void) | ||
411 | { | ||
412 | ACPI_FUNCTION_TRACE ("ut_delete_object_cache"); | ||
413 | |||
414 | |||
415 | acpi_ut_delete_generic_cache (ACPI_MEM_LIST_OPERAND); | ||
416 | return_VOID; | 389 | return_VOID; |
417 | } | 390 | } |
418 | #endif | ||
419 | 391 | ||
420 | 392 | ||
421 | /******************************************************************************* | 393 | /******************************************************************************* |
diff --git a/drivers/acpi/utilities/utstate.c b/drivers/acpi/utilities/utstate.c new file mode 100644 index 000000000000..192e7ac95690 --- /dev/null +++ b/drivers/acpi/utilities/utstate.c | |||
@@ -0,0 +1,376 @@ | |||
1 | /******************************************************************************* | ||
2 | * | ||
3 | * Module Name: utstate - state object support procedures | ||
4 | * | ||
5 | ******************************************************************************/ | ||
6 | |||
7 | /* | ||
8 | * Copyright (C) 2000 - 2005, R. Byron Moore | ||
9 | * All rights reserved. | ||
10 | * | ||
11 | * Redistribution and use in source and binary forms, with or without | ||
12 | * modification, are permitted provided that the following conditions | ||
13 | * are met: | ||
14 | * 1. Redistributions of source code must retain the above copyright | ||
15 | * notice, this list of conditions, and the following disclaimer, | ||
16 | * without modification. | ||
17 | * 2. Redistributions in binary form must reproduce at minimum a disclaimer | ||
18 | * substantially similar to the "NO WARRANTY" disclaimer below | ||
19 | * ("Disclaimer") and any redistribution must be conditioned upon | ||
20 | * including a substantially similar Disclaimer requirement for further | ||
21 | * binary redistribution. | ||
22 | * 3. Neither the names of the above-listed copyright holders nor the names | ||
23 | * of any contributors may be used to endorse or promote products derived | ||
24 | * from this software without specific prior written permission. | ||
25 | * | ||
26 | * Alternatively, this software may be distributed under the terms of the | ||
27 | * GNU General Public License ("GPL") version 2 as published by the Free | ||
28 | * Software Foundation. | ||
29 | * | ||
30 | * NO WARRANTY | ||
31 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
32 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
33 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR | ||
34 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
35 | * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
36 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
37 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
38 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
39 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING | ||
40 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | ||
41 | * POSSIBILITY OF SUCH DAMAGES. | ||
42 | */ | ||
43 | |||
44 | |||
45 | #include <acpi/acpi.h> | ||
46 | |||
47 | #define _COMPONENT ACPI_UTILITIES | ||
48 | ACPI_MODULE_NAME ("utstate") | ||
49 | |||
50 | |||
51 | /******************************************************************************* | ||
52 | * | ||
53 | * FUNCTION: acpi_ut_create_pkg_state_and_push | ||
54 | * | ||
55 | * PARAMETERS: Object - Object to be added to the new state | ||
56 | * Action - Increment/Decrement | ||
57 | * state_list - List the state will be added to | ||
58 | * | ||
59 | * RETURN: Status | ||
60 | * | ||
61 | * DESCRIPTION: Create a new state and push it | ||
62 | * | ||
63 | ******************************************************************************/ | ||
64 | |||
65 | acpi_status | ||
66 | acpi_ut_create_pkg_state_and_push ( | ||
67 | void *internal_object, | ||
68 | void *external_object, | ||
69 | u16 index, | ||
70 | union acpi_generic_state **state_list) | ||
71 | { | ||
72 | union acpi_generic_state *state; | ||
73 | |||
74 | |||
75 | ACPI_FUNCTION_ENTRY (); | ||
76 | |||
77 | |||
78 | state = acpi_ut_create_pkg_state (internal_object, external_object, index); | ||
79 | if (!state) { | ||
80 | return (AE_NO_MEMORY); | ||
81 | } | ||
82 | |||
83 | acpi_ut_push_generic_state (state_list, state); | ||
84 | return (AE_OK); | ||
85 | } | ||
86 | |||
87 | |||
88 | /******************************************************************************* | ||
89 | * | ||
90 | * FUNCTION: acpi_ut_push_generic_state | ||
91 | * | ||
92 | * PARAMETERS: list_head - Head of the state stack | ||
93 | * State - State object to push | ||
94 | * | ||
95 | * RETURN: None | ||
96 | * | ||
97 | * DESCRIPTION: Push a state object onto a state stack | ||
98 | * | ||
99 | ******************************************************************************/ | ||
100 | |||
101 | void | ||
102 | acpi_ut_push_generic_state ( | ||
103 | union acpi_generic_state **list_head, | ||
104 | union acpi_generic_state *state) | ||
105 | { | ||
106 | ACPI_FUNCTION_TRACE ("ut_push_generic_state"); | ||
107 | |||
108 | |||
109 | /* Push the state object onto the front of the list (stack) */ | ||
110 | |||
111 | state->common.next = *list_head; | ||
112 | *list_head = state; | ||
113 | |||
114 | return_VOID; | ||
115 | } | ||
116 | |||
117 | |||
118 | /******************************************************************************* | ||
119 | * | ||
120 | * FUNCTION: acpi_ut_pop_generic_state | ||
121 | * | ||
122 | * PARAMETERS: list_head - Head of the state stack | ||
123 | * | ||
124 | * RETURN: The popped state object | ||
125 | * | ||
126 | * DESCRIPTION: Pop a state object from a state stack | ||
127 | * | ||
128 | ******************************************************************************/ | ||
129 | |||
130 | union acpi_generic_state * | ||
131 | acpi_ut_pop_generic_state ( | ||
132 | union acpi_generic_state **list_head) | ||
133 | { | ||
134 | union acpi_generic_state *state; | ||
135 | |||
136 | |||
137 | ACPI_FUNCTION_TRACE ("ut_pop_generic_state"); | ||
138 | |||
139 | |||
140 | /* Remove the state object at the head of the list (stack) */ | ||
141 | |||
142 | state = *list_head; | ||
143 | if (state) { | ||
144 | /* Update the list head */ | ||
145 | |||
146 | *list_head = state->common.next; | ||
147 | } | ||
148 | |||
149 | return_PTR (state); | ||
150 | } | ||
151 | |||
152 | |||
153 | /******************************************************************************* | ||
154 | * | ||
155 | * FUNCTION: acpi_ut_create_generic_state | ||
156 | * | ||
157 | * PARAMETERS: None | ||
158 | * | ||
159 | * RETURN: The new state object. NULL on failure. | ||
160 | * | ||
161 | * DESCRIPTION: Create a generic state object. Attempt to obtain one from | ||
162 | * the global state cache; If none available, create a new one. | ||
163 | * | ||
164 | ******************************************************************************/ | ||
165 | |||
166 | union acpi_generic_state * | ||
167 | acpi_ut_create_generic_state ( | ||
168 | void) | ||
169 | { | ||
170 | union acpi_generic_state *state; | ||
171 | |||
172 | |||
173 | ACPI_FUNCTION_ENTRY (); | ||
174 | |||
175 | |||
176 | state = acpi_os_acquire_object (acpi_gbl_state_cache); | ||
177 | if (state) { | ||
178 | /* Initialize */ | ||
179 | memset(state, 0, sizeof(union acpi_generic_state)); | ||
180 | state->common.data_type = ACPI_DESC_TYPE_STATE; | ||
181 | } | ||
182 | |||
183 | return (state); | ||
184 | } | ||
185 | |||
186 | |||
187 | /******************************************************************************* | ||
188 | * | ||
189 | * FUNCTION: acpi_ut_create_thread_state | ||
190 | * | ||
191 | * PARAMETERS: None | ||
192 | * | ||
193 | * RETURN: New Thread State. NULL on failure | ||
194 | * | ||
195 | * DESCRIPTION: Create a "Thread State" - a flavor of the generic state used | ||
196 | * to track per-thread info during method execution | ||
197 | * | ||
198 | ******************************************************************************/ | ||
199 | |||
200 | struct acpi_thread_state * | ||
201 | acpi_ut_create_thread_state ( | ||
202 | void) | ||
203 | { | ||
204 | union acpi_generic_state *state; | ||
205 | |||
206 | |||
207 | ACPI_FUNCTION_TRACE ("ut_create_thread_state"); | ||
208 | |||
209 | |||
210 | /* Create the generic state object */ | ||
211 | |||
212 | state = acpi_ut_create_generic_state (); | ||
213 | if (!state) { | ||
214 | return_PTR (NULL); | ||
215 | } | ||
216 | |||
217 | /* Init fields specific to the update struct */ | ||
218 | |||
219 | state->common.data_type = ACPI_DESC_TYPE_STATE_THREAD; | ||
220 | state->thread.thread_id = acpi_os_get_thread_id (); | ||
221 | |||
222 | return_PTR ((struct acpi_thread_state *) state); | ||
223 | } | ||
224 | |||
225 | |||
226 | /******************************************************************************* | ||
227 | * | ||
228 | * FUNCTION: acpi_ut_create_update_state | ||
229 | * | ||
230 | * PARAMETERS: Object - Initial Object to be installed in the state | ||
231 | * Action - Update action to be performed | ||
232 | * | ||
233 | * RETURN: New state object, null on failure | ||
234 | * | ||
235 | * DESCRIPTION: Create an "Update State" - a flavor of the generic state used | ||
236 | * to update reference counts and delete complex objects such | ||
237 | * as packages. | ||
238 | * | ||
239 | ******************************************************************************/ | ||
240 | |||
241 | union acpi_generic_state * | ||
242 | acpi_ut_create_update_state ( | ||
243 | union acpi_operand_object *object, | ||
244 | u16 action) | ||
245 | { | ||
246 | union acpi_generic_state *state; | ||
247 | |||
248 | |||
249 | ACPI_FUNCTION_TRACE_PTR ("ut_create_update_state", object); | ||
250 | |||
251 | |||
252 | /* Create the generic state object */ | ||
253 | |||
254 | state = acpi_ut_create_generic_state (); | ||
255 | if (!state) { | ||
256 | return_PTR (NULL); | ||
257 | } | ||
258 | |||
259 | /* Init fields specific to the update struct */ | ||
260 | |||
261 | state->common.data_type = ACPI_DESC_TYPE_STATE_UPDATE; | ||
262 | state->update.object = object; | ||
263 | state->update.value = action; | ||
264 | |||
265 | return_PTR (state); | ||
266 | } | ||
267 | |||
268 | |||
269 | /******************************************************************************* | ||
270 | * | ||
271 | * FUNCTION: acpi_ut_create_pkg_state | ||
272 | * | ||
273 | * PARAMETERS: Object - Initial Object to be installed in the state | ||
274 | * Action - Update action to be performed | ||
275 | * | ||
276 | * RETURN: New state object, null on failure | ||
277 | * | ||
278 | * DESCRIPTION: Create a "Package State" | ||
279 | * | ||
280 | ******************************************************************************/ | ||
281 | |||
282 | union acpi_generic_state * | ||
283 | acpi_ut_create_pkg_state ( | ||
284 | void *internal_object, | ||
285 | void *external_object, | ||
286 | u16 index) | ||
287 | { | ||
288 | union acpi_generic_state *state; | ||
289 | |||
290 | |||
291 | ACPI_FUNCTION_TRACE_PTR ("ut_create_pkg_state", internal_object); | ||
292 | |||
293 | |||
294 | /* Create the generic state object */ | ||
295 | |||
296 | state = acpi_ut_create_generic_state (); | ||
297 | if (!state) { | ||
298 | return_PTR (NULL); | ||
299 | } | ||
300 | |||
301 | /* Init fields specific to the update struct */ | ||
302 | |||
303 | state->common.data_type = ACPI_DESC_TYPE_STATE_PACKAGE; | ||
304 | state->pkg.source_object = (union acpi_operand_object *) internal_object; | ||
305 | state->pkg.dest_object = external_object; | ||
306 | state->pkg.index = index; | ||
307 | state->pkg.num_packages = 1; | ||
308 | |||
309 | return_PTR (state); | ||
310 | } | ||
311 | |||
312 | |||
313 | /******************************************************************************* | ||
314 | * | ||
315 | * FUNCTION: acpi_ut_create_control_state | ||
316 | * | ||
317 | * PARAMETERS: None | ||
318 | * | ||
319 | * RETURN: New state object, null on failure | ||
320 | * | ||
321 | * DESCRIPTION: Create a "Control State" - a flavor of the generic state used | ||
322 | * to support nested IF/WHILE constructs in the AML. | ||
323 | * | ||
324 | ******************************************************************************/ | ||
325 | |||
326 | union acpi_generic_state * | ||
327 | acpi_ut_create_control_state ( | ||
328 | void) | ||
329 | { | ||
330 | union acpi_generic_state *state; | ||
331 | |||
332 | |||
333 | ACPI_FUNCTION_TRACE ("ut_create_control_state"); | ||
334 | |||
335 | |||
336 | /* Create the generic state object */ | ||
337 | |||
338 | state = acpi_ut_create_generic_state (); | ||
339 | if (!state) { | ||
340 | return_PTR (NULL); | ||
341 | } | ||
342 | |||
343 | /* Init fields specific to the control struct */ | ||
344 | |||
345 | state->common.data_type = ACPI_DESC_TYPE_STATE_CONTROL; | ||
346 | state->common.state = ACPI_CONTROL_CONDITIONAL_EXECUTING; | ||
347 | |||
348 | return_PTR (state); | ||
349 | } | ||
350 | |||
351 | |||
352 | /******************************************************************************* | ||
353 | * | ||
354 | * FUNCTION: acpi_ut_delete_generic_state | ||
355 | * | ||
356 | * PARAMETERS: State - The state object to be deleted | ||
357 | * | ||
358 | * RETURN: None | ||
359 | * | ||
360 | * DESCRIPTION: Put a state object back into the global state cache. The object | ||
361 | * is not actually freed at this time. | ||
362 | * | ||
363 | ******************************************************************************/ | ||
364 | |||
365 | void | ||
366 | acpi_ut_delete_generic_state ( | ||
367 | union acpi_generic_state *state) | ||
368 | { | ||
369 | ACPI_FUNCTION_TRACE ("ut_delete_generic_state"); | ||
370 | |||
371 | |||
372 | (void) acpi_os_release_object (acpi_gbl_state_cache, state); | ||
373 | return_VOID; | ||
374 | } | ||
375 | |||
376 | |||
diff --git a/drivers/acpi/utilities/utxface.c b/drivers/acpi/utilities/utxface.c index e8803d810656..850da6817423 100644 --- a/drivers/acpi/utilities/utxface.c +++ b/drivers/acpi/utilities/utxface.c | |||
@@ -46,8 +46,6 @@ | |||
46 | #include <acpi/acpi.h> | 46 | #include <acpi/acpi.h> |
47 | #include <acpi/acevents.h> | 47 | #include <acpi/acevents.h> |
48 | #include <acpi/acnamesp.h> | 48 | #include <acpi/acnamesp.h> |
49 | #include <acpi/acparser.h> | ||
50 | #include <acpi/acdispat.h> | ||
51 | #include <acpi/acdebug.h> | 49 | #include <acpi/acdebug.h> |
52 | 50 | ||
53 | #define _COMPONENT ACPI_UTILITIES | 51 | #define _COMPONENT ACPI_UTILITIES |
@@ -79,11 +77,6 @@ acpi_initialize_subsystem ( | |||
79 | 77 | ||
80 | ACPI_DEBUG_EXEC (acpi_ut_init_stack_ptr_trace ()); | 78 | ACPI_DEBUG_EXEC (acpi_ut_init_stack_ptr_trace ()); |
81 | 79 | ||
82 | |||
83 | /* Initialize all globals used by the subsystem */ | ||
84 | |||
85 | acpi_ut_init_globals (); | ||
86 | |||
87 | /* Initialize the OS-Dependent layer */ | 80 | /* Initialize the OS-Dependent layer */ |
88 | 81 | ||
89 | status = acpi_os_initialize (); | 82 | status = acpi_os_initialize (); |
@@ -93,6 +86,10 @@ acpi_initialize_subsystem ( | |||
93 | return_ACPI_STATUS (status); | 86 | return_ACPI_STATUS (status); |
94 | } | 87 | } |
95 | 88 | ||
89 | /* Initialize all globals used by the subsystem */ | ||
90 | |||
91 | acpi_ut_init_globals (); | ||
92 | |||
96 | /* Create the default mutex objects */ | 93 | /* Create the default mutex objects */ |
97 | 94 | ||
98 | status = acpi_ut_mutex_initialize (); | 95 | status = acpi_ut_mutex_initialize (); |
@@ -522,13 +519,9 @@ acpi_purge_cached_objects ( | |||
522 | { | 519 | { |
523 | ACPI_FUNCTION_TRACE ("acpi_purge_cached_objects"); | 520 | ACPI_FUNCTION_TRACE ("acpi_purge_cached_objects"); |
524 | 521 | ||
525 | 522 | (void) acpi_os_purge_cache (acpi_gbl_state_cache); | |
526 | #ifdef ACPI_ENABLE_OBJECT_CACHE | 523 | (void) acpi_os_purge_cache (acpi_gbl_operand_cache); |
527 | acpi_ut_delete_generic_state_cache (); | 524 | (void) acpi_os_purge_cache (acpi_gbl_ps_node_cache); |
528 | acpi_ut_delete_object_cache (); | 525 | (void) acpi_os_purge_cache (acpi_gbl_ps_node_ext_cache); |
529 | acpi_ds_delete_walk_state_cache (); | ||
530 | acpi_ps_delete_parse_cache (); | ||
531 | #endif | ||
532 | |||
533 | return_ACPI_STATUS (AE_OK); | 526 | return_ACPI_STATUS (AE_OK); |
534 | } | 527 | } |