File: /usr/src/linux/drivers/acpi/executer/exresnte.c

1     
2     /******************************************************************************
3      *
4      * Module Name: exresnte - AML Interpreter object resolution
5      *              $Revision: 41 $
6      *
7      *****************************************************************************/
8     
9     /*
10      *  Copyright (C) 2000, 2001 R. Byron Moore
11      *
12      *  This program is free software; you can redistribute it and/or modify
13      *  it under the terms of the GNU General Public License as published by
14      *  the Free Software Foundation; either version 2 of the License, or
15      *  (at your option) any later version.
16      *
17      *  This program is distributed in the hope that it will be useful,
18      *  but WITHOUT ANY WARRANTY; without even the implied warranty of
19      *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20      *  GNU General Public License for more details.
21      *
22      *  You should have received a copy of the GNU General Public License
23      *  along with this program; if not, write to the Free Software
24      *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
25      */
26     
27     
28     #include "acpi.h"
29     #include "amlcode.h"
30     #include "acparser.h"
31     #include "acdispat.h"
32     #include "acinterp.h"
33     #include "acnamesp.h"
34     #include "actables.h"
35     #include "acevents.h"
36     
37     
38     #define _COMPONENT          ACPI_EXECUTER
39     	 MODULE_NAME         ("exresnte")
40     
41     
42     /*******************************************************************************
43      *
44      * FUNCTION:    Acpi_ex_resolve_node_to_value
45      *
46      * PARAMETERS:  Stack_ptr       - Pointer to a location on a stack that contains
47      *                                a pointer to a Node
48      *              Walk_state      - Current state
49      *
50      * RETURN:      Status
51      *
52      * DESCRIPTION: Resolve a Namespace node (AKA a "direct name pointer") to
53      *              a valued object
54      *
55      * Note: for some of the data types, the pointer attached to the Node
56      * can be either a pointer to an actual internal object or a pointer into the
57      * AML stream itself.  These types are currently:
58      *
59      *      ACPI_TYPE_INTEGER
60      *      ACPI_TYPE_STRING
61      *      ACPI_TYPE_BUFFER
62      *      ACPI_TYPE_MUTEX
63      *      ACPI_TYPE_PACKAGE
64      *
65      ******************************************************************************/
66     
67     acpi_status
68     acpi_ex_resolve_node_to_value (
69     	acpi_namespace_node     **stack_ptr,
70     	acpi_walk_state         *walk_state)
71     
72     {
73     	acpi_status             status = AE_OK;
74     	acpi_operand_object     *val_desc;
75     	acpi_operand_object     *obj_desc = NULL;
76     	acpi_namespace_node     *node;
77     	acpi_object_type8       entry_type;
78     	acpi_integer            temp_val;
79     
80     
81     	FUNCTION_TRACE ("Ex_resolve_node_to_value");
82     
83     
84     	/*
85     	 * The stack pointer points to a acpi_namespace_node (Node).  Get the
86     	 * object that is attached to the Node.
87     	 */
88     	node      = *stack_ptr;
89     	val_desc  = acpi_ns_get_attached_object (node);
90     	entry_type = acpi_ns_get_type ((acpi_handle) node);
91     
92     	ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Entry=%p Val_desc=%p Type=%X\n",
93     		 node, val_desc, entry_type));
94     
95     
96     	/*
97     	 * Several object types require no further processing:
98     	 * 1) Devices rarely have an attached object, return the Node
99     	 * 2) Method locals and arguments have a pseudo-Node
100     	 */
101     	if (entry_type == ACPI_TYPE_DEVICE ||
102     		(node->flags & (ANOBJ_METHOD_ARG | ANOBJ_METHOD_LOCAL))) {
103     		return_ACPI_STATUS (AE_OK);
104     	}
105     
106     	if (!val_desc) {
107     		ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "No object attached to node %p\n",
108     			node));
109     		return_ACPI_STATUS (AE_AML_NO_OPERAND);
110     	}
111     
112     	/*
113     	 * Action is based on the type of the Node, which indicates the type
114     	 * of the attached object or pointer
115     	 */
116     	switch (entry_type) {
117     
118     	case ACPI_TYPE_PACKAGE:
119     
120     		if (ACPI_TYPE_PACKAGE != val_desc->common.type) {
121     			ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Object not a Package, type %s\n",
122     				acpi_ut_get_type_name (val_desc->common.type)));
123     			return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
124     		}
125     
126     		/* Return an additional reference to the object */
127     
128     		obj_desc = val_desc;
129     		acpi_ut_add_reference (obj_desc);
130     		break;
131     
132     
133     	case ACPI_TYPE_BUFFER:
134     
135     		if (ACPI_TYPE_BUFFER != val_desc->common.type) {
136     			ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Object not a Buffer, type %s\n",
137     				acpi_ut_get_type_name (val_desc->common.type)));
138     			return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
139     		}
140     
141     		/* Return an additional reference to the object */
142     
143     		obj_desc = val_desc;
144     		acpi_ut_add_reference (obj_desc);
145     		break;
146     
147     
148     	case ACPI_TYPE_STRING:
149     
150     		if (ACPI_TYPE_STRING != val_desc->common.type) {
151     			ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Object not a String, type %s\n",
152     				acpi_ut_get_type_name (val_desc->common.type)));
153     			return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
154     		}
155     
156     		/* Return an additional reference to the object */
157     
158     		obj_desc = val_desc;
159     		acpi_ut_add_reference (obj_desc);
160     		break;
161     
162     
163     	case ACPI_TYPE_INTEGER:
164     
165     		if (ACPI_TYPE_INTEGER != val_desc->common.type) {
166     			ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Object not a Integer, type %s\n",
167     				acpi_ut_get_type_name (val_desc->common.type)));
168     			return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
169     		}
170     
171     		/* Return an additional reference to the object */
172     
173     		obj_desc = val_desc;
174     		acpi_ut_add_reference (obj_desc);
175     		break;
176     
177     
178     	case ACPI_TYPE_BUFFER_FIELD:
179     	case INTERNAL_TYPE_REGION_FIELD:
180     	case INTERNAL_TYPE_BANK_FIELD:
181     	case INTERNAL_TYPE_INDEX_FIELD:
182     
183     		ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Field_read Node=%p Val_desc=%p Type=%X\n",
184     			node, val_desc, entry_type));
185     
186     		status = acpi_ex_read_data_from_field (val_desc, &obj_desc);
187     		break;
188     
189     
190     	/*
191     	 * For these objects, just return the object attached to the Node
192     	 */
193     	case ACPI_TYPE_MUTEX:
194     	case ACPI_TYPE_METHOD:
195     	case ACPI_TYPE_POWER:
196     	case ACPI_TYPE_PROCESSOR:
197     	case ACPI_TYPE_THERMAL:
198     	case ACPI_TYPE_EVENT:
199     	case ACPI_TYPE_REGION:
200     
201     		/* Return an additional reference to the object */
202     
203     		obj_desc = val_desc;
204     		acpi_ut_add_reference (obj_desc);
205     		break;
206     
207     
208     	/* TYPE_Any is untyped, and thus there is no object associated with it */
209     
210     	case ACPI_TYPE_ANY:
211     
212     		ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Untyped entry %p, no attached object!\n",
213     			node));
214     
215     		return_ACPI_STATUS (AE_AML_OPERAND_TYPE);  /* Cannot be AE_TYPE */
216     		break;
217     
218     
219     	/*
220     	 * The only named references allowed are named constants
221     	 *   e.g. -- Name (\OSFL, Ones)
222     	 */
223     	case INTERNAL_TYPE_REFERENCE:
224     
225     		switch (val_desc->reference.opcode) {
226     
227     		case AML_ZERO_OP:
228     
229     			temp_val = 0;
230     			break;
231     
232     		case AML_ONE_OP:
233     
234     			temp_val = 1;
235     			break;
236     
237     		case AML_ONES_OP:
238     
239     			temp_val = ACPI_INTEGER_MAX;
240     			break;
241     
242     		case AML_REVISION_OP:
243     
244     			temp_val = ACPI_CA_VERSION;
245     			break;
246     
247     		default:
248     
249     			ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Unsupported reference opcode %X\n",
250     				val_desc->reference.opcode));
251     
252     			return_ACPI_STATUS (AE_AML_BAD_OPCODE);
253     		}
254     
255     		/* Create object for result */
256     
257     		obj_desc = acpi_ut_create_internal_object (ACPI_TYPE_INTEGER);
258     		if (!obj_desc) {
259     			return_ACPI_STATUS (AE_NO_MEMORY);
260     		}
261     
262     		obj_desc->integer.value = temp_val;
263     
264     		/* Truncate value if we are executing from a 32-bit ACPI table */
265     
266     		acpi_ex_truncate_for32bit_table (obj_desc, walk_state);
267     		break;
268     
269     
270     	/* Default case is for unknown types */
271     
272     	default:
273     
274     		ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Node %p - Unknown object type %X\n",
275     			node, entry_type));
276     
277     		return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
278     
279     	} /* switch (Entry_type) */
280     
281     
282     	/* Put the object descriptor on the stack */
283     
284     	*stack_ptr = (void *) obj_desc;
285     	return_ACPI_STATUS (status);
286     }
287     
288     
289