1 2/****************************************************************************** 3 * 4 * Module Name: exresop - AML Interpreter operand/object resolution 5 * $Revision: 1.1.1.1 $ 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 ("exresop") 40 41 42/******************************************************************************* 43 * 44 * FUNCTION: Acpi_ex_check_object_type 45 * 46 * PARAMETERS: Type_needed Object type needed 47 * This_type Actual object type 48 * Object Object pointer 49 * 50 * RETURN: Status 51 * 52 * DESCRIPTION: Check required type against actual type 53 * 54 ******************************************************************************/ 55 56acpi_status 57acpi_ex_check_object_type ( 58 acpi_object_type type_needed, 59 acpi_object_type this_type, 60 void *object) 61{ 62 PROC_NAME ("Ex_check_object_type"); 63 64 65 if (type_needed == ACPI_TYPE_ANY) { 66 /* All types OK, so we don't perform any typechecks */ 67 68 return (AE_OK); 69 } 70 71 if (type_needed != this_type) { 72 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 73 "Needed [%s], found [%s] %p\n", 74 acpi_ut_get_type_name (type_needed), 75 acpi_ut_get_type_name (this_type), object)); 76 77 return (AE_AML_OPERAND_TYPE); 78 } 79 80 return (AE_OK); 81} 82 83 84/******************************************************************************* 85 * 86 * FUNCTION: Acpi_ex_resolve_operands 87 * 88 * PARAMETERS: Opcode Opcode being interpreted 89 * Stack_ptr Top of operand stack 90 * 91 * RETURN: Status 92 * 93 * DESCRIPTION: Convert stack entries to required types 94 * 95 * Each nibble in Arg_types represents one required operand 96 * and indicates the required Type: 97 * 98 * The corresponding stack entry will be converted to the 99 * required type if possible, else return an exception 100 * 101 ******************************************************************************/ 102 103acpi_status 104acpi_ex_resolve_operands ( 105 u16 opcode, 106 acpi_operand_object **stack_ptr, 107 acpi_walk_state *walk_state) 108{ 109 acpi_operand_object *obj_desc; 110 acpi_status status = AE_OK; 111 u8 object_type; 112 void *temp_node; 113 u32 arg_types; 114 const acpi_opcode_info *op_info; 115 u32 this_arg_type; 116 acpi_object_type type_needed; 117 118 119 FUNCTION_TRACE_U32 ("Ex_resolve_operands", opcode); 120 121 122 op_info = acpi_ps_get_opcode_info (opcode); 123 if (op_info->class == AML_CLASS_UNKNOWN) { 124 return_ACPI_STATUS (AE_AML_BAD_OPCODE); 125 } 126 127 128 arg_types = op_info->runtime_args; 129 if (arg_types == ARGI_INVALID_OPCODE) { 130 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Internal - %X is not a valid AML opcode\n", 131 opcode)); 132 133 return_ACPI_STATUS (AE_AML_INTERNAL); 134 } 135 136 ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Opcode %X Operand_types=%X \n", 137 opcode, arg_types)); 138 139 140 /* 141 * Normal exit is with (Arg_types == 0) at end of argument list. 142 * Function will return an exception from within the loop upon 143 * finding an entry which is not (or cannot be converted 144 * to) the required type; if stack underflows; or upon 145 * finding a NULL stack entry (which should not happen). 146 */ 147 while (GET_CURRENT_ARG_TYPE (arg_types)) { 148 if (!stack_ptr || !*stack_ptr) { 149 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Internal - null stack entry at %p\n", 150 stack_ptr)); 151 152 return_ACPI_STATUS (AE_AML_INTERNAL); 153 } 154 155 /* Extract useful items */ 156 157 obj_desc = *stack_ptr; 158 159 /* Decode the descriptor type */ 160 161 if (VALID_DESCRIPTOR_TYPE (obj_desc, ACPI_DESC_TYPE_NAMED)) { 162 /* Node */ 163 164 object_type = ((acpi_namespace_node *) obj_desc)->type; 165 } 166 167 else if (VALID_DESCRIPTOR_TYPE (obj_desc, ACPI_DESC_TYPE_INTERNAL)) { 168 /* ACPI internal object */ 169 170 object_type = obj_desc->common.type; 171 172 /* Check for bad acpi_object_type */ 173 174 if (!acpi_ex_validate_object_type (object_type)) { 175 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Bad operand object type [%X]\n", 176 object_type)); 177 178 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 179 } 180 181 if (object_type == (u8) INTERNAL_TYPE_REFERENCE) { 182 /* 183 * Decode the Reference 184 */ 185 op_info = acpi_ps_get_opcode_info (opcode); 186 if (op_info->class == AML_CLASS_UNKNOWN) { 187 return_ACPI_STATUS (AE_AML_BAD_OPCODE); 188 } 189 190 191 switch (obj_desc->reference.opcode) { 192 case AML_ZERO_OP: 193 case AML_ONE_OP: 194 case AML_ONES_OP: 195 case AML_DEBUG_OP: 196 case AML_NAME_OP: 197 case AML_INDEX_OP: 198 case AML_ARG_OP: 199 case AML_LOCAL_OP: 200 case AML_REVISION_OP: 201 202 DEBUG_ONLY_MEMBERS (ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 203 "Reference Opcode: %s\n", op_info->name))); 204 break; 205 206 default: 207 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 208 "Reference Opcode: Unknown [%02x]\n", 209 obj_desc->reference.opcode)); 210 211 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 212 break; 213 } 214 } 215 } 216 217 else { 218 /* Invalid descriptor */ 219 220 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 221 "Bad descriptor type %X in Obj %p\n", 222 obj_desc->common.data_type, obj_desc)); 223 224 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 225 } 226 227 228 /* 229 * Get one argument type, point to the next 230 */ 231 this_arg_type = GET_CURRENT_ARG_TYPE (arg_types); 232 INCREMENT_ARG_LIST (arg_types); 233 234 235 /* 236 * Handle cases where the object does not need to be 237 * resolved to a value 238 */ 239 switch (this_arg_type) { 240 241 case ARGI_REFERENCE: /* References */ 242 case ARGI_INTEGER_REF: 243 case ARGI_OBJECT_REF: 244 case ARGI_DEVICE_REF: 245 case ARGI_TARGETREF: /* TBD: must implement implicit conversion rules before store */ 246 case ARGI_FIXED_TARGET: /* No implicit conversion before store to target */ 247 case ARGI_SIMPLE_TARGET: /* Name, Local, or Arg - no implicit conversion */ 248 249 /* Need an operand of type INTERNAL_TYPE_REFERENCE */ 250 251 if (VALID_DESCRIPTOR_TYPE (obj_desc, ACPI_DESC_TYPE_NAMED)) /* direct name ptr OK as-is */ { 252 goto next_operand; 253 } 254 255 status = acpi_ex_check_object_type (INTERNAL_TYPE_REFERENCE, 256 object_type, obj_desc); 257 if (ACPI_FAILURE (status)) { 258 return_ACPI_STATUS (status); 259 } 260 261 262 if (AML_NAME_OP == obj_desc->reference.opcode) { 263 /* 264 * Convert an indirect name ptr to direct name ptr and put 265 * it on the stack 266 */ 267 temp_node = obj_desc->reference.object; 268 acpi_ut_remove_reference (obj_desc); 269 (*stack_ptr) = temp_node; 270 } 271 272 goto next_operand; 273 break; 274 275 276 case ARGI_ANYTYPE: 277 278 /* 279 * We don't want to resolve Index_op reference objects during 280 * a store because this would be an implicit De_ref_of operation. 281 * Instead, we just want to store the reference object. 282 * -- All others must be resolved below. 283 */ 284 if ((opcode == AML_STORE_OP) && 285 ((*stack_ptr)->common.type == INTERNAL_TYPE_REFERENCE) && 286 ((*stack_ptr)->reference.opcode == AML_INDEX_OP)) { 287 goto next_operand; 288 } 289 break; 290 } 291 292 293 /* 294 * Resolve this object to a value 295 */ 296 status = acpi_ex_resolve_to_value (stack_ptr, walk_state); 297 if (ACPI_FAILURE (status)) { 298 return_ACPI_STATUS (status); 299 } 300 301 302 /* 303 * Check the resulting object (value) type 304 */ 305 switch (this_arg_type) { 306 /* 307 * For the simple cases, only one type of resolved object 308 * is allowed 309 */ 310 case ARGI_MUTEX: 311 312 /* Need an operand of type ACPI_TYPE_MUTEX */ 313 314 type_needed = ACPI_TYPE_MUTEX; 315 break; 316 317 case ARGI_EVENT: 318 319 /* Need an operand of type ACPI_TYPE_EVENT */ 320 321 type_needed = ACPI_TYPE_EVENT; 322 break; 323 324 case ARGI_REGION: 325 326 /* Need an operand of type ACPI_TYPE_REGION */ 327 328 type_needed = ACPI_TYPE_REGION; 329 break; 330 331 case ARGI_IF: /* If */ 332 333 /* Need an operand of type INTERNAL_TYPE_IF */ 334 335 type_needed = INTERNAL_TYPE_IF; 336 break; 337 338 case ARGI_PACKAGE: /* Package */ 339 340 /* Need an operand of type ACPI_TYPE_PACKAGE */ 341 342 type_needed = ACPI_TYPE_PACKAGE; 343 break; 344 345 case ARGI_ANYTYPE: 346 347 /* Any operand type will do */ 348 349 type_needed = ACPI_TYPE_ANY; 350 break; 351 352 353 /* 354 * The more complex cases allow multiple resolved object types 355 */ 356 case ARGI_INTEGER: /* Number */ 357 358 /* 359 * Need an operand of type ACPI_TYPE_INTEGER, 360 * But we can implicitly convert from a STRING or BUFFER 361 */ 362 status = acpi_ex_convert_to_integer (*stack_ptr, stack_ptr, walk_state); 363 if (ACPI_FAILURE (status)) { 364 if (status == AE_TYPE) { 365 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 366 "Needed [Integer/String/Buffer], found [%s] %p\n", 367 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 368 369 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 370 } 371 372 return_ACPI_STATUS (status); 373 } 374 375 goto next_operand; 376 break; 377 378 379 case ARGI_BUFFER: 380 381 /* 382 * Need an operand of type ACPI_TYPE_BUFFER, 383 * But we can implicitly convert from a STRING or INTEGER 384 */ 385 status = acpi_ex_convert_to_buffer (*stack_ptr, stack_ptr, walk_state); 386 if (ACPI_FAILURE (status)) { 387 if (status == AE_TYPE) { 388 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 389 "Needed [Integer/String/Buffer], found [%s] %p\n", 390 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 391 392 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 393 } 394 395 return_ACPI_STATUS (status); 396 } 397 398 goto next_operand; 399 break; 400 401 402 case ARGI_STRING: 403 404 /* 405 * Need an operand of type ACPI_TYPE_STRING, 406 * But we can implicitly convert from a BUFFER or INTEGER 407 */ 408 status = acpi_ex_convert_to_string (*stack_ptr, stack_ptr, 16, ACPI_UINT32_MAX, walk_state); 409 if (ACPI_FAILURE (status)) { 410 if (status == AE_TYPE) { 411 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 412 "Needed [Integer/String/Buffer], found [%s] %p\n", 413 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 414 415 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 416 } 417 418 return_ACPI_STATUS (status); 419 } 420 421 goto next_operand; 422 break; 423 424 425 case ARGI_COMPUTEDATA: 426 427 /* Need an operand of type INTEGER, STRING or BUFFER */ 428 429 if ((ACPI_TYPE_INTEGER != (*stack_ptr)->common.type) && 430 (ACPI_TYPE_STRING != (*stack_ptr)->common.type) && 431 (ACPI_TYPE_BUFFER != (*stack_ptr)->common.type)) { 432 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 433 "Needed [Integer/String/Buffer], found [%s] %p\n", 434 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 435 436 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 437 } 438 goto next_operand; 439 break; 440 441 442 case ARGI_DATAOBJECT: 443 /* 444 * ARGI_DATAOBJECT is only used by the Size_of operator. 445 * 446 * The ACPI specification allows Size_of to return the size of 447 * a Buffer, String or Package. However, the MS ACPI.SYS AML 448 * Interpreter also allows an Node reference to return without 449 * error with a size of 4. 450 */ 451 452 /* Need a buffer, string, package or Node reference */ 453 454 if (((*stack_ptr)->common.type != ACPI_TYPE_BUFFER) && 455 ((*stack_ptr)->common.type != ACPI_TYPE_STRING) && 456 ((*stack_ptr)->common.type != ACPI_TYPE_PACKAGE) && 457 ((*stack_ptr)->common.type != INTERNAL_TYPE_REFERENCE)) { 458 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 459 "Needed [Buf/Str/Pkg/Ref], found [%s] %p\n", 460 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 461 462 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 463 } 464 465 /* 466 * If this is a reference, only allow a reference to an Node. 467 */ 468 if ((*stack_ptr)->common.type == INTERNAL_TYPE_REFERENCE) { 469 if (!(*stack_ptr)->reference.node) { 470 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 471 "Needed [Node Reference], found [%p]\n", 472 *stack_ptr)); 473 474 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 475 } 476 } 477 goto next_operand; 478 break; 479 480 481 case ARGI_COMPLEXOBJ: 482 483 /* Need a buffer or package or (ACPI 2.0) String */ 484 485 if (((*stack_ptr)->common.type != ACPI_TYPE_BUFFER) && 486 ((*stack_ptr)->common.type != ACPI_TYPE_STRING) && 487 ((*stack_ptr)->common.type != ACPI_TYPE_PACKAGE)) { 488 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 489 "Needed [Buf/Pkg], found [%s] %p\n", 490 acpi_ut_get_type_name ((*stack_ptr)->common.type), *stack_ptr)); 491 492 return_ACPI_STATUS (AE_AML_OPERAND_TYPE); 493 } 494 goto next_operand; 495 break; 496 497 498 default: 499 500 /* Unknown type */ 501 502 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 503 "Internal - Unknown ARGI type %X\n", 504 this_arg_type)); 505 506 return_ACPI_STATUS (AE_BAD_PARAMETER); 507 } 508 509 510 /* 511 * Make sure that the original object was resolved to the 512 * required object type (Simple cases only). 513 */ 514 status = acpi_ex_check_object_type (type_needed, 515 (*stack_ptr)->common.type, *stack_ptr); 516 if (ACPI_FAILURE (status)) { 517 return_ACPI_STATUS (status); 518 } 519 520 521next_operand: 522 /* 523 * If more operands needed, decrement Stack_ptr to point 524 * to next operand on stack 525 */ 526 if (GET_CURRENT_ARG_TYPE (arg_types)) { 527 stack_ptr--; 528 } 529 530 } /* while (*Types) */ 531 532 533 return_ACPI_STATUS (status); 534} 535 536 537