📄 dsobject.c
字号:
/****************************************************************************** * * Module Name: dsobject - Dispatcher object management routines * *****************************************************************************//* * Copyright (C) 2000 - 2005, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification. * 2. Redistributions in binary form must reproduce at minimum a disclaimer * substantially similar to the "NO WARRANTY" disclaimer below * ("Disclaimer") and any redistribution must be conditioned upon * including a substantially similar Disclaimer requirement for further * binary redistribution. * 3. Neither the names of the above-listed copyright holders nor the names * of any contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * Alternatively, this software may be distributed under the terms of the * GNU General Public License ("GPL") version 2 as published by the Free * Software Foundation. * * NO WARRANTY * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. */#include <acpi/acpi.h>#include <acpi/acparser.h>#include <acpi/amlcode.h>#include <acpi/acdispat.h>#include <acpi/acnamesp.h>#include <acpi/acinterp.h>#define _COMPONENT ACPI_DISPATCHERACPI_MODULE_NAME("dsobject")static acpi_statusacpi_ds_build_internal_object(struct acpi_walk_state *walk_state, union acpi_parse_object *op, union acpi_operand_object **obj_desc_ptr);#ifndef ACPI_NO_METHOD_EXECUTION/******************************************************************************* * * FUNCTION: acpi_ds_build_internal_object * * PARAMETERS: walk_state - Current walk state * Op - Parser object to be translated * obj_desc_ptr - Where the ACPI internal object is returned * * RETURN: Status * * DESCRIPTION: Translate a parser Op object to the equivalent namespace object * Simple objects are any objects other than a package object! * ******************************************************************************/static acpi_statusacpi_ds_build_internal_object(struct acpi_walk_state *walk_state, union acpi_parse_object *op, union acpi_operand_object **obj_desc_ptr){ union acpi_operand_object *obj_desc; acpi_status status; ACPI_FUNCTION_TRACE("ds_build_internal_object"); *obj_desc_ptr = NULL; if (op->common.aml_opcode == AML_INT_NAMEPATH_OP) { /* * This is an named object reference. If this name was * previously looked up in the namespace, it was stored in this op. * Otherwise, go ahead and look it up now */ if (!op->common.node) { status = acpi_ns_lookup(walk_state->scope_info, op->common.value.string, ACPI_TYPE_ANY, ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, NULL, (struct acpi_namespace_node **) &(op->common.node)); if (ACPI_FAILURE(status)) { ACPI_REPORT_NSERROR(op->common.value.string, status); return_ACPI_STATUS(status); } } } /* Create and init the internal ACPI object */ obj_desc = acpi_ut_create_internal_object((acpi_ps_get_opcode_info (op->common.aml_opcode))-> object_type); if (!obj_desc) { return_ACPI_STATUS(AE_NO_MEMORY); } status = acpi_ds_init_object_from_op(walk_state, op, op->common.aml_opcode, &obj_desc); if (ACPI_FAILURE(status)) { acpi_ut_remove_reference(obj_desc); return_ACPI_STATUS(status); } *obj_desc_ptr = obj_desc; return_ACPI_STATUS(AE_OK);}/******************************************************************************* * * FUNCTION: acpi_ds_build_internal_buffer_obj * * PARAMETERS: walk_state - Current walk state * Op - Parser object to be translated * buffer_length - Length of the buffer * obj_desc_ptr - Where the ACPI internal object is returned * * RETURN: Status * * DESCRIPTION: Translate a parser Op package object to the equivalent * namespace object * ******************************************************************************/acpi_statusacpi_ds_build_internal_buffer_obj(struct acpi_walk_state *walk_state, union acpi_parse_object *op, u32 buffer_length, union acpi_operand_object **obj_desc_ptr){ union acpi_parse_object *arg; union acpi_operand_object *obj_desc; union acpi_parse_object *byte_list; u32 byte_list_length = 0; ACPI_FUNCTION_TRACE("ds_build_internal_buffer_obj"); obj_desc = *obj_desc_ptr; if (obj_desc) { /* * We are evaluating a Named buffer object "Name (xxxx, Buffer)". * The buffer object already exists (from the NS node) */ } else { /* Create a new buffer object */ obj_desc = acpi_ut_create_internal_object(ACPI_TYPE_BUFFER); *obj_desc_ptr = obj_desc; if (!obj_desc) { return_ACPI_STATUS(AE_NO_MEMORY); } } /* * Second arg is the buffer data (optional) byte_list can be either * individual bytes or a string initializer. In either case, a * byte_list appears in the AML. */ arg = op->common.value.arg; /* skip first arg */ byte_list = arg->named.next; if (byte_list) { if (byte_list->common.aml_opcode != AML_INT_BYTELIST_OP) { ACPI_DEBUG_PRINT((ACPI_DB_ERROR, "Expecting bytelist, got AML opcode %X in op %p\n", byte_list->common.aml_opcode, byte_list)); acpi_ut_remove_reference(obj_desc); return (AE_TYPE); } byte_list_length = (u32) byte_list->common.value.integer; } /* * The buffer length (number of bytes) will be the larger of: * 1) The specified buffer length and * 2) The length of the initializer byte list */ obj_desc->buffer.length = buffer_length; if (byte_list_length > buffer_length) { obj_desc->buffer.length = byte_list_length; } /* Allocate the buffer */ if (obj_desc->buffer.length == 0) { obj_desc->buffer.pointer = NULL; ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Buffer defined with zero length in AML, creating\n")); } else { obj_desc->buffer.pointer = ACPI_MEM_CALLOCATE(obj_desc->buffer.length); if (!obj_desc->buffer.pointer) { acpi_ut_delete_object_desc(obj_desc); return_ACPI_STATUS(AE_NO_MEMORY); } /* Initialize buffer from the byte_list (if present) */ if (byte_list) { ACPI_MEMCPY(obj_desc->buffer.pointer, byte_list->named.data, byte_list_length); } } obj_desc->buffer.flags |= AOPOBJ_DATA_VALID; op->common.node = (struct acpi_namespace_node *)obj_desc; return_ACPI_STATUS(AE_OK);}/******************************************************************************* * * FUNCTION: acpi_ds_build_internal_package_obj * * PARAMETERS: walk_state - Current walk state * Op - Parser object to be translated * package_length - Number of elements in the package * obj_desc_ptr - Where the ACPI internal object is returned * * RETURN: Status * * DESCRIPTION: Translate a parser Op package object to the equivalent * namespace object * ******************************************************************************/acpi_statusacpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, union acpi_parse_object *op, u32 package_length, union acpi_operand_object **obj_desc_ptr){ union acpi_parse_object *arg; union acpi_parse_object *parent; union acpi_operand_object *obj_desc = NULL; u32 package_list_length; acpi_status status = AE_OK; u32 i; ACPI_FUNCTION_TRACE("ds_build_internal_package_obj"); /* Find the parent of a possibly nested package */ parent = op->common.parent; while ((parent->common.aml_opcode == AML_PACKAGE_OP) || (parent->common.aml_opcode == AML_VAR_PACKAGE_OP)) { parent = parent->common.parent; } obj_desc = *obj_desc_ptr; if (obj_desc) { /* * We are evaluating a Named package object "Name (xxxx, Package)". * Get the existing package object from the NS node */ } else { obj_desc = acpi_ut_create_internal_object(ACPI_TYPE_PACKAGE); *obj_desc_ptr = obj_desc; if (!obj_desc) { return_ACPI_STATUS(AE_NO_MEMORY); } obj_desc->package.node = parent->common.node; } obj_desc->package.count = package_length; /* Count the number of items in the package list */ package_list_length = 0; arg = op->common.value.arg; arg = arg->common.next; while (arg) { package_list_length++; arg = arg->common.next; } /* * The package length (number of elements) will be the greater * of the specified length and the length of the initializer list */ if (package_list_length > package_length) { obj_desc->package.count = package_list_length; } /* * Allocate the pointer array (array of pointers to the * individual objects). Add an extra pointer slot so * that the list is always null terminated. */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -