ftp://ftp.kernel.org/pub/linux/kernel/v2.6/linux-2.6.6.tar.bz2
[linux-2.6.git] / drivers / acpi / utilities / utdelete.c
1 /*******************************************************************************
2  *
3  * Module Name: utdelete - object deletion and reference count utilities
4  *
5  ******************************************************************************/
6
7 /*
8  * Copyright (C) 2000 - 2004, 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 #include <acpi/acinterp.h>
47 #include <acpi/acnamesp.h>
48 #include <acpi/acevents.h>
49
50 #define _COMPONENT          ACPI_UTILITIES
51          ACPI_MODULE_NAME    ("utdelete")
52
53
54 /*******************************************************************************
55  *
56  * FUNCTION:    acpi_ut_delete_internal_obj
57  *
58  * PARAMETERS:  *Object        - Pointer to the list to be deleted
59  *
60  * RETURN:      None
61  *
62  * DESCRIPTION: Low level object deletion, after reference counts have been
63  *              updated (All reference counts, including sub-objects!)
64  *
65  ******************************************************************************/
66
67 void
68 acpi_ut_delete_internal_obj (
69         union acpi_operand_object       *object)
70 {
71         void                            *obj_pointer = NULL;
72         union acpi_operand_object       *handler_desc;
73         union acpi_operand_object       *second_desc;
74         union acpi_operand_object       *next_desc;
75
76
77         ACPI_FUNCTION_TRACE_PTR ("ut_delete_internal_obj", object);
78
79
80         if (!object) {
81                 return_VOID;
82         }
83
84         /*
85          * Must delete or free any pointers within the object that are not
86          * actual ACPI objects (for example, a raw buffer pointer).
87          */
88         switch (ACPI_GET_OBJECT_TYPE (object)) {
89         case ACPI_TYPE_STRING:
90
91                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "**** String %p, ptr %p\n",
92                         object, object->string.pointer));
93
94                 /* Free the actual string buffer */
95
96                 if (!(object->common.flags & AOPOBJ_STATIC_POINTER)) {
97                         /* But only if it is NOT a pointer into an ACPI table */
98
99                         obj_pointer = object->string.pointer;
100                 }
101                 break;
102
103
104         case ACPI_TYPE_BUFFER:
105
106                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "**** Buffer %p, ptr %p\n",
107                         object, object->buffer.pointer));
108
109                 /* Free the actual buffer */
110
111                 if (!(object->common.flags & AOPOBJ_STATIC_POINTER)) {
112                         /* But only if it is NOT a pointer into an ACPI table */
113
114                         obj_pointer = object->buffer.pointer;
115                 }
116                 break;
117
118
119         case ACPI_TYPE_PACKAGE:
120
121                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, " **** Package of count %X\n",
122                         object->package.count));
123
124                 /*
125                  * Elements of the package are not handled here, they are deleted
126                  * separately
127                  */
128
129                 /* Free the (variable length) element pointer array */
130
131                 obj_pointer = object->package.elements;
132                 break;
133
134
135         case ACPI_TYPE_DEVICE:
136
137                 if (object->device.gpe_block) {
138                         (void) acpi_ev_delete_gpe_block (object->device.gpe_block);
139                 }
140
141                 /* Walk the handler list for this device */
142
143                 handler_desc = object->device.handler;
144                 while (handler_desc) {
145                         next_desc = handler_desc->address_space.next;
146                         acpi_ut_remove_reference (handler_desc);
147                         handler_desc = next_desc;
148                 }
149                 break;
150
151
152         case ACPI_TYPE_MUTEX:
153
154                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "***** Mutex %p, Semaphore %p\n",
155                         object, object->mutex.semaphore));
156
157                 acpi_ex_unlink_mutex (object);
158                 (void) acpi_os_delete_semaphore (object->mutex.semaphore);
159                 break;
160
161
162         case ACPI_TYPE_EVENT:
163
164                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "***** Event %p, Semaphore %p\n",
165                         object, object->event.semaphore));
166
167                 (void) acpi_os_delete_semaphore (object->event.semaphore);
168                 object->event.semaphore = NULL;
169                 break;
170
171
172         case ACPI_TYPE_METHOD:
173
174                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "***** Method %p\n", object));
175
176                 /* Delete the method semaphore if it exists */
177
178                 if (object->method.semaphore) {
179                         (void) acpi_os_delete_semaphore (object->method.semaphore);
180                         object->method.semaphore = NULL;
181                 }
182                 break;
183
184
185         case ACPI_TYPE_REGION:
186
187                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "***** Region %p\n", object));
188
189                 second_desc = acpi_ns_get_secondary_object (object);
190                 if (second_desc) {
191                         /*
192                          * Free the region_context if and only if the handler is one of the
193                          * default handlers -- and therefore, we created the context object
194                          * locally, it was not created by an external caller.
195                          */
196                         handler_desc = object->region.handler;
197                         if (handler_desc) {
198                                 if (handler_desc->address_space.hflags & ACPI_ADDR_HANDLER_DEFAULT_INSTALLED) {
199                                         obj_pointer = second_desc->extra.region_context;
200                                 }
201
202                                 acpi_ut_remove_reference (handler_desc);
203                         }
204
205                         /* Now we can free the Extra object */
206
207                         acpi_ut_delete_object_desc (second_desc);
208                 }
209                 break;
210
211
212         case ACPI_TYPE_BUFFER_FIELD:
213
214                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "***** Buffer Field %p\n", object));
215
216                 second_desc = acpi_ns_get_secondary_object (object);
217                 if (second_desc) {
218                         acpi_ut_delete_object_desc (second_desc);
219                 }
220                 break;
221
222
223         default:
224                 break;
225         }
226
227         /* Free any allocated memory (pointer within the object) found above */
228
229         if (obj_pointer) {
230                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Deleting Object Subptr %p\n",
231                                 obj_pointer));
232                 ACPI_MEM_FREE (obj_pointer);
233         }
234
235         /* Now the object can be safely deleted */
236
237         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Deleting Object %p [%s]\n",
238                         object, acpi_ut_get_object_type_name (object)));
239
240         acpi_ut_delete_object_desc (object);
241         return_VOID;
242 }
243
244
245 /*******************************************************************************
246  *
247  * FUNCTION:    acpi_ut_delete_internal_object_list
248  *
249  * PARAMETERS:  *obj_list       - Pointer to the list to be deleted
250  *
251  * RETURN:      None
252  *
253  * DESCRIPTION: This function deletes an internal object list, including both
254  *              simple objects and package objects
255  *
256  ******************************************************************************/
257
258 void
259 acpi_ut_delete_internal_object_list (
260         union acpi_operand_object       **obj_list)
261 {
262         union acpi_operand_object       **internal_obj;
263
264
265         ACPI_FUNCTION_TRACE ("ut_delete_internal_object_list");
266
267
268         /* Walk the null-terminated internal list */
269
270         for (internal_obj = obj_list; *internal_obj; internal_obj++) {
271                 acpi_ut_remove_reference (*internal_obj);
272         }
273
274         /* Free the combined parameter pointer list and object array */
275
276         ACPI_MEM_FREE (obj_list);
277         return_VOID;
278 }
279
280
281 /*******************************************************************************
282  *
283  * FUNCTION:    acpi_ut_update_ref_count
284  *
285  * PARAMETERS:  *Object         - Object whose ref count is to be updated
286  *              Action          - What to do
287  *
288  * RETURN:      New ref count
289  *
290  * DESCRIPTION: Modify the ref count and return it.
291  *
292  ******************************************************************************/
293
294 static void
295 acpi_ut_update_ref_count (
296         union acpi_operand_object       *object,
297         u32                             action)
298 {
299         u16                             count;
300         u16                             new_count;
301
302
303         ACPI_FUNCTION_NAME ("ut_update_ref_count");
304
305
306         if (!object) {
307                 return;
308         }
309
310         count = object->common.reference_count;
311         new_count = count;
312
313         /*
314          * Perform the reference count action (increment, decrement, or force delete)
315          */
316         switch (action) {
317
318         case REF_INCREMENT:
319
320                 new_count++;
321                 object->common.reference_count = new_count;
322
323                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Obj %p Refs=%X, [Incremented]\n",
324                         object, new_count));
325                 break;
326
327
328         case REF_DECREMENT:
329
330                 if (count < 1) {
331                         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Obj %p Refs=%X, can't decrement! (Set to 0)\n",
332                                 object, new_count));
333
334                         new_count = 0;
335                 }
336                 else {
337                         new_count--;
338
339                         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Obj %p Refs=%X, [Decremented]\n",
340                                 object, new_count));
341                 }
342
343                 if (ACPI_GET_OBJECT_TYPE (object) == ACPI_TYPE_METHOD) {
344                         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Method Obj %p Refs=%X, [Decremented]\n",
345                                 object, new_count));
346                 }
347
348                 object->common.reference_count = new_count;
349                 if (new_count == 0) {
350                         acpi_ut_delete_internal_obj (object);
351                 }
352
353                 break;
354
355
356         case REF_FORCE_DELETE:
357
358                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Obj %p Refs=%X, Force delete! (Set to 0)\n",
359                         object, count));
360
361                 new_count = 0;
362                 object->common.reference_count = new_count;
363                 acpi_ut_delete_internal_obj (object);
364                 break;
365
366
367         default:
368
369                 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Unknown action (%X)\n", action));
370                 break;
371         }
372
373         /*
374          * Sanity check the reference count, for debug purposes only.
375          * (A deleted object will have a huge reference count)
376          */
377         if (count > ACPI_MAX_REFERENCE_COUNT) {
378
379                 ACPI_DEBUG_PRINT ((ACPI_DB_WARN,
380                         "**** Warning **** Large Reference Count (%X) in object %p\n\n",
381                         count, object));
382         }
383
384         return;
385 }
386
387
388 /*******************************************************************************
389  *
390  * FUNCTION:    acpi_ut_update_object_reference
391  *
392  * PARAMETERS:  *Object             - Increment ref count for this object
393  *                                    and all sub-objects
394  *              Action              - Either REF_INCREMENT or REF_DECREMENT or
395  *                                    REF_FORCE_DELETE
396  *
397  * RETURN:      Status
398  *
399  * DESCRIPTION: Increment the object reference count
400  *
401  * Object references are incremented when:
402  * 1) An object is attached to a Node (namespace object)
403  * 2) An object is copied (all subobjects must be incremented)
404  *
405  * Object references are decremented when:
406  * 1) An object is detached from an Node
407  *
408  ******************************************************************************/
409
410 acpi_status
411 acpi_ut_update_object_reference (
412         union acpi_operand_object       *object,
413         u16                             action)
414 {
415         acpi_status                     status;
416         u32                             i;
417         union acpi_generic_state         *state_list = NULL;
418         union acpi_generic_state         *state;
419         union acpi_operand_object        *tmp;
420
421         ACPI_FUNCTION_TRACE_PTR ("ut_update_object_reference", object);
422
423
424         /* Ignore a null object ptr */
425
426         if (!object) {
427                 return_ACPI_STATUS (AE_OK);
428         }
429
430         /* Make sure that this isn't a namespace handle */
431
432         if (ACPI_GET_DESCRIPTOR_TYPE (object) == ACPI_DESC_TYPE_NAMED) {
433                 ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Object %p is NS handle\n", object));
434                 return_ACPI_STATUS (AE_OK);
435         }
436
437         state = acpi_ut_create_update_state (object, action);
438
439         while (state) {
440                 object = state->update.object;
441                 action = state->update.value;
442                 acpi_ut_delete_generic_state (state);
443
444                 /*
445                  * All sub-objects must have their reference count incremented also.
446                  * Different object types have different subobjects.
447                  */
448                 switch (ACPI_GET_OBJECT_TYPE (object)) {
449                 case ACPI_TYPE_DEVICE:
450
451                         tmp = object->device.system_notify;
452                         if (tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT)
453                                 object->device.system_notify = NULL;
454                         acpi_ut_update_ref_count (tmp, action);
455
456                         tmp = object->device.device_notify;
457                         if (tmp && (tmp->common.reference_count <= 1) && action == REF_DECREMENT)
458                                 object->device.device_notify = NULL;
459                         acpi_ut_update_ref_count (tmp, action);
460
461                         break;
462
463
464                 case ACPI_TYPE_PACKAGE:
465
466                         /*
467                          * We must update all the sub-objects of the package
468                          * (Each of whom may have their own sub-objects, etc.
469                          */
470                         for (i = 0; i < object->package.count; i++) {
471                                 /*
472                                  * Push each element onto the stack for later processing.
473                                  * Note: There can be null elements within the package,
474                                  * these are simply ignored
475                                  */
476                                 status = acpi_ut_create_update_state_and_push (
477                                                  object->package.elements[i], action, &state_list);
478                                 if (ACPI_FAILURE (status)) {
479                                         goto error_exit;
480                                 }
481
482                                 tmp = object->package.elements[i];
483                                 if (tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
484                                         object->package.elements[i] = NULL;
485                         }
486                         break;
487
488
489                 case ACPI_TYPE_BUFFER_FIELD:
490
491                         status = acpi_ut_create_update_state_and_push (
492                                          object->buffer_field.buffer_obj, action, &state_list);
493                         if (ACPI_FAILURE (status)) {
494                                 goto error_exit;
495                         }
496
497                         tmp = object->buffer_field.buffer_obj;
498                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
499                                 object->buffer_field.buffer_obj = NULL;
500                         break;
501
502
503                 case ACPI_TYPE_LOCAL_REGION_FIELD:
504
505                         status = acpi_ut_create_update_state_and_push (
506                                          object->field.region_obj, action, &state_list);
507                         if (ACPI_FAILURE (status)) {
508                                 goto error_exit;
509                         }
510
511                         tmp = object->field.region_obj;
512                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
513                                 object->field.region_obj = NULL;
514                    break;
515
516
517                 case ACPI_TYPE_LOCAL_BANK_FIELD:
518
519                         status = acpi_ut_create_update_state_and_push (
520                                          object->bank_field.bank_obj, action, &state_list);
521                         if (ACPI_FAILURE (status)) {
522                                 goto error_exit;
523                         }
524
525                         tmp = object->bank_field.bank_obj;
526                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
527                                 object->bank_field.bank_obj = NULL;
528
529                         status = acpi_ut_create_update_state_and_push (
530                                          object->bank_field.region_obj, action, &state_list);
531                         if (ACPI_FAILURE (status)) {
532                                 goto error_exit;
533                         }
534
535                         tmp = object->bank_field.region_obj;
536                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
537                                 object->bank_field.region_obj = NULL;
538                         break;
539
540
541                 case ACPI_TYPE_LOCAL_INDEX_FIELD:
542
543                         status = acpi_ut_create_update_state_and_push (
544                                          object->index_field.index_obj, action, &state_list);
545                         if (ACPI_FAILURE (status)) {
546                                 goto error_exit;
547                         }
548
549                         tmp = object->index_field.index_obj;
550                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
551                                 object->index_field.index_obj = NULL;
552
553                         status = acpi_ut_create_update_state_and_push (
554                                          object->index_field.data_obj, action, &state_list);
555                         if (ACPI_FAILURE (status)) {
556                                 goto error_exit;
557                         }
558
559                         tmp = object->index_field.data_obj;
560                         if ( tmp && (tmp->common.reference_count <= 1)  && action == REF_DECREMENT)
561                                 object->index_field.data_obj = NULL;
562                         break;
563
564
565                 case ACPI_TYPE_REGION:
566                 case ACPI_TYPE_LOCAL_REFERENCE:
567                 default:
568
569                         /* No subobjects */
570                         break;
571                 }
572
573                 /*
574                  * Now we can update the count in the main object.  This can only
575                  * happen after we update the sub-objects in case this causes the
576                  * main object to be deleted.
577                  */
578                 acpi_ut_update_ref_count (object, action);
579
580                 /* Move on to the next object to be updated */
581
582                 state = acpi_ut_pop_generic_state (&state_list);
583         }
584
585         return_ACPI_STATUS (AE_OK);
586
587
588 error_exit:
589
590         ACPI_REPORT_ERROR (("Could not update object reference count, %s\n",
591                 acpi_format_exception (status)));
592
593         return_ACPI_STATUS (status);
594 }
595
596
597 /*******************************************************************************
598  *
599  * FUNCTION:    acpi_ut_add_reference
600  *
601  * PARAMETERS:  *Object        - Object whose reference count is to be
602  *                                  incremented
603  *
604  * RETURN:      None
605  *
606  * DESCRIPTION: Add one reference to an ACPI object
607  *
608  ******************************************************************************/
609
610 void
611 acpi_ut_add_reference (
612         union acpi_operand_object       *object)
613 {
614
615         ACPI_FUNCTION_TRACE_PTR ("ut_add_reference", object);
616
617
618         /* Ensure that we have a valid object */
619
620         if (!acpi_ut_valid_internal_object (object)) {
621                 return_VOID;
622         }
623
624         /* Increment the reference count */
625
626         (void) acpi_ut_update_object_reference (object, REF_INCREMENT);
627         return_VOID;
628 }
629
630
631 /*******************************************************************************
632  *
633  * FUNCTION:    acpi_ut_remove_reference
634  *
635  * PARAMETERS:  *Object        - Object whose ref count will be decremented
636  *
637  * RETURN:      None
638  *
639  * DESCRIPTION: Decrement the reference count of an ACPI internal object
640  *
641  ******************************************************************************/
642
643 void
644 acpi_ut_remove_reference (
645         union acpi_operand_object       *object)
646 {
647
648         ACPI_FUNCTION_TRACE_PTR ("ut_remove_reference", object);
649
650
651         /*
652          * Allow a NULL pointer to be passed in, just ignore it.  This saves
653          * each caller from having to check.  Also, ignore NS nodes.
654          *
655          */
656         if (!object ||
657                 (ACPI_GET_DESCRIPTOR_TYPE (object) == ACPI_DESC_TYPE_NAMED)) {
658                 return_VOID;
659         }
660
661         /* Ensure that we have a valid object */
662
663         if (!acpi_ut_valid_internal_object (object)) {
664                 return_VOID;
665         }
666
667         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Obj %p Refs=%X\n",
668                         object, object->common.reference_count));
669
670         /*
671          * Decrement the reference count, and only actually delete the object
672          * if the reference count becomes 0.  (Must also decrement the ref count
673          * of all subobjects!)
674          */
675         (void) acpi_ut_update_object_reference (object, REF_DECREMENT);
676         return_VOID;
677 }
678
679