Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
at v2.6.13 716 lines 19 kB view raw
1/****************************************************************************** 2 * 3 * Module Name: exconvrt - Object conversion 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#include <acpi/acinterp.h> 47#include <acpi/amlcode.h> 48 49 50#define _COMPONENT ACPI_EXECUTER 51 ACPI_MODULE_NAME ("exconvrt") 52 53/* Local prototypes */ 54 55static u32 56acpi_ex_convert_to_ascii ( 57 acpi_integer integer, 58 u16 base, 59 u8 *string, 60 u8 max_length); 61 62 63/******************************************************************************* 64 * 65 * FUNCTION: acpi_ex_convert_to_integer 66 * 67 * PARAMETERS: obj_desc - Object to be converted. Must be an 68 * Integer, Buffer, or String 69 * result_desc - Where the new Integer object is returned 70 * Flags - Used for string conversion 71 * 72 * RETURN: Status 73 * 74 * DESCRIPTION: Convert an ACPI Object to an integer. 75 * 76 ******************************************************************************/ 77 78acpi_status 79acpi_ex_convert_to_integer ( 80 union acpi_operand_object *obj_desc, 81 union acpi_operand_object **result_desc, 82 u32 flags) 83{ 84 union acpi_operand_object *return_desc; 85 u8 *pointer; 86 acpi_integer result; 87 u32 i; 88 u32 count; 89 acpi_status status; 90 91 92 ACPI_FUNCTION_TRACE_PTR ("ex_convert_to_integer", obj_desc); 93 94 95 switch (ACPI_GET_OBJECT_TYPE (obj_desc)) { 96 case ACPI_TYPE_INTEGER: 97 98 /* No conversion necessary */ 99 100 *result_desc = obj_desc; 101 return_ACPI_STATUS (AE_OK); 102 103 case ACPI_TYPE_BUFFER: 104 case ACPI_TYPE_STRING: 105 106 /* Note: Takes advantage of common buffer/string fields */ 107 108 pointer = obj_desc->buffer.pointer; 109 count = obj_desc->buffer.length; 110 break; 111 112 default: 113 return_ACPI_STATUS (AE_TYPE); 114 } 115 116 /* 117 * Convert the buffer/string to an integer. Note that both buffers and 118 * strings are treated as raw data - we don't convert ascii to hex for 119 * strings. 120 * 121 * There are two terminating conditions for the loop: 122 * 1) The size of an integer has been reached, or 123 * 2) The end of the buffer or string has been reached 124 */ 125 result = 0; 126 127 /* String conversion is different than Buffer conversion */ 128 129 switch (ACPI_GET_OBJECT_TYPE (obj_desc)) { 130 case ACPI_TYPE_STRING: 131 132 /* 133 * Convert string to an integer - for most cases, the string must be 134 * hexadecimal as per the ACPI specification. The only exception (as 135 * of ACPI 3.0) is that the to_integer() operator allows both decimal 136 * and hexadecimal strings (hex prefixed with "0x"). 137 */ 138 status = acpi_ut_strtoul64 ((char *) pointer, flags, &result); 139 if (ACPI_FAILURE (status)) { 140 return_ACPI_STATUS (status); 141 } 142 break; 143 144 145 case ACPI_TYPE_BUFFER: 146 147 /* Check for zero-length buffer */ 148 149 if (!count) { 150 return_ACPI_STATUS (AE_AML_BUFFER_LIMIT); 151 } 152 153 /* Transfer no more than an integer's worth of data */ 154 155 if (count > acpi_gbl_integer_byte_width) { 156 count = acpi_gbl_integer_byte_width; 157 } 158 159 /* 160 * Convert buffer to an integer - we simply grab enough raw data 161 * from the buffer to fill an integer 162 */ 163 for (i = 0; i < count; i++) { 164 /* 165 * Get next byte and shift it into the Result. 166 * Little endian is used, meaning that the first byte of the buffer 167 * is the LSB of the integer 168 */ 169 result |= (((acpi_integer) pointer[i]) << (i * 8)); 170 } 171 break; 172 173 174 default: 175 /* No other types can get here */ 176 break; 177 } 178 179 /* Create a new integer */ 180 181 return_desc = acpi_ut_create_internal_object (ACPI_TYPE_INTEGER); 182 if (!return_desc) { 183 return_ACPI_STATUS (AE_NO_MEMORY); 184 } 185 186 /* Save the Result */ 187 188 return_desc->integer.value = result; 189 acpi_ex_truncate_for32bit_table (return_desc); 190 *result_desc = return_desc; 191 return_ACPI_STATUS (AE_OK); 192} 193 194 195/******************************************************************************* 196 * 197 * FUNCTION: acpi_ex_convert_to_buffer 198 * 199 * PARAMETERS: obj_desc - Object to be converted. Must be an 200 * Integer, Buffer, or String 201 * result_desc - Where the new buffer object is returned 202 * 203 * RETURN: Status 204 * 205 * DESCRIPTION: Convert an ACPI Object to a Buffer 206 * 207 ******************************************************************************/ 208 209acpi_status 210acpi_ex_convert_to_buffer ( 211 union acpi_operand_object *obj_desc, 212 union acpi_operand_object **result_desc) 213{ 214 union acpi_operand_object *return_desc; 215 u8 *new_buf; 216 217 218 ACPI_FUNCTION_TRACE_PTR ("ex_convert_to_buffer", obj_desc); 219 220 221 switch (ACPI_GET_OBJECT_TYPE (obj_desc)) { 222 case ACPI_TYPE_BUFFER: 223 224 /* No conversion necessary */ 225 226 *result_desc = obj_desc; 227 return_ACPI_STATUS (AE_OK); 228 229 230 case ACPI_TYPE_INTEGER: 231 232 /* 233 * Create a new Buffer object. 234 * Need enough space for one integer 235 */ 236 return_desc = acpi_ut_create_buffer_object (acpi_gbl_integer_byte_width); 237 if (!return_desc) { 238 return_ACPI_STATUS (AE_NO_MEMORY); 239 } 240 241 /* Copy the integer to the buffer, LSB first */ 242 243 new_buf = return_desc->buffer.pointer; 244 ACPI_MEMCPY (new_buf, 245 &obj_desc->integer.value, 246 acpi_gbl_integer_byte_width); 247 break; 248 249 250 case ACPI_TYPE_STRING: 251 252 /* 253 * Create a new Buffer object 254 * Size will be the string length 255 * 256 * NOTE: Add one to the string length to include the null terminator. 257 * The ACPI spec is unclear on this subject, but there is existing 258 * ASL/AML code that depends on the null being transferred to the new 259 * buffer. 260 */ 261 return_desc = acpi_ut_create_buffer_object ( 262 (acpi_size) obj_desc->string.length + 1); 263 if (!return_desc) { 264 return_ACPI_STATUS (AE_NO_MEMORY); 265 } 266 267 /* Copy the string to the buffer */ 268 269 new_buf = return_desc->buffer.pointer; 270 ACPI_STRNCPY ((char *) new_buf, (char *) obj_desc->string.pointer, 271 obj_desc->string.length); 272 break; 273 274 275 default: 276 return_ACPI_STATUS (AE_TYPE); 277 } 278 279 /* Mark buffer initialized */ 280 281 return_desc->common.flags |= AOPOBJ_DATA_VALID; 282 *result_desc = return_desc; 283 return_ACPI_STATUS (AE_OK); 284} 285 286 287/******************************************************************************* 288 * 289 * FUNCTION: acpi_ex_convert_to_ascii 290 * 291 * PARAMETERS: Integer - Value to be converted 292 * Base - ACPI_STRING_DECIMAL or ACPI_STRING_HEX 293 * String - Where the string is returned 294 * data_width - Size of data item to be converted, in bytes 295 * 296 * RETURN: Actual string length 297 * 298 * DESCRIPTION: Convert an ACPI Integer to a hex or decimal string 299 * 300 ******************************************************************************/ 301 302static u32 303acpi_ex_convert_to_ascii ( 304 acpi_integer integer, 305 u16 base, 306 u8 *string, 307 u8 data_width) 308{ 309 acpi_integer digit; 310 acpi_native_uint i; 311 acpi_native_uint j; 312 acpi_native_uint k = 0; 313 acpi_native_uint hex_length; 314 acpi_native_uint decimal_length; 315 u32 remainder; 316 u8 supress_zeros; 317 318 319 ACPI_FUNCTION_ENTRY (); 320 321 322 switch (base) { 323 case 10: 324 325 /* Setup max length for the decimal number */ 326 327 switch (data_width) { 328 case 1: 329 decimal_length = ACPI_MAX8_DECIMAL_DIGITS; 330 break; 331 332 case 4: 333 decimal_length = ACPI_MAX32_DECIMAL_DIGITS; 334 break; 335 336 case 8: 337 default: 338 decimal_length = ACPI_MAX64_DECIMAL_DIGITS; 339 break; 340 } 341 342 supress_zeros = TRUE; /* No leading zeros */ 343 remainder = 0; 344 345 for (i = decimal_length; i > 0; i--) { 346 /* Divide by nth factor of 10 */ 347 348 digit = integer; 349 for (j = 0; j < i; j++) { 350 (void) acpi_ut_short_divide (digit, 10, &digit, &remainder); 351 } 352 353 /* Handle leading zeros */ 354 355 if (remainder != 0) { 356 supress_zeros = FALSE; 357 } 358 359 if (!supress_zeros) { 360 string[k] = (u8) (ACPI_ASCII_ZERO + remainder); 361 k++; 362 } 363 } 364 break; 365 366 case 16: 367 368 /* hex_length: 2 ascii hex chars per data byte */ 369 370 hex_length = ACPI_MUL_2 (data_width); 371 for (i = 0, j = (hex_length-1); i < hex_length; i++, j--) { 372 /* Get one hex digit, most significant digits first */ 373 374 string[k] = (u8) acpi_ut_hex_to_ascii_char (integer, ACPI_MUL_4 (j)); 375 k++; 376 } 377 break; 378 379 default: 380 return (0); 381 } 382 383 /* 384 * Since leading zeros are supressed, we must check for the case where 385 * the integer equals 0 386 * 387 * Finally, null terminate the string and return the length 388 */ 389 if (!k) { 390 string [0] = ACPI_ASCII_ZERO; 391 k = 1; 392 } 393 394 string [k] = 0; 395 return ((u32) k); 396} 397 398 399/******************************************************************************* 400 * 401 * FUNCTION: acpi_ex_convert_to_string 402 * 403 * PARAMETERS: obj_desc - Object to be converted. Must be an 404 * Integer, Buffer, or String 405 * result_desc - Where the string object is returned 406 * Type - String flags (base and conversion type) 407 * 408 * RETURN: Status 409 * 410 * DESCRIPTION: Convert an ACPI Object to a string 411 * 412 ******************************************************************************/ 413 414acpi_status 415acpi_ex_convert_to_string ( 416 union acpi_operand_object *obj_desc, 417 union acpi_operand_object **result_desc, 418 u32 type) 419{ 420 union acpi_operand_object *return_desc; 421 u8 *new_buf; 422 u32 i; 423 u32 string_length = 0; 424 u16 base = 16; 425 u8 separator = ','; 426 427 428 ACPI_FUNCTION_TRACE_PTR ("ex_convert_to_string", obj_desc); 429 430 431 switch (ACPI_GET_OBJECT_TYPE (obj_desc)) { 432 case ACPI_TYPE_STRING: 433 434 /* No conversion necessary */ 435 436 *result_desc = obj_desc; 437 return_ACPI_STATUS (AE_OK); 438 439 440 case ACPI_TYPE_INTEGER: 441 442 switch (type) { 443 case ACPI_EXPLICIT_CONVERT_DECIMAL: 444 445 /* Make room for maximum decimal number */ 446 447 string_length = ACPI_MAX_DECIMAL_DIGITS; 448 base = 10; 449 break; 450 451 default: 452 453 /* Two hex string characters for each integer byte */ 454 455 string_length = ACPI_MUL_2 (acpi_gbl_integer_byte_width); 456 break; 457 } 458 459 /* 460 * Create a new String 461 * Need enough space for one ASCII integer (plus null terminator) 462 */ 463 return_desc = acpi_ut_create_string_object ((acpi_size) string_length); 464 if (!return_desc) { 465 return_ACPI_STATUS (AE_NO_MEMORY); 466 } 467 468 new_buf = return_desc->buffer.pointer; 469 470 /* Convert integer to string */ 471 472 string_length = acpi_ex_convert_to_ascii (obj_desc->integer.value, base, 473 new_buf, acpi_gbl_integer_byte_width); 474 475 /* Null terminate at the correct place */ 476 477 return_desc->string.length = string_length; 478 new_buf [string_length] = 0; 479 break; 480 481 482 case ACPI_TYPE_BUFFER: 483 484 /* Setup string length, base, and separator */ 485 486 switch (type) { 487 case ACPI_EXPLICIT_CONVERT_DECIMAL: /* Used by to_decimal_string */ 488 /* 489 * From ACPI: "If Data is a buffer, it is converted to a string of 490 * decimal values separated by commas." 491 */ 492 base = 10; 493 494 /* 495 * Calculate the final string length. Individual string values 496 * are variable length (include separator for each) 497 */ 498 for (i = 0; i < obj_desc->buffer.length; i++) { 499 if (obj_desc->buffer.pointer[i] >= 100) { 500 string_length += 4; 501 } 502 else if (obj_desc->buffer.pointer[i] >= 10) { 503 string_length += 3; 504 } 505 else { 506 string_length += 2; 507 } 508 } 509 break; 510 511 case ACPI_IMPLICIT_CONVERT_HEX: 512 /* 513 * From the ACPI spec: 514 *"The entire contents of the buffer are converted to a string of 515 * two-character hexadecimal numbers, each separated by a space." 516 */ 517 separator = ' '; 518 string_length = (obj_desc->buffer.length * 3); 519 break; 520 521 case ACPI_EXPLICIT_CONVERT_HEX: /* Used by to_hex_string */ 522 /* 523 * From ACPI: "If Data is a buffer, it is converted to a string of 524 * hexadecimal values separated by commas." 525 */ 526 string_length = (obj_desc->buffer.length * 3); 527 break; 528 529 default: 530 return_ACPI_STATUS (AE_BAD_PARAMETER); 531 } 532 533 /* 534 * Perform the conversion. 535 * (-1 because of extra separator included in string_length from above) 536 */ 537 string_length--; 538 if (string_length > ACPI_MAX_STRING_CONVERSION) /* ACPI limit */ { 539 return_ACPI_STATUS (AE_AML_STRING_LIMIT); 540 } 541 542 /* Create a new string object and string buffer */ 543 544 return_desc = acpi_ut_create_string_object ((acpi_size) string_length); 545 if (!return_desc) { 546 return_ACPI_STATUS (AE_NO_MEMORY); 547 } 548 549 new_buf = return_desc->buffer.pointer; 550 551 /* 552 * Convert buffer bytes to hex or decimal values 553 * (separated by commas or spaces) 554 */ 555 for (i = 0; i < obj_desc->buffer.length; i++) { 556 new_buf += acpi_ex_convert_to_ascii ( 557 (acpi_integer) obj_desc->buffer.pointer[i], base, 558 new_buf, 1); 559 *new_buf++ = separator; /* each separated by a comma or space */ 560 } 561 562 /* 563 * Null terminate the string 564 * (overwrites final comma/space from above) 565 */ 566 new_buf--; 567 *new_buf = 0; 568 break; 569 570 default: 571 return_ACPI_STATUS (AE_TYPE); 572 } 573 574 *result_desc = return_desc; 575 return_ACPI_STATUS (AE_OK); 576} 577 578 579/******************************************************************************* 580 * 581 * FUNCTION: acpi_ex_convert_to_target_type 582 * 583 * PARAMETERS: destination_type - Current type of the destination 584 * source_desc - Source object to be converted. 585 * result_desc - Where the converted object is returned 586 * walk_state - Current method state 587 * 588 * RETURN: Status 589 * 590 * DESCRIPTION: Implements "implicit conversion" rules for storing an object. 591 * 592 ******************************************************************************/ 593 594acpi_status 595acpi_ex_convert_to_target_type ( 596 acpi_object_type destination_type, 597 union acpi_operand_object *source_desc, 598 union acpi_operand_object **result_desc, 599 struct acpi_walk_state *walk_state) 600{ 601 acpi_status status = AE_OK; 602 603 604 ACPI_FUNCTION_TRACE ("ex_convert_to_target_type"); 605 606 607 /* Default behavior */ 608 609 *result_desc = source_desc; 610 611 /* 612 * If required by the target, 613 * perform implicit conversion on the source before we store it. 614 */ 615 switch (GET_CURRENT_ARG_TYPE (walk_state->op_info->runtime_args)) { 616 case ARGI_SIMPLE_TARGET: 617 case ARGI_FIXED_TARGET: 618 case ARGI_INTEGER_REF: /* Handles Increment, Decrement cases */ 619 620 switch (destination_type) { 621 case ACPI_TYPE_LOCAL_REGION_FIELD: 622 /* 623 * Named field can always handle conversions 624 */ 625 break; 626 627 default: 628 /* No conversion allowed for these types */ 629 630 if (destination_type != ACPI_GET_OBJECT_TYPE (source_desc)) { 631 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 632 "Explicit operator, will store (%s) over existing type (%s)\n", 633 acpi_ut_get_object_type_name (source_desc), 634 acpi_ut_get_type_name (destination_type))); 635 status = AE_TYPE; 636 } 637 } 638 break; 639 640 641 case ARGI_TARGETREF: 642 643 switch (destination_type) { 644 case ACPI_TYPE_INTEGER: 645 case ACPI_TYPE_BUFFER_FIELD: 646 case ACPI_TYPE_LOCAL_BANK_FIELD: 647 case ACPI_TYPE_LOCAL_INDEX_FIELD: 648 /* 649 * These types require an Integer operand. We can convert 650 * a Buffer or a String to an Integer if necessary. 651 */ 652 status = acpi_ex_convert_to_integer (source_desc, result_desc, 653 16); 654 break; 655 656 657 case ACPI_TYPE_STRING: 658 /* 659 * The operand must be a String. We can convert an 660 * Integer or Buffer if necessary 661 */ 662 status = acpi_ex_convert_to_string (source_desc, result_desc, 663 ACPI_IMPLICIT_CONVERT_HEX); 664 break; 665 666 667 case ACPI_TYPE_BUFFER: 668 /* 669 * The operand must be a Buffer. We can convert an 670 * Integer or String if necessary 671 */ 672 status = acpi_ex_convert_to_buffer (source_desc, result_desc); 673 break; 674 675 676 default: 677 ACPI_REPORT_ERROR (("Bad destination type during conversion: %X\n", 678 destination_type)); 679 status = AE_AML_INTERNAL; 680 break; 681 } 682 break; 683 684 685 case ARGI_REFERENCE: 686 /* 687 * create_xxxx_field cases - we are storing the field object into the name 688 */ 689 break; 690 691 692 default: 693 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 694 "Unknown Target type ID 0x%X Op %s dest_type %s\n", 695 GET_CURRENT_ARG_TYPE (walk_state->op_info->runtime_args), 696 walk_state->op_info->name, acpi_ut_get_type_name (destination_type))); 697 698 ACPI_REPORT_ERROR (("Bad Target Type (ARGI): %X\n", 699 GET_CURRENT_ARG_TYPE (walk_state->op_info->runtime_args))) 700 status = AE_AML_INTERNAL; 701 } 702 703 /* 704 * Source-to-Target conversion semantics: 705 * 706 * If conversion to the target type cannot be performed, then simply 707 * overwrite the target with the new object and type. 708 */ 709 if (status == AE_TYPE) { 710 status = AE_OK; 711 } 712 713 return_ACPI_STATUS (status); 714} 715 716