brintos

brintos / linux-shallow public Read only

0
0
Text · 26.1 KiB · 2e17e65 Raw
970 lines · c
1// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.02/******************************************************************************3 *4 * Module Name: utcopy - Internal to external object translation utilities5 *6 * Copyright (C) 2000 - 2023, Intel Corp.7 *8 *****************************************************************************/9 10#include <acpi/acpi.h>11#include "accommon.h"12#include "acnamesp.h"13 14 15#define _COMPONENT          ACPI_UTILITIES16ACPI_MODULE_NAME("utcopy")17 18/* Local prototypes */19static acpi_status20acpi_ut_copy_isimple_to_esimple(union acpi_operand_object *internal_object,21				union acpi_object *external_object,22				u8 *data_space, acpi_size *buffer_space_used);23 24static acpi_status25acpi_ut_copy_ielement_to_ielement(u8 object_type,26				  union acpi_operand_object *source_object,27				  union acpi_generic_state *state,28				  void *context);29 30static acpi_status31acpi_ut_copy_ipackage_to_epackage(union acpi_operand_object *internal_object,32				  u8 *buffer, acpi_size *space_used);33 34static acpi_status35acpi_ut_copy_esimple_to_isimple(union acpi_object *user_obj,36				union acpi_operand_object **return_obj);37 38static acpi_status39acpi_ut_copy_epackage_to_ipackage(union acpi_object *external_object,40				  union acpi_operand_object **internal_object);41 42static acpi_status43acpi_ut_copy_simple_object(union acpi_operand_object *source_desc,44			   union acpi_operand_object *dest_desc);45 46static acpi_status47acpi_ut_copy_ielement_to_eelement(u8 object_type,48				  union acpi_operand_object *source_object,49				  union acpi_generic_state *state,50				  void *context);51 52static acpi_status53acpi_ut_copy_ipackage_to_ipackage(union acpi_operand_object *source_obj,54				  union acpi_operand_object *dest_obj,55				  struct acpi_walk_state *walk_state);56 57/*******************************************************************************58 *59 * FUNCTION:    acpi_ut_copy_isimple_to_esimple60 *61 * PARAMETERS:  internal_object     - Source object to be copied62 *              external_object     - Where to return the copied object63 *              data_space          - Where object data is returned (such as64 *                                    buffer and string data)65 *              buffer_space_used   - Length of data_space that was used66 *67 * RETURN:      Status68 *69 * DESCRIPTION: This function is called to copy a simple internal object to70 *              an external object.71 *72 *              The data_space buffer is assumed to have sufficient space for73 *              the object.74 *75 ******************************************************************************/76 77static acpi_status78acpi_ut_copy_isimple_to_esimple(union acpi_operand_object *internal_object,79				union acpi_object *external_object,80				u8 *data_space, acpi_size *buffer_space_used)81{82	acpi_status status = AE_OK;83 84	ACPI_FUNCTION_TRACE(ut_copy_isimple_to_esimple);85 86	*buffer_space_used = 0;87 88	/*89	 * Check for NULL object case (could be an uninitialized90	 * package element)91	 */92	if (!internal_object) {93		return_ACPI_STATUS(AE_OK);94	}95 96	/* Always clear the external object */97 98	memset(external_object, 0, sizeof(union acpi_object));99 100	/*101	 * In general, the external object will be the same type as102	 * the internal object103	 */104	external_object->type = internal_object->common.type;105 106	/* However, only a limited number of external types are supported */107 108	switch (internal_object->common.type) {109	case ACPI_TYPE_STRING:110 111		external_object->string.pointer = (char *)data_space;112		external_object->string.length = internal_object->string.length;113		*buffer_space_used = ACPI_ROUND_UP_TO_NATIVE_WORD((acpi_size)114								  internal_object->115								  string.116								  length + 1);117 118		memcpy((void *)data_space,119		       (void *)internal_object->string.pointer,120		       (acpi_size)internal_object->string.length + 1);121		break;122 123	case ACPI_TYPE_BUFFER:124 125		external_object->buffer.pointer = data_space;126		external_object->buffer.length = internal_object->buffer.length;127		*buffer_space_used =128		    ACPI_ROUND_UP_TO_NATIVE_WORD(internal_object->string.129						 length);130 131		memcpy((void *)data_space,132		       (void *)internal_object->buffer.pointer,133		       internal_object->buffer.length);134		break;135 136	case ACPI_TYPE_INTEGER:137 138		external_object->integer.value = internal_object->integer.value;139		break;140 141	case ACPI_TYPE_LOCAL_REFERENCE:142 143		/* This is an object reference. */144 145		switch (internal_object->reference.class) {146		case ACPI_REFCLASS_NAME:147			/*148			 * For namepath, return the object handle ("reference")149			 * We are referring to the namespace node150			 */151			external_object->reference.handle =152			    internal_object->reference.node;153			external_object->reference.actual_type =154			    acpi_ns_get_type(internal_object->reference.node);155			break;156 157		default:158 159			/* All other reference types are unsupported */160 161			return_ACPI_STATUS(AE_TYPE);162		}163		break;164 165	case ACPI_TYPE_PROCESSOR:166 167		external_object->processor.proc_id =168		    internal_object->processor.proc_id;169		external_object->processor.pblk_address =170		    internal_object->processor.address;171		external_object->processor.pblk_length =172		    internal_object->processor.length;173		break;174 175	case ACPI_TYPE_POWER:176 177		external_object->power_resource.system_level =178		    internal_object->power_resource.system_level;179 180		external_object->power_resource.resource_order =181		    internal_object->power_resource.resource_order;182		break;183 184	default:185		/*186		 * There is no corresponding external object type187		 */188		ACPI_ERROR((AE_INFO,189			    "Unsupported object type, cannot convert to external object: %s",190			    acpi_ut_get_type_name(internal_object->common.191						  type)));192 193		return_ACPI_STATUS(AE_SUPPORT);194	}195 196	return_ACPI_STATUS(status);197}198 199/*******************************************************************************200 *201 * FUNCTION:    acpi_ut_copy_ielement_to_eelement202 *203 * PARAMETERS:  acpi_pkg_callback204 *205 * RETURN:      Status206 *207 * DESCRIPTION: Copy one package element to another package element208 *209 ******************************************************************************/210 211static acpi_status212acpi_ut_copy_ielement_to_eelement(u8 object_type,213				  union acpi_operand_object *source_object,214				  union acpi_generic_state *state,215				  void *context)216{217	acpi_status status = AE_OK;218	struct acpi_pkg_info *info = (struct acpi_pkg_info *)context;219	acpi_size object_space;220	u32 this_index;221	union acpi_object *target_object;222 223	ACPI_FUNCTION_ENTRY();224 225	this_index = state->pkg.index;226	target_object = (union acpi_object *)&((union acpi_object *)227					       (state->pkg.dest_object))->228	    package.elements[this_index];229 230	switch (object_type) {231	case ACPI_COPY_TYPE_SIMPLE:232		/*233		 * This is a simple or null object234		 */235		status = acpi_ut_copy_isimple_to_esimple(source_object,236							 target_object,237							 info->free_space,238							 &object_space);239		if (ACPI_FAILURE(status)) {240			return (status);241		}242		break;243 244	case ACPI_COPY_TYPE_PACKAGE:245		/*246		 * Build the package object247		 */248		target_object->type = ACPI_TYPE_PACKAGE;249		target_object->package.count = source_object->package.count;250		target_object->package.elements =251		    ACPI_CAST_PTR(union acpi_object, info->free_space);252 253		/*254		 * Pass the new package object back to the package walk routine255		 */256		state->pkg.this_target_obj = target_object;257 258		/*259		 * Save space for the array of objects (Package elements)260		 * update the buffer length counter261		 */262		object_space = ACPI_ROUND_UP_TO_NATIVE_WORD((acpi_size)263							    target_object->264							    package.count *265							    sizeof(union266								   acpi_object));267		break;268 269	default:270 271		return (AE_BAD_PARAMETER);272	}273 274	info->free_space += object_space;275	info->length += object_space;276	return (status);277}278 279/*******************************************************************************280 *281 * FUNCTION:    acpi_ut_copy_ipackage_to_epackage282 *283 * PARAMETERS:  internal_object     - Pointer to the object we are returning284 *              buffer              - Where the object is returned285 *              space_used          - Where the object length is returned286 *287 * RETURN:      Status288 *289 * DESCRIPTION: This function is called to place a package object in a user290 *              buffer. A package object by definition contains other objects.291 *292 *              The buffer is assumed to have sufficient space for the object.293 *              The caller must have verified the buffer length needed using294 *              the acpi_ut_get_object_size function before calling this function.295 *296 ******************************************************************************/297 298static acpi_status299acpi_ut_copy_ipackage_to_epackage(union acpi_operand_object *internal_object,300				  u8 *buffer, acpi_size *space_used)301{302	union acpi_object *external_object;303	acpi_status status;304	struct acpi_pkg_info info;305 306	ACPI_FUNCTION_TRACE(ut_copy_ipackage_to_epackage);307 308	/*309	 * First package at head of the buffer310	 */311	external_object = ACPI_CAST_PTR(union acpi_object, buffer);312 313	/*314	 * Free space begins right after the first package315	 */316	info.length = ACPI_ROUND_UP_TO_NATIVE_WORD(sizeof(union acpi_object));317	info.free_space = buffer +318	    ACPI_ROUND_UP_TO_NATIVE_WORD(sizeof(union acpi_object));319	info.object_space = 0;320	info.num_packages = 1;321 322	external_object->type = internal_object->common.type;323	external_object->package.count = internal_object->package.count;324	external_object->package.elements =325	    ACPI_CAST_PTR(union acpi_object, info.free_space);326 327	/*328	 * Leave room for an array of ACPI_OBJECTS in the buffer329	 * and move the free space past it330	 */331	info.length += (acpi_size)external_object->package.count *332	    ACPI_ROUND_UP_TO_NATIVE_WORD(sizeof(union acpi_object));333	info.free_space += external_object->package.count *334	    ACPI_ROUND_UP_TO_NATIVE_WORD(sizeof(union acpi_object));335 336	status = acpi_ut_walk_package_tree(internal_object, external_object,337					   acpi_ut_copy_ielement_to_eelement,338					   &info);339 340	*space_used = info.length;341	return_ACPI_STATUS(status);342}343 344/*******************************************************************************345 *346 * FUNCTION:    acpi_ut_copy_iobject_to_eobject347 *348 * PARAMETERS:  internal_object     - The internal object to be converted349 *              ret_buffer          - Where the object is returned350 *351 * RETURN:      Status352 *353 * DESCRIPTION: This function is called to build an API object to be returned354 *              to the caller.355 *356 ******************************************************************************/357 358acpi_status359acpi_ut_copy_iobject_to_eobject(union acpi_operand_object *internal_object,360				struct acpi_buffer *ret_buffer)361{362	acpi_status status;363 364	ACPI_FUNCTION_TRACE(ut_copy_iobject_to_eobject);365 366	if (internal_object->common.type == ACPI_TYPE_PACKAGE) {367		/*368		 * Package object:  Copy all subobjects (including369		 * nested packages)370		 */371		status = acpi_ut_copy_ipackage_to_epackage(internal_object,372							   ret_buffer->pointer,373							   &ret_buffer->length);374	} else {375		/*376		 * Build a simple object (no nested objects)377		 */378		status = acpi_ut_copy_isimple_to_esimple(internal_object,379							 ACPI_CAST_PTR(union380								       acpi_object,381								       ret_buffer->382								       pointer),383							 ACPI_ADD_PTR(u8,384								      ret_buffer->385								      pointer,386								      ACPI_ROUND_UP_TO_NATIVE_WORD387								      (sizeof388								       (union389									acpi_object))),390							 &ret_buffer->length);391		/*392		 * build simple does not include the object size in the length393		 * so we add it in here394		 */395		ret_buffer->length += sizeof(union acpi_object);396	}397 398	return_ACPI_STATUS(status);399}400 401/*******************************************************************************402 *403 * FUNCTION:    acpi_ut_copy_esimple_to_isimple404 *405 * PARAMETERS:  external_object     - The external object to be converted406 *              ret_internal_object - Where the internal object is returned407 *408 * RETURN:      Status409 *410 * DESCRIPTION: This function copies an external object to an internal one.411 *              NOTE: Pointers can be copied, we don't need to copy data.412 *              (The pointers have to be valid in our address space no matter413 *              what we do with them!)414 *415 ******************************************************************************/416 417static acpi_status418acpi_ut_copy_esimple_to_isimple(union acpi_object *external_object,419				union acpi_operand_object **ret_internal_object)420{421	union acpi_operand_object *internal_object;422 423	ACPI_FUNCTION_TRACE(ut_copy_esimple_to_isimple);424 425	/*426	 * Simple types supported are: String, Buffer, Integer427	 */428	switch (external_object->type) {429	case ACPI_TYPE_STRING:430	case ACPI_TYPE_BUFFER:431	case ACPI_TYPE_INTEGER:432	case ACPI_TYPE_LOCAL_REFERENCE:433 434		internal_object = acpi_ut_create_internal_object((u8)435								 external_object->436								 type);437		if (!internal_object) {438			return_ACPI_STATUS(AE_NO_MEMORY);439		}440		break;441 442	case ACPI_TYPE_ANY:	/* This is the case for a NULL object */443 444		*ret_internal_object = NULL;445		return_ACPI_STATUS(AE_OK);446 447	default:448 449		/* All other types are not supported */450 451		ACPI_ERROR((AE_INFO,452			    "Unsupported object type, cannot convert to internal object: %s",453			    acpi_ut_get_type_name(external_object->type)));454 455		return_ACPI_STATUS(AE_SUPPORT);456	}457 458	/* Must COPY string and buffer contents */459 460	switch (external_object->type) {461	case ACPI_TYPE_STRING:462 463		internal_object->string.pointer =464		    ACPI_ALLOCATE_ZEROED((acpi_size)465					 external_object->string.length + 1);466 467		if (!internal_object->string.pointer) {468			goto error_exit;469		}470 471		memcpy(internal_object->string.pointer,472		       external_object->string.pointer,473		       external_object->string.length);474 475		internal_object->string.length = external_object->string.length;476		break;477 478	case ACPI_TYPE_BUFFER:479 480		internal_object->buffer.pointer =481		    ACPI_ALLOCATE_ZEROED(external_object->buffer.length);482		if (!internal_object->buffer.pointer) {483			goto error_exit;484		}485 486		memcpy(internal_object->buffer.pointer,487		       external_object->buffer.pointer,488		       external_object->buffer.length);489 490		internal_object->buffer.length = external_object->buffer.length;491 492		/* Mark buffer data valid */493 494		internal_object->buffer.flags |= AOPOBJ_DATA_VALID;495		break;496 497	case ACPI_TYPE_INTEGER:498 499		internal_object->integer.value = external_object->integer.value;500		break;501 502	case ACPI_TYPE_LOCAL_REFERENCE:503 504		/* An incoming reference is defined to be a namespace node */505 506		internal_object->reference.class = ACPI_REFCLASS_REFOF;507		internal_object->reference.object =508		    external_object->reference.handle;509		break;510 511	default:512 513		/* Other types can't get here */514 515		break;516	}517 518	*ret_internal_object = internal_object;519	return_ACPI_STATUS(AE_OK);520 521error_exit:522	acpi_ut_remove_reference(internal_object);523	return_ACPI_STATUS(AE_NO_MEMORY);524}525 526/*******************************************************************************527 *528 * FUNCTION:    acpi_ut_copy_epackage_to_ipackage529 *530 * PARAMETERS:  external_object     - The external object to be converted531 *              internal_object     - Where the internal object is returned532 *533 * RETURN:      Status534 *535 * DESCRIPTION: Copy an external package object to an internal package.536 *              Handles nested packages.537 *538 ******************************************************************************/539 540static acpi_status541acpi_ut_copy_epackage_to_ipackage(union acpi_object *external_object,542				  union acpi_operand_object **internal_object)543{544	acpi_status status = AE_OK;545	union acpi_operand_object *package_object;546	union acpi_operand_object **package_elements;547	u32 i;548 549	ACPI_FUNCTION_TRACE(ut_copy_epackage_to_ipackage);550 551	/* Create the package object */552 553	package_object =554	    acpi_ut_create_package_object(external_object->package.count);555	if (!package_object) {556		return_ACPI_STATUS(AE_NO_MEMORY);557	}558 559	package_elements = package_object->package.elements;560 561	/*562	 * Recursive implementation. Probably ok, since nested external563	 * packages as parameters should be very rare.564	 */565	for (i = 0; i < external_object->package.count; i++) {566		status =567		    acpi_ut_copy_eobject_to_iobject(&external_object->package.568						    elements[i],569						    &package_elements[i]);570		if (ACPI_FAILURE(status)) {571 572			/* Truncate package and delete it */573 574			package_object->package.count = i;575			package_elements[i] = NULL;576			acpi_ut_remove_reference(package_object);577			return_ACPI_STATUS(status);578		}579	}580 581	/* Mark package data valid */582 583	package_object->package.flags |= AOPOBJ_DATA_VALID;584 585	*internal_object = package_object;586	return_ACPI_STATUS(status);587}588 589/*******************************************************************************590 *591 * FUNCTION:    acpi_ut_copy_eobject_to_iobject592 *593 * PARAMETERS:  external_object     - The external object to be converted594 *              internal_object     - Where the internal object is returned595 *596 * RETURN:      Status597 *598 * DESCRIPTION: Converts an external object to an internal object.599 *600 ******************************************************************************/601 602acpi_status603acpi_ut_copy_eobject_to_iobject(union acpi_object *external_object,604				union acpi_operand_object **internal_object)605{606	acpi_status status;607 608	ACPI_FUNCTION_TRACE(ut_copy_eobject_to_iobject);609 610	if (external_object->type == ACPI_TYPE_PACKAGE) {611		status =612		    acpi_ut_copy_epackage_to_ipackage(external_object,613						      internal_object);614	} else {615		/*616		 * Build a simple object (no nested objects)617		 */618		status = acpi_ut_copy_esimple_to_isimple(external_object,619							 internal_object);620	}621 622	return_ACPI_STATUS(status);623}624 625/*******************************************************************************626 *627 * FUNCTION:    acpi_ut_copy_simple_object628 *629 * PARAMETERS:  source_desc         - The internal object to be copied630 *              dest_desc           - New target object631 *632 * RETURN:      Status633 *634 * DESCRIPTION: Simple copy of one internal object to another. Reference count635 *              of the destination object is preserved.636 *637 ******************************************************************************/638 639static acpi_status640acpi_ut_copy_simple_object(union acpi_operand_object *source_desc,641			   union acpi_operand_object *dest_desc)642{643	u16 reference_count;644	union acpi_operand_object *next_object;645	acpi_status status;646	acpi_size copy_size;647 648	/* Save fields from destination that we don't want to overwrite */649 650	reference_count = dest_desc->common.reference_count;651	next_object = dest_desc->common.next_object;652 653	/*654	 * Copy the entire source object over the destination object.655	 * Note: Source can be either an operand object or namespace node.656	 */657	copy_size = sizeof(union acpi_operand_object);658	if (ACPI_GET_DESCRIPTOR_TYPE(source_desc) == ACPI_DESC_TYPE_NAMED) {659		copy_size = sizeof(struct acpi_namespace_node);660	}661 662	memcpy(ACPI_CAST_PTR(char, dest_desc),663	       ACPI_CAST_PTR(char, source_desc), copy_size);664 665	/* Restore the saved fields */666 667	dest_desc->common.reference_count = reference_count;668	dest_desc->common.next_object = next_object;669 670	/* New object is not static, regardless of source */671 672	dest_desc->common.flags &= ~AOPOBJ_STATIC_POINTER;673 674	/* Handle the objects with extra data */675 676	switch (dest_desc->common.type) {677	case ACPI_TYPE_BUFFER:678		/*679		 * Allocate and copy the actual buffer if and only if:680		 * 1) There is a valid buffer pointer681		 * 2) The buffer has a length > 0682		 */683		if ((source_desc->buffer.pointer) &&684		    (source_desc->buffer.length)) {685			dest_desc->buffer.pointer =686			    ACPI_ALLOCATE(source_desc->buffer.length);687			if (!dest_desc->buffer.pointer) {688				return (AE_NO_MEMORY);689			}690 691			/* Copy the actual buffer data */692 693			memcpy(dest_desc->buffer.pointer,694			       source_desc->buffer.pointer,695			       source_desc->buffer.length);696		}697		break;698 699	case ACPI_TYPE_STRING:700		/*701		 * Allocate and copy the actual string if and only if:702		 * 1) There is a valid string pointer703		 * (Pointer to a NULL string is allowed)704		 */705		if (source_desc->string.pointer) {706			dest_desc->string.pointer =707			    ACPI_ALLOCATE((acpi_size)source_desc->string.708					  length + 1);709			if (!dest_desc->string.pointer) {710				return (AE_NO_MEMORY);711			}712 713			/* Copy the actual string data */714 715			memcpy(dest_desc->string.pointer,716			       source_desc->string.pointer,717			       (acpi_size)source_desc->string.length + 1);718		}719		break;720 721	case ACPI_TYPE_LOCAL_REFERENCE:722		/*723		 * We copied the reference object, so we now must add a reference724		 * to the object pointed to by the reference725		 *726		 * DDBHandle reference (from Load/load_table) is a special reference,727		 * it does not have a Reference.Object, so does not need to728		 * increase the reference count729		 */730		if (source_desc->reference.class == ACPI_REFCLASS_TABLE) {731			break;732		}733 734		acpi_ut_add_reference(source_desc->reference.object);735		break;736 737	case ACPI_TYPE_REGION:738		/*739		 * We copied the Region Handler, so we now must add a reference740		 */741		if (dest_desc->region.handler) {742			acpi_ut_add_reference(dest_desc->region.handler);743		}744		break;745 746		/*747		 * For Mutex and Event objects, we cannot simply copy the underlying748		 * OS object. We must create a new one.749		 */750	case ACPI_TYPE_MUTEX:751 752		status = acpi_os_create_mutex(&dest_desc->mutex.os_mutex);753		if (ACPI_FAILURE(status)) {754			return (status);755		}756		break;757 758	case ACPI_TYPE_EVENT:759 760		status = acpi_os_create_semaphore(ACPI_NO_UNIT_LIMIT, 0,761						  &dest_desc->event.762						  os_semaphore);763		if (ACPI_FAILURE(status)) {764			return (status);765		}766		break;767 768	default:769 770		/* Nothing to do for other simple objects */771 772		break;773	}774 775	return (AE_OK);776}777 778/*******************************************************************************779 *780 * FUNCTION:    acpi_ut_copy_ielement_to_ielement781 *782 * PARAMETERS:  acpi_pkg_callback783 *784 * RETURN:      Status785 *786 * DESCRIPTION: Copy one package element to another package element787 *788 ******************************************************************************/789 790static acpi_status791acpi_ut_copy_ielement_to_ielement(u8 object_type,792				  union acpi_operand_object *source_object,793				  union acpi_generic_state *state,794				  void *context)795{796	acpi_status status = AE_OK;797	u32 this_index;798	union acpi_operand_object **this_target_ptr;799	union acpi_operand_object *target_object;800 801	ACPI_FUNCTION_ENTRY();802 803	this_index = state->pkg.index;804	this_target_ptr = (union acpi_operand_object **)805	    &state->pkg.dest_object->package.elements[this_index];806 807	switch (object_type) {808	case ACPI_COPY_TYPE_SIMPLE:809 810		/* A null source object indicates a (legal) null package element */811 812		if (source_object) {813			/*814			 * This is a simple object, just copy it815			 */816			target_object =817			    acpi_ut_create_internal_object(source_object->818							   common.type);819			if (!target_object) {820				return (AE_NO_MEMORY);821			}822 823			status =824			    acpi_ut_copy_simple_object(source_object,825						       target_object);826			if (ACPI_FAILURE(status)) {827				goto error_exit;828			}829 830			*this_target_ptr = target_object;831		} else {832			/* Pass through a null element */833 834			*this_target_ptr = NULL;835		}836		break;837 838	case ACPI_COPY_TYPE_PACKAGE:839		/*840		 * This object is a package - go down another nesting level841		 * Create and build the package object842		 */843		target_object =844		    acpi_ut_create_package_object(source_object->package.count);845		if (!target_object) {846			return (AE_NO_MEMORY);847		}848 849		target_object->common.flags = source_object->common.flags;850 851		/* Pass the new package object back to the package walk routine */852 853		state->pkg.this_target_obj = target_object;854 855		/* Store the object pointer in the parent package object */856 857		*this_target_ptr = target_object;858		break;859 860	default:861 862		return (AE_BAD_PARAMETER);863	}864 865	return (status);866 867error_exit:868	acpi_ut_remove_reference(target_object);869	return (status);870}871 872/*******************************************************************************873 *874 * FUNCTION:    acpi_ut_copy_ipackage_to_ipackage875 *876 * PARAMETERS:  source_obj      - Pointer to the source package object877 *              dest_obj        - Where the internal object is returned878 *              walk_state      - Current Walk state descriptor879 *880 * RETURN:      Status881 *882 * DESCRIPTION: This function is called to copy an internal package object883 *              into another internal package object.884 *885 ******************************************************************************/886 887static acpi_status888acpi_ut_copy_ipackage_to_ipackage(union acpi_operand_object *source_obj,889				  union acpi_operand_object *dest_obj,890				  struct acpi_walk_state *walk_state)891{892	acpi_status status = AE_OK;893 894	ACPI_FUNCTION_TRACE(ut_copy_ipackage_to_ipackage);895 896	dest_obj->common.type = source_obj->common.type;897	dest_obj->common.flags = source_obj->common.flags;898	dest_obj->package.count = source_obj->package.count;899 900	/*901	 * Create the object array and walk the source package tree902	 */903	dest_obj->package.elements = ACPI_ALLOCATE_ZEROED(((acpi_size)904							   source_obj->package.905							   count +906							   1) * sizeof(void *));907	if (!dest_obj->package.elements) {908		ACPI_ERROR((AE_INFO, "Package allocation failure"));909		return_ACPI_STATUS(AE_NO_MEMORY);910	}911 912	/*913	 * Copy the package element-by-element by walking the package "tree".914	 * This handles nested packages of arbitrary depth.915	 */916	status = acpi_ut_walk_package_tree(source_obj, dest_obj,917					   acpi_ut_copy_ielement_to_ielement,918					   walk_state);919	return_ACPI_STATUS(status);920}921 922/*******************************************************************************923 *924 * FUNCTION:    acpi_ut_copy_iobject_to_iobject925 *926 * PARAMETERS:  source_desc         - The internal object to be copied927 *              dest_desc           - Where the copied object is returned928 *              walk_state          - Current walk state929 *930 * RETURN:      Status931 *932 * DESCRIPTION: Copy an internal object to a new internal object933 *934 ******************************************************************************/935 936acpi_status937acpi_ut_copy_iobject_to_iobject(union acpi_operand_object *source_desc,938				union acpi_operand_object **dest_desc,939				struct acpi_walk_state *walk_state)940{941	acpi_status status = AE_OK;942 943	ACPI_FUNCTION_TRACE(ut_copy_iobject_to_iobject);944 945	/* Create the top level object */946 947	*dest_desc = acpi_ut_create_internal_object(source_desc->common.type);948	if (!*dest_desc) {949		return_ACPI_STATUS(AE_NO_MEMORY);950	}951 952	/* Copy the object and possible subobjects */953 954	if (source_desc->common.type == ACPI_TYPE_PACKAGE) {955		status =956		    acpi_ut_copy_ipackage_to_ipackage(source_desc, *dest_desc,957						      walk_state);958	} else {959		status = acpi_ut_copy_simple_object(source_desc, *dest_desc);960	}961 962	/* Delete the allocated object if copy failed */963 964	if (ACPI_FAILURE(status)) {965		acpi_ut_remove_reference(*dest_desc);966	}967 968	return_ACPI_STATUS(status);969}970