/******************************************************************************
 *
 * Module Name: exconvrt - Object conversion routines
 *
 *****************************************************************************/

/*
 * Copyright (C) 2000 - 2008, 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 <acpi/acpi.h>
#include "accommon.h"
#include "acinterp.h"
#include "amlcode.h"

#define _COMPONENT          ACPI_EXECUTER
ACPI_MODULE_NAME("exconvrt")

/* Local prototypes */
static u32
acpi_ex_convert_to_ascii(acpi_integer integer,
			 u16 base, u8 * string, u8 max_length);

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_integer
 *
 * PARAMETERS:  obj_desc        - Object to be converted. Must be an
 *                                Integer, Buffer, or String
 *              result_desc     - Where the new Integer object is returned
 *              Flags           - Used for string conversion
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Convert an ACPI Object to an integer.
 *
 ******************************************************************************/

acpi_status
acpi_ex_convert_to_integer(union acpi_operand_object *obj_desc,
			   union acpi_operand_object **result_desc, u32 flags)
{
	union acpi_operand_object *return_desc;
	u8 *pointer;
	acpi_integer result;
	u32 i;
	u32 count;
	acpi_status status;

	ACPI_FUNCTION_TRACE_PTR(ex_convert_to_integer, obj_desc);

	switch (obj_desc->common.type) {
	case ACPI_TYPE_INTEGER:

		/* No conversion necessary */

		*result_desc = obj_desc;
		return_ACPI_STATUS(AE_OK);

	case ACPI_TYPE_BUFFER:
	case ACPI_TYPE_STRING:

		/* Note: Takes advantage of common buffer/string fields */

		pointer = obj_desc->buffer.pointer;
		count = obj_desc->buffer.length;
		break;

	default:
		return_ACPI_STATUS(AE_TYPE);
	}

	/*
	 * Convert the buffer/string to an integer. Note that both buffers and
	 * strings are treated as raw data - we don't convert ascii to hex for
	 * strings.
	 *
	 * There are two terminating conditions for the loop:
	 * 1) The size of an integer has been reached, or
	 * 2) The end of the buffer or string has been reached
	 */
	result = 0;

	/* String conversion is different than Buffer conversion */

	switch (obj_desc->common.type) {
	case ACPI_TYPE_STRING:

		/*
		 * Convert string to an integer - for most cases, the string must be
		 * hexadecimal as per the ACPI specification. The only exception (as
		 * of ACPI 3.0) is that the to_integer() operator allows both decimal
		 * and hexadecimal strings (hex prefixed with "0x").
		 */
		status = acpi_ut_strtoul64((char *)pointer, flags, &result);
		if (ACPI_FAILURE(status)) {
			return_ACPI_STATUS(status);
		}
		break;

	case ACPI_TYPE_BUFFER:

		/* Check for zero-length buffer */

		if (!count) {
			return_ACPI_STATUS(AE_AML_BUFFER_LIMIT);
		}

		/* Transfer no more than an integer's worth of data */

		if (count > acpi_gbl_integer_byte_width) {
			count = acpi_gbl_integer_byte_width;
		}

		/*
		 * Convert buffer to an integer - we simply grab enough raw data
		 * from the buffer to fill an integer
		 */
		for (i = 0; i < count; i++) {
			/*
			 * Get next byte and shift it into the Result.
			 * Little endian is used, meaning that the first byte of the buffer
			 * is the LSB of the integer
			 */
			result |= (((acpi_integer) pointer[i]) << (i * 8));
		}
		break;

	default:

		/* No other types can get here */
		break;
	}

	/* Create a new integer */

	return_desc = acpi_ut_create_internal_object(ACPI_TYPE_INTEGER);
	if (!return_desc) {
		return_ACPI_STATUS(AE_NO_MEMORY);
	}

	ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Converted value: %8.8X%8.8X\n",
			  ACPI_FORMAT_UINT64(result)));

	/* Save the Result */

	return_desc->integer.value = result;
	acpi_ex_truncate_for32bit_table(return_desc);
	*result_desc = return_desc;
	return_ACPI_STATUS(AE_OK);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_buffer
 *
 * PARAMETERS:  obj_desc        - Object to be converted. Must be an
 *                                Integer, Buffer, or String
 *              result_desc     - Where the new buffer object is returned
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Convert an ACPI Object to a Buffer
 *
 ******************************************************************************/

acpi_status
acpi_ex_convert_to_buffer(union acpi_operand_object *obj_desc,
			  union acpi_operand_object **result_desc)
{
	union acpi_operand_object *return_desc;
	u8 *new_buf;

	ACPI_FUNCTION_TRACE_PTR(ex_convert_to_buffer, obj_desc);

	switch (obj_desc->common.type) {
	case ACPI_TYPE_BUFFER:

		/* No conversion necessary */

		*result_desc = obj_desc;
		return_ACPI_STATUS(AE_OK);

	case ACPI_TYPE_INTEGER:

		/*
		 * Create a new Buffer object.
		 * Need enough space for one integer
		 */
		return_desc =
		    acpi_ut_create_buffer_object(acpi_gbl_integer_byte_width);
		if (!return_desc) {
			return_ACPI_STATUS(AE_NO_MEMORY);
		}

		/* Copy the integer to the buffer, LSB first */

		new_buf = return_desc->buffer.pointer;
		ACPI_MEMCPY(new_buf,
			    &obj_desc->integer.value,
			    acpi_gbl_integer_byte_width);
		break;

	case ACPI_TYPE_STRING:

		/*
		 * Create a new Buffer object
		 * Size will be the string length
		 *
		 * NOTE: Add one to the string length to include the null terminator.
		 * The ACPI spec is unclear on this subject, but there is existing
		 * ASL/AML code that depends on the null being transferred to the new
		 * buffer.
		 */
		return_desc = acpi_ut_create_buffer_object((acpi_size)
							   obj_desc->string.
							   length + 1);
		if (!return_desc) {
			return_ACPI_STATUS(AE_NO_MEMORY);
		}

		/* Copy the string to the buffer */

		new_buf = return_desc->buffer.pointer;
		ACPI_STRNCPY((char *)new_buf, (char *)obj_desc->string.pointer,
			     obj_desc->string.length);
		break;

	default:
		return_ACPI_STATUS(AE_TYPE);
	}

	/* Mark buffer initialized */

	return_desc->common.flags |= AOPOBJ_DATA_VALID;
	*result_desc = return_desc;
	return_ACPI_STATUS(AE_OK);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_ascii
 *
 * PARAMETERS:  Integer         - Value to be converted
 *              Base            - ACPI_STRING_DECIMAL or ACPI_STRING_HEX
 *              String          - Where the string is returned
 *              data_width      - Size of data item to be converted, in bytes
 *
 * RETURN:      Actual string length
 *
 * DESCRIPTION: Convert an ACPI Integer to a hex or decimal string
 *
 ******************************************************************************/

static u32
acpi_ex_convert_to_ascii(acpi_integer integer,
			 u16 base, u8 * string, u8 data_width)
{
	acpi_integer digit;
	u32 i;
	u32 j;
	u32 k = 0;
	u32 hex_length;
	u32 decimal_length;
	u32 remainder;
	u8 supress_zeros;

	ACPI_FUNCTION_ENTRY();

	switch (base) {
	case 10:

		/* Setup max length for the decimal number */

		switch (data_width) {
		case 1:
			decimal_length = ACPI_MAX8_DECIMAL_DIGITS;
			break;

		case 4:
			decimal_length = ACPI_MAX32_DECIMAL_DIGITS;
			break;

		case 8:
		default:
			decimal_length = ACPI_MAX64_DECIMAL_DIGITS;
			break;
		}

		supress_zeros = TRUE;	/* No leading zeros */
		remainder = 0;

		for (i = decimal_length; i > 0; i--) {

			/* Divide by nth factor of 10 */

			digit = integer;
			for (j = 0; j < i; j++) {
				(void)acpi_ut_short_divide(digit, 10, &digit,
							   &remainder);
			}

			/* Handle leading zeros */

			if (remainder != 0) {
				supress_zeros = FALSE;
			}

			if (!supress_zeros) {
				string[k] = (u8) (ACPI_ASCII_ZERO + remainder);
				k++;
			}
		}
		break;

	case 16:

		/* hex_length: 2 ascii hex chars per data byte */

		hex_length = ACPI_MUL_2(data_width);
		for (i = 0, j = (hex_length - 1); i < hex_length; i++, j--) {

			/* Get one hex digit, most significant digits first */

			string[k] =
			    (u8) acpi_ut_hex_to_ascii_char(integer,
							   ACPI_MUL_4(j));
			k++;
		}
		break;

	default:
		return (0);
	}

	/*
	 * Since leading zeros are suppressed, we must check for the case where
	 * the integer equals 0
	 *
	 * Finally, null terminate the string and return the length
	 */
	if (!k) {
		string[0] = ACPI_ASCII_ZERO;
		k = 1;
	}

	string[k] = 0;
	return ((u32) k);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_string
 *
 * PARAMETERS:  obj_desc        - Object to be converted. Must be an
 *                                Integer, Buffer, or String
 *              result_desc     - Where the string object is returned
 *              Type            - String flags (base and conversion type)
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Convert an ACPI Object to a string
 *
 ******************************************************************************/

acpi_status
acpi_ex_convert_to_string(union acpi_operand_object * obj_desc,
			  union acpi_operand_object ** result_desc, u32 type)
{
	union acpi_operand_object *return_desc;
	u8 *new_buf;
	u32 i;
	u32 string_length = 0;
	u16 base = 16;
	u8 separator = ',';

	ACPI_FUNCTION_TRACE_PTR(ex_convert_to_string, obj_desc);

	switch (obj_desc->common.type) {
	case ACPI_TYPE_STRING:

		/* No conversion necessary */

		*result_desc = obj_desc;
		return_ACPI_STATUS(AE_OK);

	case ACPI_TYPE_INTEGER:

		switch (type) {
		case ACPI_EXPLICIT_CONVERT_DECIMAL:

			/* Make room for maximum decimal number */

			string_length = ACPI_MAX_DECIMAL_DIGITS;
			base = 10;
			break;

		default:

			/* Two hex string characters for each integer byte */

			string_length = ACPI_MUL_2(acpi_gbl_integer_byte_width);
			break;
		}

		/*
		 * Create a new String
		 * Need enough space for one ASCII integer (plus null terminator)
		 */
		return_desc =
		    acpi_ut_create_string_object((acpi_size) string_length);
		if (!return_desc) {
			return_ACPI_STATUS(AE_NO_MEMORY);
		}

		new_buf = return_desc->buffer.pointer;

		/* Convert integer to string */

		string_length =
		    acpi_ex_convert_to_ascii(obj_desc->integer.value, base,
					     new_buf,
					     acpi_gbl_integer_byte_width);

		/* Null terminate at the correct place */

		return_desc->string.length = string_length;
		new_buf[string_length] = 0;
		break;

	case ACPI_TYPE_BUFFER:

		/* Setup string length, base, and separator */

		switch (type) {
		case ACPI_EXPLICIT_CONVERT_DECIMAL:	/* Used by to_decimal_string */
			/*
			 * From ACPI: "If Data is a buffer, it is converted to a string of
			 * decimal values separated by commas."
			 */
			base = 10;

			/*
			 * Calculate the final string length. Individual string values
			 * are variable length (include separator for each)
			 */
			for (i = 0; i < obj_desc->buffer.length; i++) {
				if (obj_desc->buffer.pointer[i] >= 100) {
					string_length += 4;
				} else if (obj_desc->buffer.pointer[i] >= 10) {
					string_length += 3;
				} else {
					string_length += 2;
				}
			}
			break;

		case ACPI_IMPLICIT_CONVERT_HEX:
			/*
			 * From the ACPI spec:
			 *"The entire contents of the buffer are converted to a string of
			 * two-character hexadecimal numbers, each separated by a space."
			 */
			separator = ' ';
			string_length = (obj_desc->buffer.length * 3);
			break;

		case ACPI_EXPLICIT_CONVERT_HEX:	/* Used by to_hex_string */
			/*
			 * From ACPI: "If Data is a buffer, it is converted to a string of
			 * hexadecimal values separated by commas."
			 */
			string_length = (obj_desc->buffer.length * 3);
			break;

		default:
			return_ACPI_STATUS(AE_BAD_PARAMETER);
		}

		/*
		 * Create a new string object and string buffer
		 * (-1 because of extra separator included in string_length from above)
		 * Allow creation of zero-length strings from zero-length buffers.
		 */
		if (string_length) {
			string_length--;
		}

		return_desc = acpi_ut_create_string_object((acpi_size)
							   string_length);
		if (!return_desc) {
			return_ACPI_STATUS(AE_NO_MEMORY);
		}

		new_buf = return_desc->buffer.pointer;

		/*
		 * Convert buffer bytes to hex or decimal values
		 * (separated by commas or spaces)
		 */
		for (i = 0; i < obj_desc->buffer.length; i++) {
			new_buf += acpi_ex_convert_to_ascii((acpi_integer)
							    obj_desc->buffer.
							    pointer[i], base,
							    new_buf, 1);
			*new_buf++ = separator;	/* each separated by a comma or space */
		}

		/*
		 * Null terminate the string
		 * (overwrites final comma/space from above)
		 */
		if (obj_desc->buffer.length) {
			new_buf--;
		}
		*new_buf = 0;
		break;

	default:
		return_ACPI_STATUS(AE_TYPE);
	}

	*result_desc = return_desc;
	return_ACPI_STATUS(AE_OK);
}

/*******************************************************************************
 *
 * FUNCTION:    acpi_ex_convert_to_target_type
 *
 * PARAMETERS:  destination_type    - Current type of the destination
 *              source_desc         - Source object to be converted.
 *              result_desc         - Where the converted object is returned
 *              walk_state          - Current method state
 *
 * RETURN:      Status
 *
 * DESCRIPTION: Implements "implicit conversion" rules for storing an object.
 *
 ******************************************************************************/

acpi_status
acpi_ex_convert_to_target_type(acpi_object_type destination_type,
			       union acpi_operand_object *source_desc,
			       union acpi_operand_object **result_desc,
			       struct acpi_walk_state *walk_state)
{
	acpi_status status = AE_OK;

	ACPI_FUNCTION_TRACE(ex_convert_to_target_type);

	/* Default behavior */

	*result_desc = source_desc;

	/*
	 * If required by the target,
	 * perform implicit conversion on the source before we store it.
	 */
	switch (GET_CURRENT_ARG_TYPE(walk_state->op_info->runtime_args)) {
	case ARGI_SIMPLE_TARGET:
	case ARGI_FIXED_TARGET:
	case ARGI_INTEGER_REF:	/* Handles Increment, Decrement cases */

		switch (destination_type) {
		case ACPI_TYPE_LOCAL_REGION_FIELD:
			/*
			 * Named field can always handle conversions
			 */
			break;

		default:
			/* No conversion allowed for these types */

			if (destination_type != source_desc->common.type) {
				ACPI_DEBUG_PRINT((ACPI_DB_INFO,
						  "Explicit operator, will store (%s) over existing type (%s)\n",
						  acpi_ut_get_object_type_name
						  (source_desc),
						  acpi_ut_get_type_name
						  (destination_type)));
				status = AE_TYPE;
			}
		}
		break;

	case ARGI_TARGETREF:

		switch (destination_type) {
		case ACPI_TYPE_INTEGER:
		case ACPI_TYPE_BUFFER_FIELD:
		case ACPI_TYPE_LOCAL_BANK_FIELD:
		case ACPI_TYPE_LOCAL_INDEX_FIELD:
			/*
			 * These types require an Integer operand. We can convert
			 * a Buffer or a String to an Integer if necessary.
			 */
			status =
			    acpi_ex_convert_to_integer(source_desc, result_desc,
						       16);
			break;

		case ACPI_TYPE_STRING:
			/*
			 * The operand must be a String. We can convert an
			 * Integer or Buffer if necessary
			 */
			status =
			    acpi_ex_convert_to_string(source_desc, result_desc,
						      ACPI_IMPLICIT_CONVERT_HEX);
			break;

		case ACPI_TYPE_BUFFER:
			/*
			 * The operand must be a Buffer. We can convert an
			 * Integer or String if necessary
			 */
			status =
			    acpi_ex_convert_to_buffer(source_desc, result_desc);
			break;

		default:
			ACPI_ERROR((AE_INFO,
				    "Bad destination type during conversion: %X",
				    destination_type));
			status = AE_AML_INTERNAL;
			break;
		}
		break;

	case ARGI_REFERENCE:
		/*
		 * create_xxxx_field cases - we are storing the field object into the name
		 */
		break;

	default:
		ACPI_ERROR((AE_INFO,
			    "Unknown Target type ID 0x%X AmlOpcode %X DestType %s",
			    GET_CURRENT_ARG_TYPE(walk_state->op_info->
						 runtime_args),
			    walk_state->opcode,
			    acpi_ut_get_type_name(destination_type)));
		status = AE_AML_INTERNAL;
	}

	/*
	 * Source-to-Target conversion semantics:
	 *
	 * If conversion to the target type cannot be performed, then simply
	 * overwrite the target with the new object and type.
	 */
	if (status == AE_TYPE) {
		status = AE_OK;
	}

	return_ACPI_STATUS(status);
}
