/******************************************************************************* * * Module Name: nsobject - Utilities for objects attached to namespace * table entries * ******************************************************************************/ /* * Copyright (C) 2000 - 2015, Intel Corp. * 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 #include "accommon.h" #include "acnamesp.h" #define _COMPONENT ACPI_NAMESPACE ACPI_MODULE_NAME("nsobject") /******************************************************************************* * * FUNCTION: acpi_ns_attach_object * * PARAMETERS: node - Parent Node * object - Object to be attached * type - Type of object, or ACPI_TYPE_ANY if not * known * * RETURN: Status * * DESCRIPTION: Record the given object as the value associated with the * name whose acpi_handle is passed. If Object is NULL * and Type is ACPI_TYPE_ANY, set the name as having no value. * Note: Future may require that the Node->Flags field be passed * as a parameter. * * MUTEX: Assumes namespace is locked * ******************************************************************************/ acpi_status acpi_ns_attach_object(struct acpi_namespace_node *node, union acpi_operand_object *object, acpi_object_type type) { union acpi_operand_object *obj_desc; union acpi_operand_object *last_obj_desc; acpi_object_type object_type = ACPI_TYPE_ANY; ACPI_FUNCTION_TRACE(ns_attach_object); /* * Parameter validation */ if (!node) { /* Invalid handle */ ACPI_ERROR((AE_INFO, "Null NamedObj handle")); return_ACPI_STATUS(AE_BAD_PARAMETER); } if (!object && (ACPI_TYPE_ANY != type)) { /* Null object */ ACPI_ERROR((AE_INFO, "Null object, but type not ACPI_TYPE_ANY")); return_ACPI_STATUS(AE_BAD_PARAMETER); } if (ACPI_GET_DESCRIPTOR_TYPE(node) != ACPI_DESC_TYPE_NAMED) { /* Not a name handle */ ACPI_ERROR((AE_INFO, "Invalid handle %p [%s]", node, acpi_ut_get_descriptor_name(node))); return_ACPI_STATUS(AE_BAD_PARAMETER); } /* Check if this object is already attached */ if (node->object == object) { ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Obj %p already installed in NameObj %p\n", object, node)); return_ACPI_STATUS(AE_OK); } /* If null object, we will just install it */ if (!object) { obj_desc = NULL; object_type = ACPI_TYPE_ANY; } /* * If the source object is a namespace Node with an attached object, * we will use that (attached) object */ else if ((ACPI_GET_DESCRIPTOR_TYPE(object) == ACPI_DESC_TYPE_NAMED) && ((struct acpi_namespace_node *)object)->object) { /* * Value passed is a name handle and that name has a * non-null value. Use that name's value and type. */ obj_desc = ((struct acpi_namespace_node *)object)->object; object_type = ((struct acpi_namespace_node *)object)->type; } /* * Otherwise, we will use the parameter object, but we must type * it first */ else { obj_desc = (union acpi_operand_object *)object; /* Use the given type */ object_type = type; } ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Installing %p into Node %p [%4.4s]\n", obj_desc, node, acpi_ut_get_node_name(node))); /* Detach an existing attached object if present */ if (node->object) { acpi_ns_detach_object(node); } if (obj_desc) { /* * Must increment the new value's reference count * (if it is an internal object) */ acpi_ut_add_reference(obj_desc); /* * Handle objects with multiple descriptors - walk * to the end of the descriptor list */ last_obj_desc = obj_desc; while (last_obj_desc->common.next_object) { last_obj_desc = last_obj_desc->common.next_object; } /* Install the object a