OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [linux/] [linux-2.4/] [drivers/] [acpi/] [dispatcher/] [dswstate.c] - Blame information for rev 1275

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1275 phoenix
/******************************************************************************
2
 *
3
 * Module Name: dswstate - Dispatcher parse tree walk management routines
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/acparser.h>
47
#include <acpi/acdispat.h>
48
#include <acpi/acnamesp.h>
49
 
50
#define _COMPONENT          ACPI_DISPATCHER
51
         ACPI_MODULE_NAME    ("dswstate")
52
 
53
 
54
/*******************************************************************************
55
 *
56
 * FUNCTION:    acpi_ds_result_insert
57
 *
58
 * PARAMETERS:  Object              - Object to push
59
 *              Index               - Where to insert the object
60
 *              walk_state          - Current Walk state
61
 *
62
 * RETURN:      Status
63
 *
64
 * DESCRIPTION: Insert an object onto this walk's result stack
65
 *
66
 ******************************************************************************/
67
 
68
acpi_status
69
acpi_ds_result_insert (
70
        void                            *object,
71
        u32                             index,
72
        struct acpi_walk_state          *walk_state)
73
{
74
        union acpi_generic_state        *state;
75
 
76
 
77
        ACPI_FUNCTION_NAME ("ds_result_insert");
78
 
79
 
80
        state = walk_state->results;
81
        if (!state) {
82
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No result object pushed! State=%p\n",
83
                        walk_state));
84
                return (AE_NOT_EXIST);
85
        }
86
 
87
        if (index >= ACPI_OBJ_NUM_OPERANDS) {
88
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
89
                        "Index out of range: %X Obj=%p State=%p Num=%X\n",
90
                        index, object, walk_state, state->results.num_results));
91
                return (AE_BAD_PARAMETER);
92
        }
93
 
94
        if (!object) {
95
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
96
                        "Null Object! Index=%X Obj=%p State=%p Num=%X\n",
97
                        index, object, walk_state, state->results.num_results));
98
                return (AE_BAD_PARAMETER);
99
        }
100
 
101
        state->results.obj_desc [index] = object;
102
        state->results.num_results++;
103
 
104
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
105
                "Obj=%p [%s] State=%p Num=%X Cur=%X\n",
106
                object, object ? acpi_ut_get_object_type_name ((union acpi_operand_object *) object) : "NULL",
107
                walk_state, state->results.num_results, walk_state->current_result));
108
 
109
        return (AE_OK);
110
}
111
 
112
 
113
/*******************************************************************************
114
 *
115
 * FUNCTION:    acpi_ds_result_remove
116
 *
117
 * PARAMETERS:  Object              - Where to return the popped object
118
 *              Index               - Where to extract the object
119
 *              walk_state          - Current Walk state
120
 *
121
 * RETURN:      Status
122
 *
123
 * DESCRIPTION: Pop an object off the bottom of this walk's result stack.  In
124
 *              other words, this is a FIFO.
125
 *
126
 ******************************************************************************/
127
 
128
acpi_status
129
acpi_ds_result_remove (
130
        union acpi_operand_object       **object,
131
        u32                             index,
132
        struct acpi_walk_state          *walk_state)
133
{
134
        union acpi_generic_state        *state;
135
 
136
 
137
        ACPI_FUNCTION_NAME ("ds_result_remove");
138
 
139
 
140
        state = walk_state->results;
141
        if (!state) {
142
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No result object pushed! State=%p\n",
143
                        walk_state));
144
                return (AE_NOT_EXIST);
145
        }
146
 
147
        if (index >= ACPI_OBJ_MAX_OPERAND) {
148
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
149
                        "Index out of range: %X State=%p Num=%X\n",
150
                        index, walk_state, state->results.num_results));
151
        }
152
 
153
        /* Check for a valid result object */
154
 
155
        if (!state->results.obj_desc [index]) {
156
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
157
                        "Null operand! State=%p #Ops=%X, Index=%X\n",
158
                        walk_state, state->results.num_results, index));
159
                return (AE_AML_NO_RETURN_VALUE);
160
        }
161
 
162
        /* Remove the object */
163
 
164
        state->results.num_results--;
165
 
166
        *object = state->results.obj_desc [index];
167
        state->results.obj_desc [index] = NULL;
168
 
169
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
170
                "Obj=%p [%s] Index=%X State=%p Num=%X\n",
171
                *object, (*object) ? acpi_ut_get_object_type_name (*object) : "NULL",
172
                index, walk_state, state->results.num_results));
173
 
174
        return (AE_OK);
175
}
176
 
177
 
178
/*******************************************************************************
179
 *
180
 * FUNCTION:    acpi_ds_result_pop
181
 *
182
 * PARAMETERS:  Object              - Where to return the popped object
183
 *              walk_state          - Current Walk state
184
 *
185
 * RETURN:      Status
186
 *
187
 * DESCRIPTION: Pop an object off the bottom of this walk's result stack.  In
188
 *              other words, this is a FIFO.
189
 *
190
 ******************************************************************************/
191
 
192
acpi_status
193
acpi_ds_result_pop (
194
        union acpi_operand_object       **object,
195
        struct acpi_walk_state          *walk_state)
196
{
197
        acpi_native_uint                index;
198
        union acpi_generic_state        *state;
199
 
200
 
201
        ACPI_FUNCTION_NAME ("ds_result_pop");
202
 
203
 
204
        state = walk_state->results;
205
        if (!state) {
206
                return (AE_OK);
207
        }
208
 
209
        if (!state->results.num_results) {
210
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Result stack is empty! State=%p\n",
211
                        walk_state));
212
                return (AE_AML_NO_RETURN_VALUE);
213
        }
214
 
215
        /* Remove top element */
216
 
217
        state->results.num_results--;
218
 
219
        for (index = ACPI_OBJ_NUM_OPERANDS; index; index--) {
220
                /* Check for a valid result object */
221
 
222
                if (state->results.obj_desc [index -1]) {
223
                        *object = state->results.obj_desc [index -1];
224
                        state->results.obj_desc [index -1] = NULL;
225
 
226
                        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s] Index=%X State=%p Num=%X\n",
227
                                *object, (*object) ? acpi_ut_get_object_type_name (*object) : "NULL",
228
                                (u32) index -1, walk_state, state->results.num_results));
229
 
230
                        return (AE_OK);
231
                }
232
        }
233
 
234
        ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No result objects! State=%p\n", walk_state));
235
        return (AE_AML_NO_RETURN_VALUE);
236
}
237
 
238
 
239
/*******************************************************************************
240
 *
241
 * FUNCTION:    acpi_ds_result_pop_from_bottom
242
 *
243
 * PARAMETERS:  Object              - Where to return the popped object
244
 *              walk_state          - Current Walk state
245
 *
246
 * RETURN:      Status
247
 *
248
 * DESCRIPTION: Pop an object off the bottom of this walk's result stack.  In
249
 *              other words, this is a FIFO.
250
 *
251
 ******************************************************************************/
252
 
253
acpi_status
254
acpi_ds_result_pop_from_bottom (
255
        union acpi_operand_object       **object,
256
        struct acpi_walk_state          *walk_state)
257
{
258
        acpi_native_uint                index;
259
        union acpi_generic_state        *state;
260
 
261
 
262
        ACPI_FUNCTION_NAME ("ds_result_pop_from_bottom");
263
 
264
 
265
        state = walk_state->results;
266
        if (!state) {
267
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
268
                        "Warning: No result object pushed! State=%p\n", walk_state));
269
                return (AE_NOT_EXIST);
270
        }
271
 
272
        if (!state->results.num_results) {
273
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No result objects! State=%p\n", walk_state));
274
                return (AE_AML_NO_RETURN_VALUE);
275
        }
276
 
277
        /* Remove Bottom element */
278
 
279
        *object = state->results.obj_desc [0];
280
 
281
        /* Push entire stack down one element */
282
 
283
        for (index = 0; index < state->results.num_results; index++) {
284
                state->results.obj_desc [index] = state->results.obj_desc [index + 1];
285
        }
286
 
287
        state->results.num_results--;
288
 
289
        /* Check for a valid result object */
290
 
291
        if (!*object) {
292
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Null operand! State=%p #Ops=%X, Index=%X\n",
293
                        walk_state, state->results.num_results, (u32) index));
294
                return (AE_AML_NO_RETURN_VALUE);
295
        }
296
 
297
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s], Results=%p State=%p\n",
298
                *object, (*object) ? acpi_ut_get_object_type_name (*object) : "NULL",
299
                state, walk_state));
300
 
301
        return (AE_OK);
302
}
303
 
304
 
305
/*******************************************************************************
306
 *
307
 * FUNCTION:    acpi_ds_result_push
308
 *
309
 * PARAMETERS:  Object              - Where to return the popped object
310
 *              walk_state          - Current Walk state
311
 *
312
 * RETURN:      Status
313
 *
314
 * DESCRIPTION: Push an object onto the current result stack
315
 *
316
 ******************************************************************************/
317
 
318
acpi_status
319
acpi_ds_result_push (
320
        union acpi_operand_object       *object,
321
        struct acpi_walk_state          *walk_state)
322
{
323
        union acpi_generic_state        *state;
324
 
325
 
326
        ACPI_FUNCTION_NAME ("ds_result_push");
327
 
328
 
329
        state = walk_state->results;
330
        if (!state) {
331
                ACPI_REPORT_ERROR (("No result stack frame during push\n"));
332
                return (AE_AML_INTERNAL);
333
        }
334
 
335
        if (state->results.num_results == ACPI_OBJ_NUM_OPERANDS) {
336
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
337
                        "Result stack overflow: Obj=%p State=%p Num=%X\n",
338
                        object, walk_state, state->results.num_results));
339
                return (AE_STACK_OVERFLOW);
340
        }
341
 
342
        if (!object) {
343
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Null Object! Obj=%p State=%p Num=%X\n",
344
                        object, walk_state, state->results.num_results));
345
                return (AE_BAD_PARAMETER);
346
        }
347
 
348
        state->results.obj_desc [state->results.num_results] = object;
349
        state->results.num_results++;
350
 
351
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s] State=%p Num=%X Cur=%X\n",
352
                object, object ? acpi_ut_get_object_type_name ((union acpi_operand_object *) object) : "NULL",
353
                walk_state, state->results.num_results, walk_state->current_result));
354
 
355
        return (AE_OK);
356
}
357
 
358
 
359
/*******************************************************************************
360
 *
361
 * FUNCTION:    acpi_ds_result_stack_push
362
 *
363
 * PARAMETERS:  walk_state          - Current Walk state
364
 *
365
 * RETURN:      Status
366
 *
367
 * DESCRIPTION: Push an object onto the walk_state result stack.
368
 *
369
 ******************************************************************************/
370
 
371
acpi_status
372
acpi_ds_result_stack_push (
373
        struct acpi_walk_state          *walk_state)
374
{
375
        union acpi_generic_state        *state;
376
 
377
        ACPI_FUNCTION_NAME ("ds_result_stack_push");
378
 
379
 
380
        state = acpi_ut_create_generic_state ();
381
        if (!state) {
382
                return (AE_NO_MEMORY);
383
        }
384
 
385
        state->common.data_type = ACPI_DESC_TYPE_STATE_RESULT;
386
        acpi_ut_push_generic_state (&walk_state->results, state);
387
 
388
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Results=%p State=%p\n",
389
                state, walk_state));
390
 
391
        return (AE_OK);
392
}
393
 
394
 
395
/*******************************************************************************
396
 *
397
 * FUNCTION:    acpi_ds_result_stack_pop
398
 *
399
 * PARAMETERS:  walk_state          - Current Walk state
400
 *
401
 * RETURN:      Status
402
 *
403
 * DESCRIPTION: Pop an object off of the walk_state result stack.
404
 *
405
 ******************************************************************************/
406
 
407
acpi_status
408
acpi_ds_result_stack_pop (
409
        struct acpi_walk_state          *walk_state)
410
{
411
        union acpi_generic_state        *state;
412
 
413
        ACPI_FUNCTION_NAME ("ds_result_stack_pop");
414
 
415
 
416
        /* Check for stack underflow */
417
 
418
        if (walk_state->results == NULL) {
419
                ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Underflow - State=%p\n",
420
                        walk_state));
421
                return (AE_AML_NO_OPERAND);
422
        }
423
 
424
        state = acpi_ut_pop_generic_state (&walk_state->results);
425
 
426
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
427
                "Result=%p remaining_results=%X State=%p\n",
428
                state, state->results.num_results, walk_state));
429
 
430
        acpi_ut_delete_generic_state (state);
431
 
432
        return (AE_OK);
433
}
434
 
435
 
436
/*******************************************************************************
437
 *
438
 * FUNCTION:    acpi_ds_obj_stack_delete_all
439
 *
440
 * PARAMETERS:  walk_state          - Current Walk state
441
 *
442
 * RETURN:      Status
443
 *
444
 * DESCRIPTION: Clear the object stack by deleting all objects that are on it.
445
 *              Should be used with great care, if at all!
446
 *
447
 ******************************************************************************/
448
 
449
acpi_status
450
acpi_ds_obj_stack_delete_all (
451
        struct acpi_walk_state          *walk_state)
452
{
453
        u32                             i;
454
 
455
 
456
        ACPI_FUNCTION_TRACE_PTR ("ds_obj_stack_delete_all", walk_state);
457
 
458
 
459
        /* The stack size is configurable, but fixed */
460
 
461
        for (i = 0; i < ACPI_OBJ_NUM_OPERANDS; i++) {
462
                if (walk_state->operands[i]) {
463
                        acpi_ut_remove_reference (walk_state->operands[i]);
464
                        walk_state->operands[i] = NULL;
465
                }
466
        }
467
 
468
        return_ACPI_STATUS (AE_OK);
469
}
470
 
471
 
472
/*******************************************************************************
473
 *
474
 * FUNCTION:    acpi_ds_obj_stack_push
475
 *
476
 * PARAMETERS:  Object              - Object to push
477
 *              walk_state          - Current Walk state
478
 *
479
 * RETURN:      Status
480
 *
481
 * DESCRIPTION: Push an object onto this walk's object/operand stack
482
 *
483
 ******************************************************************************/
484
 
485
acpi_status
486
acpi_ds_obj_stack_push (
487
        void                            *object,
488
        struct acpi_walk_state          *walk_state)
489
{
490
        ACPI_FUNCTION_NAME ("ds_obj_stack_push");
491
 
492
 
493
        /* Check for stack overflow */
494
 
495
        if (walk_state->num_operands >= ACPI_OBJ_NUM_OPERANDS) {
496
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
497
                        "overflow! Obj=%p State=%p #Ops=%X\n",
498
                        object, walk_state, walk_state->num_operands));
499
                return (AE_STACK_OVERFLOW);
500
        }
501
 
502
        /* Put the object onto the stack */
503
 
504
        walk_state->operands [walk_state->num_operands] = object;
505
        walk_state->num_operands++;
506
 
507
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s] State=%p #Ops=%X\n",
508
                          object, acpi_ut_get_object_type_name ((union acpi_operand_object *) object),
509
                          walk_state, walk_state->num_operands));
510
 
511
        return (AE_OK);
512
}
513
 
514
 
515
#if 0
516
/*******************************************************************************
517
 *
518
 * FUNCTION:    acpi_ds_obj_stack_pop_object
519
 *
520
 * PARAMETERS:  pop_count           - Number of objects/entries to pop
521
 *              walk_state          - Current Walk state
522
 *
523
 * RETURN:      Status
524
 *
525
 * DESCRIPTION: Pop this walk's object stack.  Objects on the stack are NOT
526
 *              deleted by this routine.
527
 *
528
 ******************************************************************************/
529
 
530
acpi_status
531
acpi_ds_obj_stack_pop_object (
532
        union acpi_operand_object       **object,
533
        struct acpi_walk_state          *walk_state)
534
{
535
        ACPI_FUNCTION_NAME ("ds_obj_stack_pop_object");
536
 
537
 
538
        /* Check for stack underflow */
539
 
540
        if (walk_state->num_operands == 0) {
541
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
542
                        "Missing operand/stack empty! State=%p #Ops=%X\n",
543
                        walk_state, walk_state->num_operands));
544
                *object = NULL;
545
                return (AE_AML_NO_OPERAND);
546
        }
547
 
548
        /* Pop the stack */
549
 
550
        walk_state->num_operands--;
551
 
552
        /* Check for a valid operand */
553
 
554
        if (!walk_state->operands [walk_state->num_operands]) {
555
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
556
                        "Null operand! State=%p #Ops=%X\n",
557
                        walk_state, walk_state->num_operands));
558
                *object = NULL;
559
                return (AE_AML_NO_OPERAND);
560
        }
561
 
562
        /* Get operand and set stack entry to null */
563
 
564
        *object = walk_state->operands [walk_state->num_operands];
565
        walk_state->operands [walk_state->num_operands] = NULL;
566
 
567
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Obj=%p [%s] State=%p #Ops=%X\n",
568
                          *object, acpi_ut_get_object_type_name (*object),
569
                          walk_state, walk_state->num_operands));
570
 
571
        return (AE_OK);
572
}
573
#endif
574
 
575
 
576
/*******************************************************************************
577
 *
578
 * FUNCTION:    acpi_ds_obj_stack_pop
579
 *
580
 * PARAMETERS:  pop_count           - Number of objects/entries to pop
581
 *              walk_state          - Current Walk state
582
 *
583
 * RETURN:      Status
584
 *
585
 * DESCRIPTION: Pop this walk's object stack.  Objects on the stack are NOT
586
 *              deleted by this routine.
587
 *
588
 ******************************************************************************/
589
 
590
acpi_status
591
acpi_ds_obj_stack_pop (
592
        u32                             pop_count,
593
        struct acpi_walk_state          *walk_state)
594
{
595
        u32                             i;
596
 
597
        ACPI_FUNCTION_NAME ("ds_obj_stack_pop");
598
 
599
 
600
        for (i = 0; i < pop_count; i++) {
601
                /* Check for stack underflow */
602
 
603
                if (walk_state->num_operands == 0) {
604
                        ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
605
                                "Underflow! Count=%X State=%p #Ops=%X\n",
606
                                pop_count, walk_state, walk_state->num_operands));
607
                        return (AE_STACK_UNDERFLOW);
608
                }
609
 
610
                /* Just set the stack entry to null */
611
 
612
                walk_state->num_operands--;
613
                walk_state->operands [walk_state->num_operands] = NULL;
614
        }
615
 
616
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Count=%X State=%p #Ops=%X\n",
617
                          pop_count, walk_state, walk_state->num_operands));
618
 
619
        return (AE_OK);
620
}
621
 
622
 
623
/*******************************************************************************
624
 *
625
 * FUNCTION:    acpi_ds_obj_stack_pop_and_delete
626
 *
627
 * PARAMETERS:  pop_count           - Number of objects/entries to pop
628
 *              walk_state          - Current Walk state
629
 *
630
 * RETURN:      Status
631
 *
632
 * DESCRIPTION: Pop this walk's object stack and delete each object that is
633
 *              popped off.
634
 *
635
 ******************************************************************************/
636
 
637
acpi_status
638
acpi_ds_obj_stack_pop_and_delete (
639
        u32                             pop_count,
640
        struct acpi_walk_state          *walk_state)
641
{
642
        u32                             i;
643
        union acpi_operand_object       *obj_desc;
644
 
645
 
646
        ACPI_FUNCTION_NAME ("ds_obj_stack_pop_and_delete");
647
 
648
 
649
        for (i = 0; i < pop_count; i++) {
650
                /* Check for stack underflow */
651
 
652
                if (walk_state->num_operands == 0) {
653
                        ACPI_DEBUG_PRINT ((ACPI_DB_ERROR,
654
                                "Underflow! Count=%X State=%p #Ops=%X\n",
655
                                pop_count, walk_state, walk_state->num_operands));
656
                        return (AE_STACK_UNDERFLOW);
657
                }
658
 
659
                /* Pop the stack and delete an object if present in this stack entry */
660
 
661
                walk_state->num_operands--;
662
                obj_desc = walk_state->operands [walk_state->num_operands];
663
                if (obj_desc) {
664
                        acpi_ut_remove_reference (walk_state->operands [walk_state->num_operands]);
665
                        walk_state->operands [walk_state->num_operands] = NULL;
666
                }
667
        }
668
 
669
        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Count=%X State=%p #Ops=%X\n",
670
                          pop_count, walk_state, walk_state->num_operands));
671
 
672
        return (AE_OK);
673
}
674
 
675
 
676
/*******************************************************************************
677
 *
678
 * FUNCTION:    acpi_ds_obj_stack_get_value
679
 *
680
 * PARAMETERS:  Index               - Stack index whose value is desired.  Based
681
 *                                    on the top of the stack (index=0 == top)
682
 *              walk_state          - Current Walk state
683
 *
684
 * RETURN:      Status
685
 *
686
 * DESCRIPTION: Retrieve an object from this walk's object stack.  Index must
687
 *              be within the range of the current stack pointer.
688
 *
689
 ******************************************************************************/
690
 
691
void *
692
acpi_ds_obj_stack_get_value (
693
        u32                             index,
694
        struct acpi_walk_state          *walk_state)
695
{
696
 
697
        ACPI_FUNCTION_TRACE_PTR ("ds_obj_stack_get_value", walk_state);
698
 
699
 
700
        /* Can't do it if the stack is empty */
701
 
702
        if (walk_state->num_operands == 0) {
703
                return_PTR (NULL);
704
        }
705
 
706
        /* or if the index is past the top of the stack */
707
 
708
        if (index > (walk_state->num_operands - (u32) 1)) {
709
                return_PTR (NULL);
710
        }
711
 
712
        return_PTR (walk_state->operands[(acpi_native_uint)(walk_state->num_operands - 1) -
713
                          index]);
714
}
715
 
716
 
717
/*******************************************************************************
718
 *
719
 * FUNCTION:    acpi_ds_get_current_walk_state
720
 *
721
 * PARAMETERS:  Thread          - Get current active state for this Thread
722
 *
723
 * RETURN:      Pointer to the current walk state
724
 *
725
 * DESCRIPTION: Get the walk state that is at the head of the list (the "current"
726
 *              walk state.)
727
 *
728
 ******************************************************************************/
729
 
730
struct acpi_walk_state *
731
acpi_ds_get_current_walk_state (
732
        struct acpi_thread_state        *thread)
733
 
734
{
735
        ACPI_FUNCTION_NAME ("ds_get_current_walk_state");
736
 
737
 
738
        if (!thread) {
739
                return (NULL);
740
        }
741
 
742
        ACPI_DEBUG_PRINT ((ACPI_DB_PARSE, "Current walk_state %p\n",
743
                thread->walk_state_list));
744
 
745
        return (thread->walk_state_list);
746
}
747
 
748
 
749
/*******************************************************************************
750
 *
751
 * FUNCTION:    acpi_ds_push_walk_state
752
 *
753
 * PARAMETERS:  walk_state      - State to push
754
 *              walk_list       - The list that owns the walk stack
755
 *
756
 * RETURN:      None
757
 *
758
 * DESCRIPTION: Place the walk_state at the head of the state list.
759
 *
760
 ******************************************************************************/
761
 
762
void
763
acpi_ds_push_walk_state (
764
        struct acpi_walk_state          *walk_state,
765
        struct acpi_thread_state        *thread)
766
{
767
        ACPI_FUNCTION_TRACE ("ds_push_walk_state");
768
 
769
 
770
        walk_state->next      = thread->walk_state_list;
771
        thread->walk_state_list = walk_state;
772
 
773
        return_VOID;
774
}
775
 
776
 
777
/*******************************************************************************
778
 *
779
 * FUNCTION:    acpi_ds_pop_walk_state
780
 *
781
 * PARAMETERS:  walk_list       - The list that owns the walk stack
782
 *
783
 * RETURN:      A walk_state object popped from the stack
784
 *
785
 * DESCRIPTION: Remove and return the walkstate object that is at the head of
786
 *              the walk stack for the given walk list.  NULL indicates that
787
 *              the list is empty.
788
 *
789
 ******************************************************************************/
790
 
791
struct acpi_walk_state *
792
acpi_ds_pop_walk_state (
793
        struct acpi_thread_state        *thread)
794
{
795
        struct acpi_walk_state          *walk_state;
796
 
797
 
798
        ACPI_FUNCTION_TRACE ("ds_pop_walk_state");
799
 
800
 
801
        walk_state = thread->walk_state_list;
802
 
803
        if (walk_state) {
804
                /* Next walk state becomes the current walk state */
805
 
806
                thread->walk_state_list = walk_state->next;
807
 
808
                /*
809
                 * Don't clear the NEXT field, this serves as an indicator
810
                 * that there is a parent WALK STATE
811
                 *     NO: walk_state->Next = NULL;
812
                 */
813
        }
814
 
815
        return_PTR (walk_state);
816
}
817
 
818
 
819
/*******************************************************************************
820
 *
821
 * FUNCTION:    acpi_ds_create_walk_state
822
 *
823
 * PARAMETERS:  Origin          - Starting point for this walk
824
 *              Thread          - Current thread state
825
 *
826
 * RETURN:      Pointer to the new walk state.
827
 *
828
 * DESCRIPTION: Allocate and initialize a new walk state.  The current walk
829
 *              state is set to this new state.
830
 *
831
 ******************************************************************************/
832
 
833
struct acpi_walk_state *
834
acpi_ds_create_walk_state (
835
        acpi_owner_id                   owner_id,
836
        union acpi_parse_object         *origin,
837
        union acpi_operand_object       *mth_desc,
838
        struct acpi_thread_state        *thread)
839
{
840
        struct acpi_walk_state          *walk_state;
841
        acpi_status                     status;
842
 
843
 
844
        ACPI_FUNCTION_TRACE ("ds_create_walk_state");
845
 
846
 
847
        walk_state = acpi_ut_acquire_from_cache (ACPI_MEM_LIST_WALK);
848
        if (!walk_state) {
849
                return_PTR (NULL);
850
        }
851
 
852
        walk_state->data_type       = ACPI_DESC_TYPE_WALK;
853
        walk_state->owner_id        = owner_id;
854
        walk_state->origin          = origin;
855
        walk_state->method_desc     = mth_desc;
856
        walk_state->thread          = thread;
857
 
858
        walk_state->parser_state.start_op = origin;
859
 
860
        /* Init the method args/local */
861
 
862
#if (!defined (ACPI_NO_METHOD_EXECUTION) && !defined (ACPI_CONSTANT_EVAL_ONLY))
863
        acpi_ds_method_data_init (walk_state);
864
#endif
865
 
866
        /* Create an initial result stack entry */
867
 
868
        status = acpi_ds_result_stack_push (walk_state);
869
        if (ACPI_FAILURE (status)) {
870
                return_PTR (NULL);
871
        }
872
 
873
        /* Put the new state at the head of the walk list */
874
 
875
        if (thread) {
876
                acpi_ds_push_walk_state (walk_state, thread);
877
        }
878
 
879
        return_PTR (walk_state);
880
}
881
 
882
 
883
/*******************************************************************************
884
 *
885
 * FUNCTION:    acpi_ds_init_aml_walk
886
 *
887
 * PARAMETERS:  walk_state      - New state to be initialized
888
 *              Op              - Current parse op
889
 *              method_node     - Control method NS node, if any
890
 *              aml_start       - Start of AML
891
 *              aml_length      - Length of AML
892
 *              Params          - Method args, if any
893
 *              return_obj_desc - Where to store a return object, if any
894
 *              pass_number     - 1, 2, or 3
895
 *
896
 * RETURN:      Status
897
 *
898
 * DESCRIPTION: Initialize a walk state for a pass 1 or 2 parse tree walk
899
 *
900
 ******************************************************************************/
901
 
902
acpi_status
903
acpi_ds_init_aml_walk (
904
        struct acpi_walk_state          *walk_state,
905
        union acpi_parse_object         *op,
906
        struct acpi_namespace_node      *method_node,
907
        u8                              *aml_start,
908
        u32                             aml_length,
909
        union acpi_operand_object       **params,
910
        union acpi_operand_object       **return_obj_desc,
911
        u32                             pass_number)
912
{
913
        acpi_status                     status;
914
        struct acpi_parse_state         *parser_state = &walk_state->parser_state;
915
        union acpi_parse_object         *extra_op;
916
 
917
 
918
        ACPI_FUNCTION_TRACE ("ds_init_aml_walk");
919
 
920
 
921
        walk_state->parser_state.aml    =
922
        walk_state->parser_state.aml_start = aml_start;
923
        walk_state->parser_state.aml_end =
924
        walk_state->parser_state.pkg_end = aml_start + aml_length;
925
 
926
        /* The next_op of the next_walk will be the beginning of the method */
927
 
928
        walk_state->next_op             = NULL;
929
        walk_state->params              = params;
930
        walk_state->caller_return_desc  = return_obj_desc;
931
 
932
        status = acpi_ps_init_scope (&walk_state->parser_state, op);
933
        if (ACPI_FAILURE (status)) {
934
                return_ACPI_STATUS (status);
935
        }
936
 
937
        if (method_node) {
938
                walk_state->parser_state.start_node = method_node;
939
                walk_state->walk_type            = ACPI_WALK_METHOD;
940
                walk_state->method_node          = method_node;
941
                walk_state->method_desc          = acpi_ns_get_attached_object (method_node);
942
 
943
                /* Push start scope on scope stack and make it current  */
944
 
945
                status = acpi_ds_scope_stack_push (method_node, ACPI_TYPE_METHOD, walk_state);
946
                if (ACPI_FAILURE (status)) {
947
                        return_ACPI_STATUS (status);
948
                }
949
 
950
                /* Init the method arguments */
951
 
952
                status = acpi_ds_method_data_init_args (params, ACPI_METHOD_NUM_ARGS, walk_state);
953
                if (ACPI_FAILURE (status)) {
954
                        return_ACPI_STATUS (status);
955
                }
956
        }
957
        else {
958
                /*
959
                 * Setup the current scope.
960
                 * Find a Named Op that has a namespace node associated with it.
961
                 * search upwards from this Op.  Current scope is the first
962
                 * Op with a namespace node.
963
                 */
964
                extra_op = parser_state->start_op;
965
                while (extra_op && !extra_op->common.node) {
966
                        extra_op = extra_op->common.parent;
967
                }
968
 
969
                if (!extra_op) {
970
                        parser_state->start_node = NULL;
971
                }
972
                else {
973
                        parser_state->start_node = extra_op->common.node;
974
                }
975
 
976
                if (parser_state->start_node) {
977
                        /* Push start scope on scope stack and make it current  */
978
 
979
                        status = acpi_ds_scope_stack_push (parser_state->start_node,
980
                                          parser_state->start_node->type, walk_state);
981
                        if (ACPI_FAILURE (status)) {
982
                                return_ACPI_STATUS (status);
983
                        }
984
                }
985
        }
986
 
987
        status = acpi_ds_init_callbacks (walk_state, pass_number);
988
        return_ACPI_STATUS (status);
989
}
990
 
991
 
992
/*******************************************************************************
993
 *
994
 * FUNCTION:    acpi_ds_delete_walk_state
995
 *
996
 * PARAMETERS:  walk_state      - State to delete
997
 *
998
 * RETURN:      Status
999
 *
1000
 * DESCRIPTION: Delete a walk state including all internal data structures
1001
 *
1002
 ******************************************************************************/
1003
 
1004
void
1005
acpi_ds_delete_walk_state (
1006
        struct acpi_walk_state          *walk_state)
1007
{
1008
        union acpi_generic_state        *state;
1009
 
1010
 
1011
        ACPI_FUNCTION_TRACE_PTR ("ds_delete_walk_state", walk_state);
1012
 
1013
 
1014
        if (!walk_state) {
1015
                return;
1016
        }
1017
 
1018
        if (walk_state->data_type != ACPI_DESC_TYPE_WALK) {
1019
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "%p is not a valid walk state\n", walk_state));
1020
                return;
1021
        }
1022
 
1023
        if (walk_state->parser_state.scope) {
1024
                ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "%p walk still has a scope list\n", walk_state));
1025
        }
1026
 
1027
        /* Always must free any linked control states */
1028
 
1029
        while (walk_state->control_state) {
1030
                state = walk_state->control_state;
1031
                walk_state->control_state = state->common.next;
1032
 
1033
                acpi_ut_delete_generic_state (state);
1034
        }
1035
 
1036
        /* Always must free any linked parse states */
1037
 
1038
        while (walk_state->scope_info) {
1039
                state = walk_state->scope_info;
1040
                walk_state->scope_info = state->common.next;
1041
 
1042
                acpi_ut_delete_generic_state (state);
1043
        }
1044
 
1045
        /* Always must free any stacked result states */
1046
 
1047
        while (walk_state->results) {
1048
                state = walk_state->results;
1049
                walk_state->results = state->common.next;
1050
 
1051
                acpi_ut_delete_generic_state (state);
1052
        }
1053
 
1054
        acpi_ut_release_to_cache (ACPI_MEM_LIST_WALK, walk_state);
1055
        return_VOID;
1056
}
1057
 
1058
 
1059
/******************************************************************************
1060
 *
1061
 * FUNCTION:    acpi_ds_delete_walk_state_cache
1062
 *
1063
 * PARAMETERS:  None
1064
 *
1065
 * RETURN:      Status
1066
 *
1067
 * DESCRIPTION: Purge the global state object cache.  Used during subsystem
1068
 *              termination.
1069
 *
1070
 ******************************************************************************/
1071
 
1072
void
1073
acpi_ds_delete_walk_state_cache (
1074
        void)
1075
{
1076
        ACPI_FUNCTION_TRACE ("ds_delete_walk_state_cache");
1077
 
1078
 
1079
        acpi_ut_delete_generic_cache (ACPI_MEM_LIST_WALK);
1080
        return_VOID;
1081
}
1082
 
1083
 

powered by: WebSVN 2.1.0

© copyright 1999-2025 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.