diff options
| -rw-r--r-- | drivers/acpi/acpica/aclocal.h | 1 | ||||
| -rw-r--r-- | drivers/acpi/acpica/acnamesp.h | 16 | ||||
| -rw-r--r-- | drivers/acpi/acpica/nspredef.c | 27 | ||||
| -rw-r--r-- | drivers/acpi/acpica/nsrepair.c | 173 | ||||
| -rw-r--r-- | drivers/acpi/acpica/nsrepair2.c | 84 |
5 files changed, 209 insertions, 92 deletions
diff --git a/drivers/acpi/acpica/aclocal.h b/drivers/acpi/acpica/aclocal.h index 2caf141076fc..681205c75563 100644 --- a/drivers/acpi/acpica/aclocal.h +++ b/drivers/acpi/acpica/aclocal.h | |||
| @@ -374,6 +374,7 @@ union acpi_predefined_info { | |||
| 374 | struct acpi_predefined_data { | 374 | struct acpi_predefined_data { |
| 375 | char *pathname; | 375 | char *pathname; |
| 376 | const union acpi_predefined_info *predefined; | 376 | const union acpi_predefined_info *predefined; |
| 377 | union acpi_operand_object *parent_package; | ||
| 377 | u32 flags; | 378 | u32 flags; |
| 378 | u8 node_flags; | 379 | u8 node_flags; |
| 379 | }; | 380 | }; |
diff --git a/drivers/acpi/acpica/acnamesp.h b/drivers/acpi/acpica/acnamesp.h index 73f9b0c88dd8..258159cfcdfa 100644 --- a/drivers/acpi/acpica/acnamesp.h +++ b/drivers/acpi/acpica/acnamesp.h | |||
| @@ -286,6 +286,17 @@ acpi_status | |||
| 286 | acpi_ns_repair_package_list(struct acpi_predefined_data *data, | 286 | acpi_ns_repair_package_list(struct acpi_predefined_data *data, |
| 287 | union acpi_operand_object **obj_desc_ptr); | 287 | union acpi_operand_object **obj_desc_ptr); |
| 288 | 288 | ||
| 289 | acpi_status | ||
| 290 | acpi_ns_repair_null_element(struct acpi_predefined_data *data, | ||
| 291 | u32 expected_btypes, | ||
| 292 | u32 package_index, | ||
| 293 | union acpi_operand_object **return_object_ptr); | ||
| 294 | |||
| 295 | void | ||
| 296 | acpi_ns_remove_null_elements(struct acpi_predefined_data *data, | ||
| 297 | u8 package_type, | ||
| 298 | union acpi_operand_object *obj_desc); | ||
| 299 | |||
| 289 | /* | 300 | /* |
| 290 | * nsrepair2 - Return object repair for specific | 301 | * nsrepair2 - Return object repair for specific |
| 291 | * predefined methods/objects | 302 | * predefined methods/objects |
| @@ -296,11 +307,6 @@ acpi_ns_complex_repairs(struct acpi_predefined_data *data, | |||
| 296 | acpi_status validate_status, | 307 | acpi_status validate_status, |
| 297 | union acpi_operand_object **return_object_ptr); | 308 | union acpi_operand_object **return_object_ptr); |
| 298 | 309 | ||
| 299 | void | ||
| 300 | acpi_ns_remove_null_elements(struct acpi_predefined_data *data, | ||
| 301 | u8 package_type, | ||
| 302 | union acpi_operand_object *obj_desc); | ||
| 303 | |||
| 304 | /* | 310 | /* |
| 305 | * nssearch - Namespace searching and entry | 311 | * nssearch - Namespace searching and entry |
| 306 | */ | 312 | */ |
diff --git a/drivers/acpi/acpica/nspredef.c b/drivers/acpi/acpica/nspredef.c index ba1072fb0daa..7096bcda0c72 100644 --- a/drivers/acpi/acpica/nspredef.c +++ b/drivers/acpi/acpica/nspredef.c | |||
| @@ -231,6 +231,7 @@ acpi_ns_check_predefined_names(struct acpi_namespace_node *node, | |||
| 231 | * Note: Package may have been newly created by call above. | 231 | * Note: Package may have been newly created by call above. |
| 232 | */ | 232 | */ |
| 233 | if ((*return_object_ptr)->common.type == ACPI_TYPE_PACKAGE) { | 233 | if ((*return_object_ptr)->common.type == ACPI_TYPE_PACKAGE) { |
| 234 | data->parent_package = *return_object_ptr; | ||
| 234 | status = acpi_ns_check_package(data, return_object_ptr); | 235 | status = acpi_ns_check_package(data, return_object_ptr); |
| 235 | if (ACPI_FAILURE(status)) { | 236 | if (ACPI_FAILURE(status)) { |
| 236 | goto exit; | 237 | goto exit; |
| @@ -710,6 +711,7 @@ acpi_ns_check_package_list(struct acpi_predefined_data *data, | |||
| 710 | for (i = 0; i < count; i++) { | 711 | for (i = 0; i < count; i++) { |
| 711 | sub_package = *elements; | 712 | sub_package = *elements; |
| 712 | sub_elements = sub_package->package.elements; | 713 | sub_elements = sub_package->package.elements; |
| 714 | data->parent_package = sub_package; | ||
| 713 | 715 | ||
| 714 | /* Each sub-object must be of type Package */ | 716 | /* Each sub-object must be of type Package */ |
| 715 | 717 | ||
| @@ -721,6 +723,7 @@ acpi_ns_check_package_list(struct acpi_predefined_data *data, | |||
| 721 | 723 | ||
| 722 | /* Examine the different types of expected sub-packages */ | 724 | /* Examine the different types of expected sub-packages */ |
| 723 | 725 | ||
| 726 | data->parent_package = sub_package; | ||
| 724 | switch (package->ret_info.type) { | 727 | switch (package->ret_info.type) { |
| 725 | case ACPI_PTYPE2: | 728 | case ACPI_PTYPE2: |
| 726 | case ACPI_PTYPE2_PKG_COUNT: | 729 | case ACPI_PTYPE2_PKG_COUNT: |
| @@ -800,7 +803,7 @@ acpi_ns_check_package_list(struct acpi_predefined_data *data, | |||
| 800 | 803 | ||
| 801 | /* | 804 | /* |
| 802 | * First element is the (Integer) count of elements, including | 805 | * First element is the (Integer) count of elements, including |
| 803 | * the count field. | 806 | * the count field (the ACPI name is num_elements) |
| 804 | */ | 807 | */ |
| 805 | status = acpi_ns_check_object_type(data, sub_elements, | 808 | status = acpi_ns_check_object_type(data, sub_elements, |
| 806 | ACPI_RTYPE_INTEGER, | 809 | ACPI_RTYPE_INTEGER, |
| @@ -822,6 +825,16 @@ acpi_ns_check_package_list(struct acpi_predefined_data *data, | |||
| 822 | expected_count = package->ret_info.count1; | 825 | expected_count = package->ret_info.count1; |
| 823 | goto package_too_small; | 826 | goto package_too_small; |
| 824 | } | 827 | } |
| 828 | if (expected_count == 0) { | ||
| 829 | /* | ||
| 830 | * Either the num_entries element was originally zero or it was | ||
| 831 | * a NULL element and repaired to an Integer of value zero. | ||
| 832 | * In either case, repair it by setting num_entries to be the | ||
| 833 | * actual size of the subpackage. | ||
| 834 | */ | ||
| 835 | expected_count = sub_package->package.count; | ||
| 836 | (*sub_elements)->integer.value = expected_count; | ||
| 837 | } | ||
| 825 | 838 | ||
| 826 | /* Check the type of each sub-package element */ | 839 | /* Check the type of each sub-package element */ |
| 827 | 840 | ||
| @@ -945,10 +958,18 @@ acpi_ns_check_object_type(struct acpi_predefined_data *data, | |||
| 945 | char type_buffer[48]; /* Room for 5 types */ | 958 | char type_buffer[48]; /* Room for 5 types */ |
| 946 | 959 | ||
| 947 | /* | 960 | /* |
| 948 | * If we get a NULL return_object here, it is a NULL package element, | 961 | * If we get a NULL return_object here, it is a NULL package element. |
| 949 | * and this is always an error. | 962 | * Since all extraneous NULL package elements were removed earlier by a |
| 963 | * call to acpi_ns_remove_null_elements, this is an unexpected NULL element. | ||
| 964 | * We will attempt to repair it. | ||
| 950 | */ | 965 | */ |
| 951 | if (!return_object) { | 966 | if (!return_object) { |
| 967 | status = acpi_ns_repair_null_element(data, expected_btypes, | ||
| 968 | package_index, | ||
| 969 | return_object_ptr); | ||
| 970 | if (ACPI_SUCCESS(status)) { | ||
| 971 | return (AE_OK); /* Repair was successful */ | ||
| 972 | } | ||
| 952 | goto type_error_exit; | 973 | goto type_error_exit; |
| 953 | } | 974 | } |
| 954 | 975 | ||
diff --git a/drivers/acpi/acpica/nsrepair.c b/drivers/acpi/acpica/nsrepair.c index c82060fd3821..d4be37751be4 100644 --- a/drivers/acpi/acpica/nsrepair.c +++ b/drivers/acpi/acpica/nsrepair.c | |||
| @@ -45,6 +45,7 @@ | |||
| 45 | #include "accommon.h" | 45 | #include "accommon.h" |
| 46 | #include "acnamesp.h" | 46 | #include "acnamesp.h" |
| 47 | #include "acinterp.h" | 47 | #include "acinterp.h" |
| 48 | #include "acpredef.h" | ||
| 48 | 49 | ||
| 49 | #define _COMPONENT ACPI_NAMESPACE | 50 | #define _COMPONENT ACPI_NAMESPACE |
| 50 | ACPI_MODULE_NAME("nsrepair") | 51 | ACPI_MODULE_NAME("nsrepair") |
| @@ -71,6 +72,12 @@ ACPI_MODULE_NAME("nsrepair") | |||
| 71 | * Buffer -> Package of Integers | 72 | * Buffer -> Package of Integers |
| 72 | * Package -> Package of one Package | 73 | * Package -> Package of one Package |
| 73 | * | 74 | * |
| 75 | * Additional possible repairs: | ||
| 76 | * | ||
| 77 | * Optional/unnecessary NULL package elements removed | ||
| 78 | * Required package elements that are NULL replaced by Integer/String/Buffer | ||
| 79 | * Incorrect standalone package wrapped with required outer package | ||
| 80 | * | ||
| 74 | ******************************************************************************/ | 81 | ******************************************************************************/ |
| 75 | /* Local prototypes */ | 82 | /* Local prototypes */ |
| 76 | static acpi_status | 83 | static acpi_status |
| @@ -506,6 +513,172 @@ acpi_ns_convert_to_package(union acpi_operand_object *original_object, | |||
| 506 | 513 | ||
| 507 | /******************************************************************************* | 514 | /******************************************************************************* |
| 508 | * | 515 | * |
| 516 | * FUNCTION: acpi_ns_repair_null_element | ||
| 517 | * | ||
| 518 | * PARAMETERS: Data - Pointer to validation data structure | ||
| 519 | * expected_btypes - Object types expected | ||
| 520 | * package_index - Index of object within parent package (if | ||
| 521 | * applicable - ACPI_NOT_PACKAGE_ELEMENT | ||
| 522 | * otherwise) | ||
| 523 | * return_object_ptr - Pointer to the object returned from the | ||
| 524 | * evaluation of a method or object | ||
| 525 | * | ||
| 526 | * RETURN: Status. AE_OK if repair was successful. | ||
| 527 | * | ||
| 528 | * DESCRIPTION: Attempt to repair a NULL element of a returned Package object. | ||
| 529 | * | ||
| 530 | ******************************************************************************/ | ||
