// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
/******************************************************************************
 *
 * Module Name: exconcat - Concatenate-type AML operators
 *
 * Copyright (C) 2000 - 2018, Intel Corp.
 *
 *****************************************************************************/

#include <acpi/acpi.h>
#include "accommon.h"
#include "acinterp.h"
#include "amlresrc.h"

#define _COMPONENT          ACPI_EXECUTER
ACPI_MODULE_NAME("exconcat")

/* Local Prototypes */
static acpi_status
acpi_ex_convert_to_object_type_string(union acpi_operand_object *obj_desc,
				      union acpi_operand_object **result_desc);

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_do_concatenate
 *
 * PARAMETERS:  operand0            - First source object
 *              operand1            - Second source object
 *              actual_return_desc  - Where to place the return object
 *              walk_state          - Current walk state
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Concatenate two objects with the ACPI-defined conversion
 *              rules as necessary.
 * NOTE:
 * Per the ACPI spec (up to 6.1), Concatenate only supports Integer,
 * String, and Buffer objects. However, we support all objects here
 * as an extension. This improves the usefulness of both Concatenate
 * and the Printf/Fprintf macros. The extension returns a string
 * describing the object type for the other objects.
 * 02/2016.
 *
 ******************************************************************************/

acpi_status
acpi_ex_do_concatenate(union acpi_operand_object *operand0,
		       union acpi_operand_object *operand1,
		       union acpi_operand_object **actual_return_desc,
		       struct acpi_walk_state *walk_state)
{
	union acpi_operand_object *local_operand0 = operand0;
	union acpi_operand_object *local_operand1 = operand1;
	union acpi_operand_object *temp_operand1 = NULL;
	union acpi_operand_object *return_desc;
	char *buffer;
	acpi_object_type operand0_type;
	acpi_object_type operand1_type;
	acpi_status status;

	ACPI_FUNCTION_TRACE(ex_do_concatenate);

	/* Operand 0 preprocessing */

	switch (operand0->common.type) {
	case ACPI_TYPE_INTEGER:
	case ACPI_TYPE_STRING:
	case ACPI_TYPE_BUFFER:

		operand0_type = operand0->common.type;
		break;

	default:

		/* For all other types, get the "object type" string */

		status =
		    acpi_ex_convert_to_object_type_string(operand0,
							  &local_operand0);
		if (ACPI_FAILURE(status)) {
			goto cleanup;
		}

		operand0_type = ACPI_TYPE_STRING;
		break;
	}

	/* Operand 1 preprocessing */

	switch (operand1->common.type) {
	case ACPI_TYPE_INTEGER:
	case ACPI_TYPE_STRING:
	case ACPI_TYPE_BUFFER:

		operand1_type = operand1->common.type;
		break;

	default:

		/* For all other types, get the "object type" string */

		status =
		    acpi_ex_convert_to_object_type_string(operand1,
							  &local_operand1);
		if (ACPI_FAILURE(status)) {
			goto cleanup;
		}

		operand1_type = ACPI_TYPE_STRING;
		break;
	}

	/*
	 * Convert the second operand if necessary. The first operand (0)
	 * determines the type of the second operand (1) (See the Data Types
	 * section of the ACPI specification). Both object types are
	 * guaranteed to be either Integer/String/Buffer by the operand
	 * resolution mechanism.
	 */
	switch (operand0_type) {
	case ACPI_TYPE_INTEGER:

		status =
		    acpi_ex_convert_to_integer(local_operand1, &temp_operand1,
					       ACPI_IMPLICIT_CONVERSION);
		break;

	case ACPI_TYPE_BUFFER:

		status =
		    acpi_ex_convert_to_buffer(local_operand1, &temp_operand1);
		break;

	case ACPI_TYPE_STRING:

		switch (operand1_type) {
		case ACPI_TYPE_INTEGER:
		case ACPI_TYPE_STRING:
		case ACPI_TYPE_BUFFER:

			/* Other types have already been converted to string */

			status =
			    acpi_ex_convert_to_string(local_operand1,
						      &temp_operand1,
						      ACPI_IMPLICIT_CONVERT_HEX);
			break;

		default:

			status = AE_OK;
			break;
		}
		break;

	default:

		ACPI_ERROR((AE_INFO, "Invalid object type: 0x%X",
			    operand0->common.type));
		status = AE_AML_INTERNAL;
	}

	if (ACPI_FAILURE(status)) {
		goto cleanup;
	}

	/* Take care with any newly created operand objects */

	if ((local_operand1 != operand1) && (local_operand1 != temp_operand1)) {
		acpi_ut_remove_reference(local_operand1);
	}

	local_operand1 = temp_operand1;

	/*
	 * Both operands are now known to be the same object type
	 * (Both are Integer, String, or Buffer), and we can now perform
	 * the concatenation.
	 *
	 * There are three cases to handle, as per the ACPI spec:
	 *
	 * 1) Two Integers concatenated to produce a new Buffer
	 * 2) Two Strings concatenated to produce a new String
	 * 3) Two Buffers concatenated to produce a new Buffer
	 */
	switch (operand0_type) {
	case ACPI_TYPE_INTEGER:

		/* Result of two Integers is a Buffer */
		/* Need enough buffer space for two integers */

		return_desc = acpi_ut_create_buffer_object((acpi_size)
							   ACPI_MUL_2
							   (acpi_gbl_integer_byte_width));
		if (!return_desc) {
			status = AE_NO_MEMORY;
			goto cleanup;
		}

		buffer = (char *)return_desc->buffer.pointer;

		/* Copy the first integer, LSB first */

		memcpy(buffer, &operand0->integer.value,
		       acpi_gbl_integer_byte_width);

		/* Copy the second integer (LSB first) after the first */

		memcpy(buffer + acpi_gbl_integer_byte_width,
		       &local_operand1->integer.value,
		       acpi_gbl_integer_byte_width);
		break;

	case ACPI_TYPE_STRING:

		/* Result of two Strings is a String */

		return_desc = acpi_ut_create_string_object(((acpi_size)
							    local_operand0->
							    string.length +
							    local_operand1->
							    string.length));
		if (!return_desc) {
			status = AE_NO_MEMORY;
			goto cleanup;
		}

		buffer = return_desc->string.pointer;

		/* Concatenate the strings */

		strcpy(buffer, local_operand0->string.pointer);
		strcat(buffer, local_operand1->string.pointer);
		break;

	case ACPI_TYPE_BUFFER:

		/* Result of two Buffers is a Buffer */

		return_desc = acpi_ut_create_buffer_object(((acpi_size)
							    operand0->buffer.
							    length +
							    local_operand1->
							    buffer.length));
		if (!return_desc) {
			status = AE_NO_MEMORY;
			goto cleanup;
		}

		buffer = (char *)return_desc->buffer.pointer;

		/* Concatenate the buffers */

		memcpy(buffer, operand0->buffer.pointer,
		       operand0->buffer.length);
		memcpy(buffer + operand0->buffer.length,
		       local_operand1->buffer.pointer,
		       local_operand1->buffer.length);
		break;

	default:

		/* Invalid object type, should not happen here */

		ACPI_ERROR((AE_INFO, "Invalid object type: 0x%X",
			    operand0->common.type));
		status = AE_AML_INTERNAL;
		goto cleanup;
	}

	*actual_return_desc = return_desc;

cleanup:
	if (local_operand0 != operand0) {
		acpi_ut_remove_reference(local_operand0);
	}

	if (local_operand1 != operand1) {
		acpi_ut_remove_reference(local_operand1);
	}

	return_ACPI_STATUS(status);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_object_type_string
 *
 * PARAMETERS:  obj_desc            - Object to be converted
 *              return_desc         - Where to place the return object
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Convert an object of arbitrary type to a string object that
 *              contains the namestring for the object. Used for the
 *              concatenate operator.
 *
 ******************************************************************************/

static acpi_status
acpi_ex_convert_to_object_type_string(union acpi_operand_object *obj_desc,
				      union acpi_operand_object **result_desc)
{
	union acpi_operand_object *return_desc;
	const char *type_string;

	type_string = acpi_ut_get_type_name(obj_desc->common.type);

	return_desc = acpi_ut_create_string_object(((acpi_size)strlen(type_string) + 9));	/* 9 For "[ Object]" */
	if (!return_desc) {
		return (AE_NO_MEMORY);
	}

	strcpy(return_desc->string.pointer, "[");
	strcat(return_desc->string.pointer, type_string);
	strcat(return_desc->string.pointer, " Object]");

	*result_desc = return_desc;
	return (AE_OK);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_concat_template
 *
 * PARAMETERS:  operand0            - First source object
 *              operand1            - Second source object
 *              actual_return_desc  - Where to place the return object
 *              walk_state          - Current walk state
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Concatenate two resource templates
 *
 ******************************************************************************/

acpi_status
acpi_ex_concat_template(union acpi_operand_object *operand0,
			union acpi_operand_object *operand1,
			union acpi_operand_object **actual_return_desc,
			struct acpi_walk_state *walk_state)
{
	acpi_status status;
	union acpi_operand_object *return_desc;
	u8 *new_buf;
	u8 *end_tag;
	acpi_size length0;
	acpi_size length1;
	acpi_size new_length;

	ACPI_FUNCTION_TRACE(ex_concat_template);

	/*
	 * Find the end_tag descriptor in each resource template.
	 * Note1: returned pointers point TO the end_tag, not past it.
	 * Note2: zero-length buffers are allowed; treated like one end_tag
	 */

	/* Get the length of the first resource template */

	status = acpi_ut_get_resource_end_tag(operand0, &end_tag);
	if (ACPI_FAILURE(status)) {
		return_ACPI_STATUS(status);
	}

	length0 = ACPI_PTR_DIFF(end_tag, operand0->buffer.pointer);

	/* Get the length of the second resource template */

	status = acpi_ut_get_resource_end_tag(operand1, &end_tag);
	if (ACPI_FAILURE(status)) {
		return_ACPI_STATUS(status);
	}

	length1 = ACPI_PTR_DIFF(end_tag, operand1->buffer.pointer);

	/* Combine both lengths, minimum size will be 2 for end_tag */

	new_length = length0 + length1 + sizeof(struct aml_resource_end_tag);

	/* Create a new buffer object for the result (with one end_tag) */

	return_desc = acpi_ut_create_buffer_object(new_length);
	if (!return_desc) {
		return_ACPI_STATUS(AE_NO_MEMORY);
	}

	/*
	 * Copy the templates to the new buffer, 0 first, then 1 follows. One
	 * end_tag descriptor is copied from Operand1.
	 */
	new_buf = return_desc->buffer.pointer;
	memcpy(new_buf, operand0->buffer.pointer, length0);
	memcpy(new_buf + length0, operand1->buffer.pointer, length1);

	/* Insert end_tag and set the checksum to zero, means "ignore checksum" */

	new_buf[new_length - 1] = 0;
	new_buf[new_length - 2] = ACPI_RESOURCE_NAME_END_TAG | 1;

	/* Return the completed resource template */

	*actual_return_desc = return_desc;
	return_ACPI_STATUS(AE_OK);
}
