Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
0002 /*******************************************************************************
0003  *
0004  * Module Name: rsutils - Utilities for the resource manager
0005  *
0006  ******************************************************************************/
0007 
0008 #include <acpi/acpi.h>
0009 #include "accommon.h"
0010 #include "acnamesp.h"
0011 #include "acresrc.h"
0012 
0013 #define _COMPONENT          ACPI_RESOURCES
0014 ACPI_MODULE_NAME("rsutils")
0015 
0016 /*******************************************************************************
0017  *
0018  * FUNCTION:    acpi_rs_decode_bitmask
0019  *
0020  * PARAMETERS:  mask            - Bitmask to decode
0021  *              list            - Where the converted list is returned
0022  *
0023  * RETURN:      Count of bits set (length of list)
0024  *
0025  * DESCRIPTION: Convert a bit mask into a list of values
0026  *
0027  ******************************************************************************/
0028 u8 acpi_rs_decode_bitmask(u16 mask, u8 * list)
0029 {
0030     u8 i;
0031     u8 bit_count;
0032 
0033     ACPI_FUNCTION_ENTRY();
0034 
0035     /* Decode the mask bits */
0036 
0037     for (i = 0, bit_count = 0; mask; i++) {
0038         if (mask & 0x0001) {
0039             list[bit_count] = i;
0040             bit_count++;
0041         }
0042 
0043         mask >>= 1;
0044     }
0045 
0046     return (bit_count);
0047 }
0048 
0049 /*******************************************************************************
0050  *
0051  * FUNCTION:    acpi_rs_encode_bitmask
0052  *
0053  * PARAMETERS:  list            - List of values to encode
0054  *              count           - Length of list
0055  *
0056  * RETURN:      Encoded bitmask
0057  *
0058  * DESCRIPTION: Convert a list of values to an encoded bitmask
0059  *
0060  ******************************************************************************/
0061 
0062 u16 acpi_rs_encode_bitmask(u8 * list, u8 count)
0063 {
0064     u32 i;
0065     u16 mask;
0066 
0067     ACPI_FUNCTION_ENTRY();
0068 
0069     /* Encode the list into a single bitmask */
0070 
0071     for (i = 0, mask = 0; i < count; i++) {
0072         mask |= (0x1 << list[i]);
0073     }
0074 
0075     return (mask);
0076 }
0077 
0078 /*******************************************************************************
0079  *
0080  * FUNCTION:    acpi_rs_move_data
0081  *
0082  * PARAMETERS:  destination         - Pointer to the destination descriptor
0083  *              source              - Pointer to the source descriptor
0084  *              item_count          - How many items to move
0085  *              move_type           - Byte width
0086  *
0087  * RETURN:      None
0088  *
0089  * DESCRIPTION: Move multiple data items from one descriptor to another. Handles
0090  *              alignment issues and endian issues if necessary, as configured
0091  *              via the ACPI_MOVE_* macros. (This is why a memcpy is not used)
0092  *
0093  ******************************************************************************/
0094 
0095 void
0096 acpi_rs_move_data(void *destination, void *source, u16 item_count, u8 move_type)
0097 {
0098     u32 i;
0099 
0100     ACPI_FUNCTION_ENTRY();
0101 
0102     /* One move per item */
0103 
0104     for (i = 0; i < item_count; i++) {
0105         switch (move_type) {
0106             /*
0107              * For the 8-bit case, we can perform the move all at once
0108              * since there are no alignment or endian issues
0109              */
0110         case ACPI_RSC_MOVE8:
0111         case ACPI_RSC_MOVE_GPIO_RES:
0112         case ACPI_RSC_MOVE_SERIAL_VEN:
0113         case ACPI_RSC_MOVE_SERIAL_RES:
0114 
0115             memcpy(destination, source, item_count);
0116             return;
0117 
0118             /*
0119              * 16-, 32-, and 64-bit cases must use the move macros that perform
0120              * endian conversion and/or accommodate hardware that cannot perform
0121              * misaligned memory transfers
0122              */
0123         case ACPI_RSC_MOVE16:
0124         case ACPI_RSC_MOVE_GPIO_PIN:
0125 
0126             ACPI_MOVE_16_TO_16(&ACPI_CAST_PTR(u16, destination)[i],
0127                        &ACPI_CAST_PTR(u16, source)[i]);
0128             break;
0129 
0130         case ACPI_RSC_MOVE32:
0131 
0132             ACPI_MOVE_32_TO_32(&ACPI_CAST_PTR(u32, destination)[i],
0133                        &ACPI_CAST_PTR(u32, source)[i]);
0134             break;
0135 
0136         case ACPI_RSC_MOVE64:
0137 
0138             ACPI_MOVE_64_TO_64(&ACPI_CAST_PTR(u64, destination)[i],
0139                        &ACPI_CAST_PTR(u64, source)[i]);
0140             break;
0141 
0142         default:
0143 
0144             return;
0145         }
0146     }
0147 }
0148 
0149 /*******************************************************************************
0150  *
0151  * FUNCTION:    acpi_rs_set_resource_length
0152  *
0153  * PARAMETERS:  total_length        - Length of the AML descriptor, including
0154  *                                    the header and length fields.
0155  *              aml                 - Pointer to the raw AML descriptor
0156  *
0157  * RETURN:      None
0158  *
0159  * DESCRIPTION: Set the resource_length field of an AML
0160  *              resource descriptor, both Large and Small descriptors are
0161  *              supported automatically. Note: Descriptor Type field must
0162  *              be valid.
0163  *
0164  ******************************************************************************/
0165 
0166 void
0167 acpi_rs_set_resource_length(acpi_rsdesc_size total_length,
0168                 union aml_resource *aml)
0169 {
0170     acpi_rs_length resource_length;
0171 
0172     ACPI_FUNCTION_ENTRY();
0173 
0174     /* Length is the total descriptor length minus the header length */
0175 
0176     resource_length = (acpi_rs_length)
0177         (total_length - acpi_ut_get_resource_header_length(aml));
0178 
0179     /* Length is stored differently for large and small descriptors */
0180 
0181     if (aml->small_header.descriptor_type & ACPI_RESOURCE_NAME_LARGE) {
0182 
0183         /* Large descriptor -- bytes 1-2 contain the 16-bit length */
0184 
0185         ACPI_MOVE_16_TO_16(&aml->large_header.resource_length,
0186                    &resource_length);
0187     } else {
0188         /*
0189          * Small descriptor -- bits 2:0 of byte 0 contain the length
0190          * Clear any existing length, preserving descriptor type bits
0191          */
0192         aml->small_header.descriptor_type = (u8)
0193             ((aml->small_header.descriptor_type &
0194               ~ACPI_RESOURCE_NAME_SMALL_LENGTH_MASK)
0195              | resource_length);
0196     }
0197 }
0198 
0199 /*******************************************************************************
0200  *
0201  * FUNCTION:    acpi_rs_set_resource_header
0202  *
0203  * PARAMETERS:  descriptor_type     - Byte to be inserted as the type
0204  *              total_length        - Length of the AML descriptor, including
0205  *                                    the header and length fields.
0206  *              aml                 - Pointer to the raw AML descriptor
0207  *
0208  * RETURN:      None
0209  *
0210  * DESCRIPTION: Set the descriptor_type and resource_length fields of an AML
0211  *              resource descriptor, both Large and Small descriptors are
0212  *              supported automatically
0213  *
0214  ******************************************************************************/
0215 
0216 void
0217 acpi_rs_set_resource_header(u8 descriptor_type,
0218                 acpi_rsdesc_size total_length,
0219                 union aml_resource *aml)
0220 {
0221     ACPI_FUNCTION_ENTRY();
0222 
0223     /* Set the Resource Type */
0224 
0225     aml->small_header.descriptor_type = descriptor_type;
0226 
0227     /* Set the Resource Length */
0228 
0229     acpi_rs_set_resource_length(total_length, aml);
0230 }
0231 
0232 /*******************************************************************************
0233  *
0234  * FUNCTION:    acpi_rs_strcpy
0235  *
0236  * PARAMETERS:  destination         - Pointer to the destination string
0237  *              source              - Pointer to the source string
0238  *
0239  * RETURN:      String length, including NULL terminator
0240  *
0241  * DESCRIPTION: Local string copy that returns the string length, saving a
0242  *              strcpy followed by a strlen.
0243  *
0244  ******************************************************************************/
0245 
0246 static u16 acpi_rs_strcpy(char *destination, char *source)
0247 {
0248     u16 i;
0249 
0250     ACPI_FUNCTION_ENTRY();
0251 
0252     for (i = 0; source[i]; i++) {
0253         destination[i] = source[i];
0254     }
0255 
0256     destination[i] = 0;
0257 
0258     /* Return string length including the NULL terminator */
0259 
0260     return ((u16) (i + 1));
0261 }
0262 
0263 /*******************************************************************************
0264  *
0265  * FUNCTION:    acpi_rs_get_resource_source
0266  *
0267  * PARAMETERS:  resource_length     - Length field of the descriptor
0268  *              minimum_length      - Minimum length of the descriptor (minus
0269  *                                    any optional fields)
0270  *              resource_source     - Where the resource_source is returned
0271  *              aml                 - Pointer to the raw AML descriptor
0272  *              string_ptr          - (optional) where to store the actual
0273  *                                    resource_source string
0274  *
0275  * RETURN:      Length of the string plus NULL terminator, rounded up to native
0276  *              word boundary
0277  *
0278  * DESCRIPTION: Copy the optional resource_source data from a raw AML descriptor
0279  *              to an internal resource descriptor
0280  *
0281  ******************************************************************************/
0282 
0283 acpi_rs_length
0284 acpi_rs_get_resource_source(acpi_rs_length resource_length,
0285                 acpi_rs_length minimum_length,
0286                 struct acpi_resource_source * resource_source,
0287                 union aml_resource * aml, char *string_ptr)
0288 {
0289     acpi_rsdesc_size total_length;
0290     u8 *aml_resource_source;
0291 
0292     ACPI_FUNCTION_ENTRY();
0293 
0294     total_length =
0295         resource_length + sizeof(struct aml_resource_large_header);
0296     aml_resource_source = ACPI_ADD_PTR(u8, aml, minimum_length);
0297 
0298     /*
0299      * resource_source is present if the length of the descriptor is longer
0300      * than the minimum length.
0301      *
0302      * Note: Some resource descriptors will have an additional null, so
0303      * we add 1 to the minimum length.
0304      */
0305     if (total_length > (acpi_rsdesc_size)(minimum_length + 1)) {
0306 
0307         /* Get the resource_source_index */
0308 
0309         resource_source->index = aml_resource_source[0];
0310 
0311         resource_source->string_ptr = string_ptr;
0312         if (!string_ptr) {
0313             /*
0314              * String destination pointer is not specified; Set the String
0315              * pointer to the end of the current resource_source structure.
0316              */
0317             resource_source->string_ptr =
0318                 ACPI_ADD_PTR(char, resource_source,
0319                      sizeof(struct acpi_resource_source));
0320         }
0321 
0322         /*
0323          * In order for the Resource length to be a multiple of the native
0324          * word, calculate the length of the string (+1 for NULL terminator)
0325          * and expand to the next word multiple.
0326          *
0327          * Zero the entire area of the buffer.
0328          */
0329         total_length =
0330             (u32)strlen(ACPI_CAST_PTR(char, &aml_resource_source[1])) +
0331             1;
0332 
0333         total_length = (u32)ACPI_ROUND_UP_TO_NATIVE_WORD(total_length);
0334 
0335         memset(resource_source->string_ptr, 0, total_length);
0336 
0337         /* Copy the resource_source string to the destination */
0338 
0339         resource_source->string_length =
0340             acpi_rs_strcpy(resource_source->string_ptr,
0341                    ACPI_CAST_PTR(char,
0342                          &aml_resource_source[1]));
0343 
0344         return ((acpi_rs_length)total_length);
0345     }
0346 
0347     /* resource_source is not present */
0348 
0349     resource_source->index = 0;
0350     resource_source->string_length = 0;
0351     resource_source->string_ptr = NULL;
0352     return (0);
0353 }
0354 
0355 /*******************************************************************************
0356  *
0357  * FUNCTION:    acpi_rs_set_resource_source
0358  *
0359  * PARAMETERS:  aml                 - Pointer to the raw AML descriptor
0360  *              minimum_length      - Minimum length of the descriptor (minus
0361  *                                    any optional fields)
0362  *              resource_source     - Internal resource_source
0363 
0364  *
0365  * RETURN:      Total length of the AML descriptor
0366  *
0367  * DESCRIPTION: Convert an optional resource_source from internal format to a
0368  *              raw AML resource descriptor
0369  *
0370  ******************************************************************************/
0371 
0372 acpi_rsdesc_size
0373 acpi_rs_set_resource_source(union aml_resource *aml,
0374                 acpi_rs_length minimum_length,
0375                 struct acpi_resource_source *resource_source)
0376 {
0377     u8 *aml_resource_source;
0378     acpi_rsdesc_size descriptor_length;
0379 
0380     ACPI_FUNCTION_ENTRY();
0381 
0382     descriptor_length = minimum_length;
0383 
0384     /* Non-zero string length indicates presence of a resource_source */
0385 
0386     if (resource_source->string_length) {
0387 
0388         /* Point to the end of the AML descriptor */
0389 
0390         aml_resource_source = ACPI_ADD_PTR(u8, aml, minimum_length);
0391 
0392         /* Copy the resource_source_index */
0393 
0394         aml_resource_source[0] = (u8) resource_source->index;
0395 
0396         /* Copy the resource_source string */
0397 
0398         strcpy(ACPI_CAST_PTR(char, &aml_resource_source[1]),
0399                resource_source->string_ptr);
0400 
0401         /*
0402          * Add the length of the string (+ 1 for null terminator) to the
0403          * final descriptor length
0404          */
0405         descriptor_length += ((acpi_rsdesc_size)
0406                       resource_source->string_length + 1);
0407     }
0408 
0409     /* Return the new total length of the AML descriptor */
0410 
0411     return (descriptor_length);
0412 }
0413 
0414 /*******************************************************************************
0415  *
0416  * FUNCTION:    acpi_rs_get_prt_method_data
0417  *
0418  * PARAMETERS:  node            - Device node
0419  *              ret_buffer      - Pointer to a buffer structure for the
0420  *                                results
0421  *
0422  * RETURN:      Status
0423  *
0424  * DESCRIPTION: This function is called to get the _PRT value of an object
0425  *              contained in an object specified by the handle passed in
0426  *
0427  *              If the function fails an appropriate status will be returned
0428  *              and the contents of the callers buffer is undefined.
0429  *
0430  ******************************************************************************/
0431 
0432 acpi_status
0433 acpi_rs_get_prt_method_data(struct acpi_namespace_node *node,
0434                 struct acpi_buffer *ret_buffer)
0435 {
0436     union acpi_operand_object *obj_desc;
0437     acpi_status status;
0438 
0439     ACPI_FUNCTION_TRACE(rs_get_prt_method_data);
0440 
0441     /* Parameters guaranteed valid by caller */
0442 
0443     /* Execute the method, no parameters */
0444 
0445     status =
0446         acpi_ut_evaluate_object(node, METHOD_NAME__PRT, ACPI_BTYPE_PACKAGE,
0447                     &obj_desc);
0448     if (ACPI_FAILURE(status)) {
0449         return_ACPI_STATUS(status);
0450     }
0451 
0452     /*
0453      * Create a resource linked list from the byte stream buffer that comes
0454      * back from the _CRS method execution.
0455      */
0456     status = acpi_rs_create_pci_routing_table(obj_desc, ret_buffer);
0457 
0458     /* On exit, we must delete the object returned by evaluate_object */
0459 
0460     acpi_ut_remove_reference(obj_desc);
0461     return_ACPI_STATUS(status);
0462 }
0463 
0464 /*******************************************************************************
0465  *
0466  * FUNCTION:    acpi_rs_get_crs_method_data
0467  *
0468  * PARAMETERS:  node            - Device node
0469  *              ret_buffer      - Pointer to a buffer structure for the
0470  *                                results
0471  *
0472  * RETURN:      Status
0473  *
0474  * DESCRIPTION: This function is called to get the _CRS value of an object
0475  *              contained in an object specified by the handle passed in
0476  *
0477  *              If the function fails an appropriate status will be returned
0478  *              and the contents of the callers buffer is undefined.
0479  *
0480  ******************************************************************************/
0481 
0482 acpi_status
0483 acpi_rs_get_crs_method_data(struct acpi_namespace_node *node,
0484                 struct acpi_buffer *ret_buffer)
0485 {
0486     union acpi_operand_object *obj_desc;
0487     acpi_status status;
0488 
0489     ACPI_FUNCTION_TRACE(rs_get_crs_method_data);
0490 
0491     /* Parameters guaranteed valid by caller */
0492 
0493     /* Execute the method, no parameters */
0494 
0495     status =
0496         acpi_ut_evaluate_object(node, METHOD_NAME__CRS, ACPI_BTYPE_BUFFER,
0497                     &obj_desc);
0498     if (ACPI_FAILURE(status)) {
0499         return_ACPI_STATUS(status);
0500     }
0501 
0502     /*
0503      * Make the call to create a resource linked list from the
0504      * byte stream buffer that comes back from the _CRS method
0505      * execution.
0506      */
0507     status = acpi_rs_create_resource_list(obj_desc, ret_buffer);
0508 
0509     /* On exit, we must delete the object returned by evaluateObject */
0510 
0511     acpi_ut_remove_reference(obj_desc);
0512     return_ACPI_STATUS(status);
0513 }
0514 
0515 /*******************************************************************************
0516  *
0517  * FUNCTION:    acpi_rs_get_prs_method_data
0518  *
0519  * PARAMETERS:  node            - Device node
0520  *              ret_buffer      - Pointer to a buffer structure for the
0521  *                                results
0522  *
0523  * RETURN:      Status
0524  *
0525  * DESCRIPTION: This function is called to get the _PRS value of an object
0526  *              contained in an object specified by the handle passed in
0527  *
0528  *              If the function fails an appropriate status will be returned
0529  *              and the contents of the callers buffer is undefined.
0530  *
0531  ******************************************************************************/
0532 
0533 acpi_status
0534 acpi_rs_get_prs_method_data(struct acpi_namespace_node *node,
0535                 struct acpi_buffer *ret_buffer)
0536 {
0537     union acpi_operand_object *obj_desc;
0538     acpi_status status;
0539 
0540     ACPI_FUNCTION_TRACE(rs_get_prs_method_data);
0541 
0542     /* Parameters guaranteed valid by caller */
0543 
0544     /* Execute the method, no parameters */
0545 
0546     status =
0547         acpi_ut_evaluate_object(node, METHOD_NAME__PRS, ACPI_BTYPE_BUFFER,
0548                     &obj_desc);
0549     if (ACPI_FAILURE(status)) {
0550         return_ACPI_STATUS(status);
0551     }
0552 
0553     /*
0554      * Make the call to create a resource linked list from the
0555      * byte stream buffer that comes back from the _CRS method
0556      * execution.
0557      */
0558     status = acpi_rs_create_resource_list(obj_desc, ret_buffer);
0559 
0560     /* On exit, we must delete the object returned by evaluateObject */
0561 
0562     acpi_ut_remove_reference(obj_desc);
0563     return_ACPI_STATUS(status);
0564 }
0565 
0566 /*******************************************************************************
0567  *
0568  * FUNCTION:    acpi_rs_get_aei_method_data
0569  *
0570  * PARAMETERS:  node            - Device node
0571  *              ret_buffer      - Pointer to a buffer structure for the
0572  *                                results
0573  *
0574  * RETURN:      Status
0575  *
0576  * DESCRIPTION: This function is called to get the _AEI value of an object
0577  *              contained in an object specified by the handle passed in
0578  *
0579  *              If the function fails an appropriate status will be returned
0580  *              and the contents of the callers buffer is undefined.
0581  *
0582  ******************************************************************************/
0583 
0584 acpi_status
0585 acpi_rs_get_aei_method_data(struct acpi_namespace_node *node,
0586                 struct acpi_buffer *ret_buffer)
0587 {
0588     union acpi_operand_object *obj_desc;
0589     acpi_status status;
0590 
0591     ACPI_FUNCTION_TRACE(rs_get_aei_method_data);
0592 
0593     /* Parameters guaranteed valid by caller */
0594 
0595     /* Execute the method, no parameters */
0596 
0597     status =
0598         acpi_ut_evaluate_object(node, METHOD_NAME__AEI, ACPI_BTYPE_BUFFER,
0599                     &obj_desc);
0600     if (ACPI_FAILURE(status)) {
0601         return_ACPI_STATUS(status);
0602     }
0603 
0604     /*
0605      * Make the call to create a resource linked list from the
0606      * byte stream buffer that comes back from the _CRS method
0607      * execution.
0608      */
0609     status = acpi_rs_create_resource_list(obj_desc, ret_buffer);
0610 
0611     /* On exit, we must delete the object returned by evaluateObject */
0612 
0613     acpi_ut_remove_reference(obj_desc);
0614     return_ACPI_STATUS(status);
0615 }
0616 
0617 /*******************************************************************************
0618  *
0619  * FUNCTION:    acpi_rs_get_method_data
0620  *
0621  * PARAMETERS:  handle          - Handle to the containing object
0622  *              path            - Path to method, relative to Handle
0623  *              ret_buffer      - Pointer to a buffer structure for the
0624  *                                results
0625  *
0626  * RETURN:      Status
0627  *
0628  * DESCRIPTION: This function is called to get the _CRS or _PRS value of an
0629  *              object contained in an object specified by the handle passed in
0630  *
0631  *              If the function fails an appropriate status will be returned
0632  *              and the contents of the callers buffer is undefined.
0633  *
0634  ******************************************************************************/
0635 
0636 acpi_status
0637 acpi_rs_get_method_data(acpi_handle handle,
0638             const char *path, struct acpi_buffer *ret_buffer)
0639 {
0640     union acpi_operand_object *obj_desc;
0641     acpi_status status;
0642 
0643     ACPI_FUNCTION_TRACE(rs_get_method_data);
0644 
0645     /* Parameters guaranteed valid by caller */
0646 
0647     /* Execute the method, no parameters */
0648 
0649     status =
0650         acpi_ut_evaluate_object(ACPI_CAST_PTR
0651                     (struct acpi_namespace_node, handle), path,
0652                     ACPI_BTYPE_BUFFER, &obj_desc);
0653     if (ACPI_FAILURE(status)) {
0654         return_ACPI_STATUS(status);
0655     }
0656 
0657     /*
0658      * Make the call to create a resource linked list from the
0659      * byte stream buffer that comes back from the method
0660      * execution.
0661      */
0662     status = acpi_rs_create_resource_list(obj_desc, ret_buffer);
0663 
0664     /* On exit, we must delete the object returned by evaluate_object */
0665 
0666     acpi_ut_remove_reference(obj_desc);
0667     return_ACPI_STATUS(status);
0668 }
0669 
0670 /*******************************************************************************
0671  *
0672  * FUNCTION:    acpi_rs_set_srs_method_data
0673  *
0674  * PARAMETERS:  node            - Device node
0675  *              in_buffer       - Pointer to a buffer structure of the
0676  *                                parameter
0677  *
0678  * RETURN:      Status
0679  *
0680  * DESCRIPTION: This function is called to set the _SRS of an object contained
0681  *              in an object specified by the handle passed in
0682  *
0683  *              If the function fails an appropriate status will be returned
0684  *              and the contents of the callers buffer is undefined.
0685  *
0686  * Note: Parameters guaranteed valid by caller
0687  *
0688  ******************************************************************************/
0689 
0690 acpi_status
0691 acpi_rs_set_srs_method_data(struct acpi_namespace_node *node,
0692                 struct acpi_buffer *in_buffer)
0693 {
0694     struct acpi_evaluate_info *info;
0695     union acpi_operand_object *args[2];
0696     acpi_status status;
0697     struct acpi_buffer buffer;
0698 
0699     ACPI_FUNCTION_TRACE(rs_set_srs_method_data);
0700 
0701     /* Allocate and initialize the evaluation information block */
0702 
0703     info = ACPI_ALLOCATE_ZEROED(sizeof(struct acpi_evaluate_info));
0704     if (!info) {
0705         return_ACPI_STATUS(AE_NO_MEMORY);
0706     }
0707 
0708     info->prefix_node = node;
0709     info->relative_pathname = METHOD_NAME__SRS;
0710     info->parameters = args;
0711     info->flags = ACPI_IGNORE_RETURN_VALUE;
0712 
0713     /*
0714      * The in_buffer parameter will point to a linked list of
0715      * resource parameters. It needs to be formatted into a
0716      * byte stream to be sent in as an input parameter to _SRS
0717      *
0718      * Convert the linked list into a byte stream
0719      */
0720     buffer.length = ACPI_ALLOCATE_LOCAL_BUFFER;
0721     status = acpi_rs_create_aml_resources(in_buffer, &buffer);
0722     if (ACPI_FAILURE(status)) {
0723         goto cleanup;
0724     }
0725 
0726     /* Create and initialize the method parameter object */
0727 
0728     args[0] = acpi_ut_create_internal_object(ACPI_TYPE_BUFFER);
0729     if (!args[0]) {
0730         /*
0731          * Must free the buffer allocated above (otherwise it is freed
0732          * later)
0733          */
0734         ACPI_FREE(buffer.pointer);
0735         status = AE_NO_MEMORY;
0736         goto cleanup;
0737     }
0738 
0739     args[0]->buffer.length = (u32) buffer.length;
0740     args[0]->buffer.pointer = buffer.pointer;
0741     args[0]->common.flags = AOPOBJ_DATA_VALID;
0742     args[1] = NULL;
0743 
0744     /* Execute the method, no return value is expected */
0745 
0746     status = acpi_ns_evaluate(info);
0747 
0748     /* Clean up and return the status from acpi_ns_evaluate */
0749 
0750     acpi_ut_remove_reference(args[0]);
0751 
0752 cleanup:
0753     ACPI_FREE(info);
0754     return_ACPI_STATUS(status);
0755 }