1 /****************************************************************************** 2 * 3 * Module Name: nsprepkg - Validation of package objects for predefined names 4 * 5 *****************************************************************************/ 6 7 /* 8 * Copyright (C) 2000 - 2015, Intel Corp. 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 #include <acpi/acpi.h> 45 #include "accommon.h" 46 #include "acnamesp.h" 47 #include "acpredef.h" 48 49 #define _COMPONENT ACPI_NAMESPACE 50 ACPI_MODULE_NAME("nsprepkg") 51 52 /* Local prototypes */ 53 static acpi_status 54 acpi_ns_check_package_list(struct acpi_evaluate_info *info, 55 const union acpi_predefined_info *package, 56 union acpi_operand_object **elements, u32 count); 57 58 static acpi_status 59 acpi_ns_check_package_elements(struct acpi_evaluate_info *info, 60 union acpi_operand_object **elements, 61 u8 type1, 62 u32 count1, 63 u8 type2, u32 count2, u32 start_index); 64 65 /******************************************************************************* 66 * 67 * FUNCTION: acpi_ns_check_package 68 * 69 * PARAMETERS: info - Method execution information block 70 * return_object_ptr - Pointer to the object returned from the 71 * evaluation of a method or object 72 * 73 * RETURN: Status 74 * 75 * DESCRIPTION: Check a returned package object for the correct count and 76 * correct type of all sub-objects. 77 * 78 ******************************************************************************/ 79 80 acpi_status 81 acpi_ns_check_package(struct acpi_evaluate_info *info, 82 union acpi_operand_object **return_object_ptr) 83 { 84 union acpi_operand_object *return_object = *return_object_ptr; 85 const union acpi_predefined_info *package; 86 union acpi_operand_object **elements; 87 acpi_status status = AE_OK; 88 u32 expected_count; 89 u32 count; 90 u32 i; 91 92 ACPI_FUNCTION_NAME(ns_check_package); 93 94 /* The package info for this name is in the next table entry */ 95 96 package = info->predefined + 1; 97 98 ACPI_DEBUG_PRINT((ACPI_DB_NAMES, 99 "%s Validating return Package of Type %X, Count %X\n", 100 info->full_pathname, package->ret_info.type, 101 return_object->package.count)); 102 103 /* 104 * For variable-length Packages, we can safely remove all embedded 105 * and trailing NULL package elements 106 */ 107 acpi_ns_remove_null_elements(info, package->ret_info.type, 108 return_object); 109 110 /* Extract package count and elements array */ 111 112 elements = return_object->package.elements; 113 count = return_object->package.count; 114 115 /* 116 * Most packages must have at least one element. The only exception 117 * is the variable-length package (ACPI_PTYPE1_VAR). 118 */ 119 if (!count) { 120 if (package->ret_info.type == ACPI_PTYPE1_VAR) { 121 return (AE_OK); 122 } 123 124 ACPI_WARN_PREDEFINED((AE_INFO, info->full_pathname, 125 info->node_flags, 126 "Return Package has no elements (empty)")); 127 128 return (AE_AML_OPERAND_VALUE); 129 } 130 131 /* 132 * Decode the type of the expected package contents 133 * 134 * PTYPE1 packages contain no subpackages 135 * PTYPE2 packages contain subpackages 136 */ 137 switch (package->ret_info.type) { 138 case ACPI_PTYPE1_FIXED: 139 /* 140 * The package count is fixed and there are no subpackages 141 * 142 * If package is too small, exit. 143 * If package is larger than expected, issue warning but continue 144 */ 145 expected_count = 146 package->ret_info.count1 + package->ret_info.count2; 147 if (count < expected_count) { 148 goto package_too_small; 149 } else if (count > expected_count) { 150 ACPI_DEBUG_PRINT((ACPI_DB_REPAIR, 151 "%s: Return Package is larger than needed - " 152 "found %u, expected %u\n", 153 info->full_pathname, count, 154 expected_count)); 155 } 156 157 /* Validate all elements of the returned package */ 158 159 status = acpi_ns_check_package_elements(info, elements, 160 package->ret_info. 161 object_type1, 162 package->ret_info. 163 count1, 164 package->ret_info. 165 object_type2, 166 package->ret_info. 167 count2, 0); 168 break; 169 170 case ACPI_PTYPE1_VAR: 171 /* 172 * The package count is variable, there are no subpackages, and all 173 * elements must be of the same type 174 */ 175 for (i = 0; i < count; i++) { 176 status = acpi_ns_check_object_type(info, elements, 177 package->ret_info. 178 object_type1, i); 179 if (ACPI_FAILURE(status)) { 180 return (status); 181 } 182 elements++; 183 } 184 break; 185 186 case ACPI_PTYPE1_OPTION: 187 /* 188 * The package count is variable, there are no subpackages. There are 189 * a fixed number of required elements, and a variable number of 190 * optional elements. 191 * 192 * Check if package is at least as large as the minimum required 193 */ 194 expected_count = package->ret_info3.count; 195 if (count < expected_count) { 196 goto package_too_small; 197 } 198 199 /* Variable number of sub-objects */ 200 201 for (i = 0; i < count; i++) { 202 if (i < package->ret_info3.count) { 203 204 /* These are the required package elements (0, 1, or 2) */ 205 206 status = 207 acpi_ns_check_object_type(info, elements, 208 package-> 209 ret_info3. 210 object_type[i], 211 i); 212 if (ACPI_FAILURE(status)) { 213 return (status); 214 } 215 } else { 216 /* These are the optional package elements */ 217 218 status = 219 acpi_ns_check_object_type(info, elements, 220 package-> 221 ret_info3. 222 tail_object_type, 223 i); 224 if (ACPI_FAILURE(status)) { 225 return (status); 226 } 227 } 228 elements++; 229 } 230 break; 231 232 case ACPI_PTYPE2_REV_FIXED: 233 234 /* First element is the (Integer) revision */ 235 236 status = acpi_ns_check_object_type(info, elements, 237 ACPI_RTYPE_INTEGER, 0); 238 if (ACPI_FAILURE(status)) { 239 return (status); 240 } 241 242 elements++; 243 count--; 244 245 /* Examine the subpackages */ 246 247 status = 248 acpi_ns_check_package_list(info, package, elements, count); 249 break; 250 251 case ACPI_PTYPE2_PKG_COUNT: 252 253 /* First element is the (Integer) count of subpackages to follow */ 254 255 status = acpi_ns_check_object_type(info, elements, 256 ACPI_RTYPE_INTEGER, 0); 257 if (ACPI_FAILURE(status)) { 258 return (status); 259 } 260 261 /* 262 * Count cannot be larger than the parent package length, but allow it 263 * to be smaller. The >= accounts for the Integer above. 264 */ 265 expected_count = (u32)(*elements)->integer.value; 266 if (expected_count >= count) { 267 goto package_too_small; 268 } 269 270 count = expected_count; 271 elements++; 272 273 /* Examine the subpackages */ 274 275 status = 276 acpi_ns_check_package_list(info, package, elements, count); 277 break; 278 279 case ACPI_PTYPE2: 280 case ACPI_PTYPE2_FIXED: 281 case ACPI_PTYPE2_MIN: 282 case ACPI_PTYPE2_COUNT: 283 case ACPI_PTYPE2_FIX_VAR: 284 /* 285 * These types all return a single Package that consists of a 286 * variable number of subpackages. 287 * 288 * First, ensure that the first element is a subpackage. If not, 289 * the BIOS may have incorrectly returned the object as a single 290 * package instead of a Package of Packages (a common error if 291 * there is only one entry). We may be able to repair this by 292 * wrapping the returned Package with a new outer Package. 293 */ 294 if (*elements 295 && ((*elements)->common.type != ACPI_TYPE_PACKAGE)) { 296 297 /* Create the new outer package and populate it */ 298 299 status = 300 acpi_ns_wrap_with_package(info, return_object, 301 return_object_ptr); 302 if (ACPI_FAILURE(status)) { 303 return (status); 304 } 305 306 /* Update locals to point to the new package (of 1 element) */ 307 308 return_object = *return_object_ptr; 309 elements = return_object->package.elements; 310 count = 1; 311 } 312 313 /* Examine the subpackages */ 314 315 status = 316 acpi_ns_check_package_list(info, package, elements, count); 317 break; 318 319 case ACPI_PTYPE2_VAR_VAR: 320 /* 321 * Returns a variable list of packages, each with a variable list 322 * of objects. 323 */ 324 break; 325 326 case ACPI_PTYPE2_UUID_PAIR: 327 328 /* The package must contain pairs of (UUID + type) */ 329 330 if (count & 1) { 331 expected_count = count + 1; 332 goto package_too_small; 333 } 334 335 while (count > 0) { 336 status = acpi_ns_check_object_type(info, elements, 337 package->ret_info. 338 object_type1, 0); 339 if (ACPI_FAILURE(status)) { 340 return (status); 341 } 342 343 /* Validate length of the UUID buffer */ 344 345 if ((*elements)->buffer.length != 16) { 346 ACPI_WARN_PREDEFINED((AE_INFO, 347 info->full_pathname, 348 info->node_flags, 349 "Invalid length for UUID Buffer")); 350 return (AE_AML_OPERAND_VALUE); 351 } 352 353 status = acpi_ns_check_object_type(info, elements + 1, 354 package->ret_info. 355 object_type2, 0); 356 if (ACPI_FAILURE(status)) { 357 return (status); 358 } 359 360 elements += 2; 361 count -= 2; 362 } 363 break; 364 365 default: 366 367 /* Should not get here if predefined info table is correct */ 368 369 ACPI_WARN_PREDEFINED((AE_INFO, info->full_pathname, 370 info->node_flags, 371 "Invalid internal return type in table entry: %X", 372 package->ret_info.type)); 373 374 return (AE_AML_INTERNAL); 375 } 376 377 return (status); 378 379 package_too_small: 380 381 /* Error exit for the case with an incorrect package count */ 382 383 ACPI_WARN_PREDEFINED((AE_INFO, info->full_pathname, info->node_flags, 384 "Return Package is too small - found %u elements, expected %u", 385 count, expected_count)); 386 387 return (AE_AML_OPERAND_VALUE); 388 } 389 390 /******************************************************************************* 391 * 392 * FUNCTION: acpi_ns_check_package_list 393 * 394 * PARAMETERS: info - Method execution information block 395 * package - Pointer to package-specific info for method 396 * elements - Element list of parent package. All elements 397 * of this list should be of type Package. 398 * count - Count of subpackages 399 * 400 * RETURN: Status 401 * 402 * DESCRIPTION: Examine a list of subpackages 403 * 404 ******************************************************************************/ 405 406 static acpi_status 407 acpi_ns_check_package_list(struct acpi_evaluate_info *info, 408 const union acpi_predefined_info *package, 409 union acpi_operand_object **elements, u32 count) 410 { 411 union acpi_operand_object *sub_package; 412 union acpi_operand_object **sub_elements; 413 acpi_status status; 414 u32 expected_count; 415 u32 i; 416 u32 j; 417 418 /* 419 * Validate each subpackage in the parent Package 420 * 421 * NOTE: assumes list of subpackages contains no NULL elements. 422 * Any NULL elements should have been removed by earlier call 423 * to acpi_ns_remove_null_elements. 424 */ 425 for (i = 0; i < count; i++) { 426 sub_package = *elements; 427 sub_elements = sub_package->package.elements; 428 info->parent_package = sub_package; 429 430 /* Each sub-object must be of type Package */ 431 432 status = acpi_ns_check_object_type(info, &sub_package, 433 ACPI_RTYPE_PACKAGE, i); 434 if (ACPI_FAILURE(status)) { 435 return (status); 436 } 437 438 /* Examine the different types of expected subpackages */ 439 440 info->parent_package = sub_package; 441 switch (package->ret_info.type) { 442 case ACPI_PTYPE2: 443 case ACPI_PTYPE2_PKG_COUNT: 444 case ACPI_PTYPE2_REV_FIXED: 445 446 /* Each subpackage has a fixed number of elements */ 447 448 expected_count = 449 package->ret_info.count1 + package->ret_info.count2; 450 if (sub_package->package.count < expected_count) { 451 goto package_too_small; 452 } 453 454 status = 455 acpi_ns_check_package_elements(info, sub_elements, 456 package->ret_info. 457 object_type1, 458 package->ret_info. 459 count1, 460 package->ret_info. 461 object_type2, 462 package->ret_info. 463 count2, 0); 464 if (ACPI_FAILURE(status)) { 465 return (status); 466 } 467 break; 468 469 case ACPI_PTYPE2_FIX_VAR: 470 /* 471 * Each subpackage has a fixed number of elements and an 472 * optional element 473 */ 474 expected_count = 475 package->ret_info.count1 + package->ret_info.count2; 476 if (sub_package->package.count < expected_count) { 477 goto package_too_small; 478 } 479 480 status = 481 acpi_ns_check_package_elements(info, sub_elements, 482 package->ret_info. 483 object_type1, 484 package->ret_info. 485 count1, 486 package->ret_info. 487 object_type2, 488 sub_package->package. 489 count - 490 package->ret_info. 491 count1, 0); 492 if (ACPI_FAILURE(status)) { 493 return (status); 494 } 495 break; 496 497 case ACPI_PTYPE2_VAR_VAR: 498 /* 499 * Each subpackage has a fixed or variable number of elements 500 */ 501 break; 502 503 case ACPI_PTYPE2_FIXED: 504 505 /* Each subpackage has a fixed length */ 506 507 expected_count = package->ret_info2.count; 508 if (sub_package->package.count < expected_count) { 509 goto package_too_small; 510 } 511 512 /* Check the type of each subpackage element */ 513 514 for (j = 0; j < expected_count; j++) { 515 status = 516 acpi_ns_check_object_type(info, 517 &sub_elements[j], 518 package-> 519 ret_info2. 520 object_type[j], 521 j); 522 if (ACPI_FAILURE(status)) { 523 return (status); 524 } 525 } 526 break; 527 528 case ACPI_PTYPE2_MIN: 529 530 /* Each subpackage has a variable but minimum length */ 531 532 expected_count = package->ret_info.count1; 533 if (sub_package->package.count < expected_count) { 534 goto package_too_small; 535 } 536 537 /* Check the type of each subpackage element */ 538 539 status = 540 acpi_ns_check_package_elements(info, sub_elements, 541 package->ret_info. 542 object_type1, 543 sub_package->package. 544 count, 0, 0, 0); 545 if (ACPI_FAILURE(status)) { 546 return (status); 547 } 548 break; 549 550 case ACPI_PTYPE2_COUNT: 551 /* 552 * First element is the (Integer) count of elements, including 553 * the count field (the ACPI name is num_elements) 554 */ 555 status = acpi_ns_check_object_type(info, sub_elements, 556 ACPI_RTYPE_INTEGER, 557 0); 558 if (ACPI_FAILURE(status)) { 559 return (status); 560 } 561 562 /* 563 * Make sure package is large enough for the Count and is 564 * is as large as the minimum size 565 */ 566 expected_count = (u32)(*sub_elements)->integer.value; 567 if (sub_package->package.count < expected_count) { 568 goto package_too_small; 569 } 570 if (sub_package->package.count < 571 package->ret_info.count1) { 572 expected_count = package->ret_info.count1; 573 goto package_too_small; 574 } 575 if (expected_count == 0) { 576 /* 577 * Either the num_entries element was originally zero or it was 578 * a NULL element and repaired to an Integer of value zero. 579 * In either case, repair it by setting num_entries to be the 580 * actual size of the subpackage. 581 */ 582 expected_count = sub_package->package.count; 583 (*sub_elements)->integer.value = expected_count; 584 } 585 586 /* Check the type of each subpackage element */ 587 588 status = 589 acpi_ns_check_package_elements(info, 590 (sub_elements + 1), 591 package->ret_info. 592 object_type1, 593 (expected_count - 1), 594 0, 0, 1); 595 if (ACPI_FAILURE(status)) { 596 return (status); 597 } 598 break; 599 600 default: /* Should not get here, type was validated by caller */ 601 602 return (AE_AML_INTERNAL); 603 } 604 605 elements++; 606 } 607 608 return (AE_OK); 609 610 package_too_small: 611 612 /* The subpackage count was smaller than required */ 613 614 ACPI_WARN_PREDEFINED((AE_INFO, info->full_pathname, info->node_flags, 615 "Return SubPackage[%u] is too small - found %u elements, expected %u", 616 i, sub_package->package.count, expected_count)); 617 618 return (AE_AML_OPERAND_VALUE); 619 } 620 621 /******************************************************************************* 622 * 623 * FUNCTION: acpi_ns_check_package_elements 624 * 625 * PARAMETERS: info - Method execution information block 626 * elements - Pointer to the package elements array 627 * type1 - Object type for first group 628 * count1 - Count for first group 629 * type2 - Object type for second group 630 * count2 - Count for second group 631 * start_index - Start of the first group of elements 632 * 633 * RETURN: Status 634 * 635 * DESCRIPTION: Check that all elements of a package are of the correct object 636 * type. Supports up to two groups of different object types. 637 * 638 ******************************************************************************/ 639 640 static acpi_status 641 acpi_ns_check_package_elements(struct acpi_evaluate_info *info, 642 union acpi_operand_object **elements, 643 u8 type1, 644 u32 count1, 645 u8 type2, u32 count2, u32 start_index) 646 { 647 union acpi_operand_object **this_element = elements; 648 acpi_status status; 649 u32 i; 650 651 /* 652 * Up to two groups of package elements are supported by the data 653 * structure. All elements in each group must be of the same type. 654 * The second group can have a count of zero. 655 */ 656 for (i = 0; i < count1; i++) { 657 status = acpi_ns_check_object_type(info, this_element, 658 type1, i + start_index); 659 if (ACPI_FAILURE(status)) { 660 return (status); 661 } 662 this_element++; 663 } 664 665 for (i = 0; i < count2; i++) { 666 status = acpi_ns_check_object_type(info, this_element, 667 type2, 668 (i + count1 + start_index)); 669 if (ACPI_FAILURE(status)) { 670 return (status); 671 } 672 this_element++; 673 } 674 675 return (AE_OK); 676 } 677