/*
 * Copyright 2012-15 Advanced Micro Devices, Inc.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a
 * copy of this software and associated documentation files (the "Software"),
 * to deal in the Software without restriction, including without limitation
 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
 * and/or sell copies of the Software, and to permit persons to whom the
 * Software is furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 * OTHER DEALINGS IN THE SOFTWARE.
 *
 * Authors: AMD
 *
 */

#include "dm_services.h"

#include "atom.h"

#include "dc_bios_types.h"
#include "include/gpio_service_interface.h"
#include "include/grph_object_ctrl_defs.h"
#include "include/bios_parser_interface.h"
#include "include/i2caux_interface.h"
#include "include/logger_interface.h"

#include "command_table.h"
#include "bios_parser_helper.h"
#include "command_table_helper.h"
#include "bios_parser.h"
#include "bios_parser_types_internal.h"
#include "bios_parser_interface.h"

#include "bios_parser_common.h"
/* TODO remove - only needed for default i2c speed */
#include "dc.h"

#define THREE_PERCENT_OF_10000 300

#define LAST_RECORD_TYPE 0xff

#define DC_LOGGER \
	bp->base.ctx->logger

/* GUID to validate external display connection info table (aka OPM module) */
static const uint8_t ext_display_connection_guid[NUMBER_OF_UCHAR_FOR_GUID] = {
	0x91, 0x6E, 0x57, 0x09,
	0x3F, 0x6D, 0xD2, 0x11,
	0x39, 0x8E, 0x00, 0xA0,
	0xC9, 0x69, 0x72, 0x3B};

#define DATA_TABLES(table) (bp->master_data_tbl->ListOfDataTables.table)

static void get_atom_data_table_revision(
	ATOM_COMMON_TABLE_HEADER *atom_data_tbl,
	struct atom_data_revision *tbl_revision);
static uint32_t get_dst_number_from_object(struct bios_parser *bp,
	ATOM_OBJECT *object);
static uint32_t get_src_obj_list(struct bios_parser *bp, ATOM_OBJECT *object,
	uint16_t **id_list);
static uint32_t get_dest_obj_list(struct bios_parser *bp,
	ATOM_OBJECT *object, uint16_t **id_list);
static ATOM_OBJECT *get_bios_object(struct bios_parser *bp,
	struct graphics_object_id id);
static enum bp_result get_gpio_i2c_info(struct bios_parser *bp,
	ATOM_I2C_RECORD *record,
	struct graphics_object_i2c_info *info);
static ATOM_HPD_INT_RECORD *get_hpd_record(struct bios_parser *bp,
	ATOM_OBJECT *object);
static struct device_id device_type_from_device_id(uint16_t device_id);
static uint32_t signal_to_ss_id(enum as_signal_type signal);
static uint32_t get_support_mask_for_device_id(struct device_id device_id);
static ATOM_ENCODER_CAP_RECORD_V2 *get_encoder_cap_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object);

#define BIOS_IMAGE_SIZE_OFFSET 2
#define BIOS_IMAGE_SIZE_UNIT 512

/*****************************************************************************/
static bool bios_parser_construct(
	struct bios_parser *bp,
	struct bp_init_data *init,
	enum dce_version dce_version);

static uint8_t bios_parser_get_connectors_number(
	struct dc_bios *dcb);

static enum bp_result bios_parser_get_embedded_panel_info(
	struct dc_bios *dcb,
	struct embedded_panel_info *info);

/*****************************************************************************/

struct dc_bios *bios_parser_create(
	struct bp_init_data *init,
	enum dce_version dce_version)
{
	struct bios_parser *bp = NULL;

	bp = kzalloc(sizeof(struct bios_parser), GFP_KERNEL);
	if (!bp)
		return NULL;

	if (bios_parser_construct(bp, init, dce_version))
		return &bp->base;

	kfree(bp);
	BREAK_TO_DEBUGGER();
	return NULL;
}

static void destruct(struct bios_parser *bp)
{
	kfree(bp->base.bios_local_image);
	kfree(bp->base.integrated_info);
}

static void bios_parser_destroy(struct dc_bios **dcb)
{
	struct bios_parser *bp = BP_FROM_DCB(*dcb);

	if (!bp) {
		BREAK_TO_DEBUGGER();
		return;
	}

	destruct(bp);

	kfree(bp);
	*dcb = NULL;
}

static uint8_t get_number_of_objects(struct bios_parser *bp, uint32_t offset)
{
	ATOM_OBJECT_TABLE *table;

	uint32_t object_table_offset = bp->object_info_tbl_offset + offset;

	table = GET_IMAGE(ATOM_OBJECT_TABLE, object_table_offset);

	if (!table)
		return 0;
	else
		return table->ucNumberOfObjects;
}

static uint8_t bios_parser_get_connectors_number(struct dc_bios *dcb)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	return get_number_of_objects(bp,
		le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset));
}

static struct graphics_object_id bios_parser_get_encoder_id(
	struct dc_bios *dcb,
	uint32_t i)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	struct graphics_object_id object_id = dal_graphics_object_id_init(
		0, ENUM_ID_UNKNOWN, OBJECT_TYPE_UNKNOWN);

	uint32_t encoder_table_offset = bp->object_info_tbl_offset
		+ le16_to_cpu(bp->object_info_tbl.v1_1->usEncoderObjectTableOffset);

	ATOM_OBJECT_TABLE *tbl =
		GET_IMAGE(ATOM_OBJECT_TABLE, encoder_table_offset);

	if (tbl && tbl->ucNumberOfObjects > i) {
		const uint16_t id = le16_to_cpu(tbl->asObjects[i].usObjectID);

		object_id = object_id_from_bios_object_id(id);
	}

	return object_id;
}

static struct graphics_object_id bios_parser_get_connector_id(
	struct dc_bios *dcb,
	uint8_t i)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	struct graphics_object_id object_id = dal_graphics_object_id_init(
		0, ENUM_ID_UNKNOWN, OBJECT_TYPE_UNKNOWN);
	uint16_t id;

	uint32_t connector_table_offset = bp->object_info_tbl_offset
		+ le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset);

	ATOM_OBJECT_TABLE *tbl =
		GET_IMAGE(ATOM_OBJECT_TABLE, connector_table_offset);

	if (!tbl) {
		dm_error("Can't get connector table from atom bios.\n");
		return object_id;
	}

	if (tbl->ucNumberOfObjects <= i) {
		dm_error("Can't find connector id %d in connector table of size %d.\n",
			 i, tbl->ucNumberOfObjects);
		return object_id;
	}

	id = le16_to_cpu(tbl->asObjects[i].usObjectID);
	object_id = object_id_from_bios_object_id(id);
	return object_id;
}

static uint32_t bios_parser_get_dst_number(struct dc_bios *dcb,
	struct graphics_object_id id)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_OBJECT *object = get_bios_object(bp, id);

	return get_dst_number_from_object(bp, object);
}

static enum bp_result bios_parser_get_src_obj(struct dc_bios *dcb,
	struct graphics_object_id object_id, uint32_t index,
	struct graphics_object_id *src_object_id)
{
	uint32_t number;
	uint16_t *id;
	ATOM_OBJECT *object;
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!src_object_id)
		return BP_RESULT_BADINPUT;

	object = get_bios_object(bp, object_id);

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object id */
		return BP_RESULT_BADINPUT;
	}

	number = get_src_obj_list(bp, object, &id);

	if (number <= index)
		return BP_RESULT_BADINPUT;

	*src_object_id = object_id_from_bios_object_id(id[index]);

	return BP_RESULT_OK;
}

static enum bp_result bios_parser_get_dst_obj(struct dc_bios *dcb,
	struct graphics_object_id object_id, uint32_t index,
	struct graphics_object_id *dest_object_id)
{
	uint32_t number;
	uint16_t *id = NULL;
	ATOM_OBJECT *object;
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!dest_object_id)
		return BP_RESULT_BADINPUT;

	object = get_bios_object(bp, object_id);

	number = get_dest_obj_list(bp, object, &id);

	if (number <= index || !id)
		return BP_RESULT_BADINPUT;

	*dest_object_id = object_id_from_bios_object_id(id[index]);

	return BP_RESULT_OK;
}

static enum bp_result bios_parser_get_i2c_info(struct dc_bios *dcb,
	struct graphics_object_id id,
	struct graphics_object_i2c_info *info)
{
	uint32_t offset;
	ATOM_OBJECT *object;
	ATOM_COMMON_RECORD_HEADER *header;
	ATOM_I2C_RECORD *record;
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!info)
		return BP_RESULT_BADINPUT;

	object = get_bios_object(bp, id);

	if (!object)
		return BP_RESULT_BADINPUT;

	offset = le16_to_cpu(object->usRecordOffset)
			+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return BP_RESULT_BADBIOSTABLE;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
			!header->ucRecordSize)
			break;

		if (ATOM_I2C_RECORD_TYPE == header->ucRecordType
			&& sizeof(ATOM_I2C_RECORD) <= header->ucRecordSize) {
			/* get the I2C info */
			record = (ATOM_I2C_RECORD *) header;

			if (get_gpio_i2c_info(bp, record, info) == BP_RESULT_OK)
				return BP_RESULT_OK;
		}

		offset += header->ucRecordSize;
	}

	return BP_RESULT_NORECORD;
}

static enum bp_result get_voltage_ddc_info_v1(uint8_t *i2c_line,
	ATOM_COMMON_TABLE_HEADER *header,
	uint8_t *address)
{
	enum bp_result result = BP_RESULT_NORECORD;
	ATOM_VOLTAGE_OBJECT_INFO *info =
		(ATOM_VOLTAGE_OBJECT_INFO *) address;

	uint8_t *voltage_current_object = (uint8_t *) &info->asVoltageObj[0];

	while ((address + le16_to_cpu(header->usStructureSize)) > voltage_current_object) {
		ATOM_VOLTAGE_OBJECT *object =
			(ATOM_VOLTAGE_OBJECT *) voltage_current_object;

		if ((object->ucVoltageType == SET_VOLTAGE_INIT_MODE) &&
			(object->ucVoltageType &
				VOLTAGE_CONTROLLED_BY_I2C_MASK)) {

			*i2c_line = object->asControl.ucVoltageControlI2cLine
					^ 0x90;
			result = BP_RESULT_OK;
			break;
		}

		voltage_current_object += object->ucSize;
	}
	return result;
}

static enum bp_result get_voltage_ddc_info_v3(uint8_t *i2c_line,
	uint32_t index,
	ATOM_COMMON_TABLE_HEADER *header,
	uint8_t *address)
{
	enum bp_result result = BP_RESULT_NORECORD;
	ATOM_VOLTAGE_OBJECT_INFO_V3_1 *info =
		(ATOM_VOLTAGE_OBJECT_INFO_V3_1 *) address;

	uint8_t *voltage_current_object =
		(uint8_t *) (&(info->asVoltageObj[0]));

	while ((address + le16_to_cpu(header->usStructureSize)) > voltage_current_object) {
		ATOM_I2C_VOLTAGE_OBJECT_V3 *object =
			(ATOM_I2C_VOLTAGE_OBJECT_V3 *) voltage_current_object;

		if (object->sHeader.ucVoltageMode ==
			ATOM_INIT_VOLTAGE_REGULATOR) {
			if (object->sHeader.ucVoltageType == index) {
				*i2c_line = object->ucVoltageControlI2cLine
						^ 0x90;
				result = BP_RESULT_OK;
				break;
			}
		}

		voltage_current_object += le16_to_cpu(object->sHeader.usSize);
	}
	return result;
}

static enum bp_result bios_parser_get_thermal_ddc_info(
	struct dc_bios *dcb,
	uint32_t i2c_channel_id,
	struct graphics_object_i2c_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_I2C_ID_CONFIG_ACCESS *config;
	ATOM_I2C_RECORD record;

	if (!info)
		return BP_RESULT_BADINPUT;

	config = (ATOM_I2C_ID_CONFIG_ACCESS *) &i2c_channel_id;

	record.sucI2cId.bfHW_Capable = config->sbfAccess.bfHW_Capable;
	record.sucI2cId.bfI2C_LineMux = config->sbfAccess.bfI2C_LineMux;
	record.sucI2cId.bfHW_EngineID = config->sbfAccess.bfHW_EngineID;

	return get_gpio_i2c_info(bp, &record, info);
}

static enum bp_result bios_parser_get_voltage_ddc_info(struct dc_bios *dcb,
	uint32_t index,
	struct graphics_object_i2c_info *info)
{
	uint8_t i2c_line = 0;
	enum bp_result result = BP_RESULT_NORECORD;
	uint8_t *voltage_info_address;
	ATOM_COMMON_TABLE_HEADER *header;
	struct atom_data_revision revision = {0};
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!DATA_TABLES(VoltageObjectInfo))
		return result;

	voltage_info_address = bios_get_image(&bp->base, DATA_TABLES(VoltageObjectInfo), sizeof(ATOM_COMMON_TABLE_HEADER));

	header = (ATOM_COMMON_TABLE_HEADER *) voltage_info_address;

	get_atom_data_table_revision(header, &revision);

	switch (revision.major) {
	case 1:
	case 2:
		result = get_voltage_ddc_info_v1(&i2c_line, header,
			voltage_info_address);
		break;
	case 3:
		if (revision.minor != 1)
			break;
		result = get_voltage_ddc_info_v3(&i2c_line, index, header,
			voltage_info_address);
		break;
	}

	if (result == BP_RESULT_OK)
		result = bios_parser_get_thermal_ddc_info(dcb,
			i2c_line, info);

	return result;
}

/* TODO: temporary commented out to suppress 'defined but not used' warning */
#if 0
static enum bp_result bios_parser_get_ddc_info_for_i2c_line(
	struct bios_parser *bp,
	uint8_t i2c_line, struct graphics_object_i2c_info *info)
{
	uint32_t offset;
	ATOM_OBJECT *object;
	ATOM_OBJECT_TABLE *table;
	uint32_t i;

	if (!info)
		return BP_RESULT_BADINPUT;

	offset = le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset);

	offset += bp->object_info_tbl_offset;

	table = GET_IMAGE(ATOM_OBJECT_TABLE, offset);

	if (!table)
		return BP_RESULT_BADBIOSTABLE;

	for (i = 0; i < table->ucNumberOfObjects; i++) {
		object = &table->asObjects[i];

		if (!object) {
			BREAK_TO_DEBUGGER(); /* Invalid object id */
			return BP_RESULT_BADINPUT;
		}

		offset = le16_to_cpu(object->usRecordOffset)
				+ bp->object_info_tbl_offset;

		for (;;) {
			ATOM_COMMON_RECORD_HEADER *header =
				GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

			if (!header)
				return BP_RESULT_BADBIOSTABLE;

			offset += header->ucRecordSize;

			if (LAST_RECORD_TYPE == header->ucRecordType ||
				!header->ucRecordSize)
				break;

			if (ATOM_I2C_RECORD_TYPE == header->ucRecordType
				&& sizeof(ATOM_I2C_RECORD) <=
				header->ucRecordSize) {
				ATOM_I2C_RECORD *record =
					(ATOM_I2C_RECORD *) header;

				if (i2c_line != record->sucI2cId.bfI2C_LineMux)
					continue;

				/* get the I2C info */
				if (get_gpio_i2c_info(bp, record, info) ==
					BP_RESULT_OK)
					return BP_RESULT_OK;
			}
		}
	}

	return BP_RESULT_NORECORD;
}
#endif

static enum bp_result bios_parser_get_hpd_info(struct dc_bios *dcb,
	struct graphics_object_id id,
	struct graphics_object_hpd_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_OBJECT *object;
	ATOM_HPD_INT_RECORD *record = NULL;

	if (!info)
		return BP_RESULT_BADINPUT;

	object = get_bios_object(bp, id);

	if (!object)
		return BP_RESULT_BADINPUT;

	record = get_hpd_record(bp, object);

	if (record != NULL) {
		info->hpd_int_gpio_uid = record->ucHPDIntGPIOID;
		info->hpd_active = record->ucPlugged_PinState;
		return BP_RESULT_OK;
	}

	return BP_RESULT_NORECORD;
}

static enum bp_result bios_parser_get_device_tag_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object,
	ATOM_CONNECTOR_DEVICE_TAG_RECORD **record)
{
	ATOM_COMMON_RECORD_HEADER *header;
	uint32_t offset;

	offset = le16_to_cpu(object->usRecordOffset)
			+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return BP_RESULT_BADBIOSTABLE;

		offset += header->ucRecordSize;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
			!header->ucRecordSize)
			break;

		if (ATOM_CONNECTOR_DEVICE_TAG_RECORD_TYPE !=
			header->ucRecordType)
			continue;

		if (sizeof(ATOM_CONNECTOR_DEVICE_TAG) > header->ucRecordSize)
			continue;

		*record = (ATOM_CONNECTOR_DEVICE_TAG_RECORD *) header;
		return BP_RESULT_OK;
	}

	return BP_RESULT_NORECORD;
}

static enum bp_result bios_parser_get_device_tag(
	struct dc_bios *dcb,
	struct graphics_object_id connector_object_id,
	uint32_t device_tag_index,
	struct connector_device_tag_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_OBJECT *object;
	ATOM_CONNECTOR_DEVICE_TAG_RECORD *record = NULL;
	ATOM_CONNECTOR_DEVICE_TAG *device_tag;

	if (!info)
		return BP_RESULT_BADINPUT;

	/* getBiosObject will return MXM object */
	object = get_bios_object(bp, connector_object_id);

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object id */
		return BP_RESULT_BADINPUT;
	}

	if (bios_parser_get_device_tag_record(bp, object, &record)
		!= BP_RESULT_OK)
		return BP_RESULT_NORECORD;

	if (device_tag_index >= record->ucNumberOfDevice)
		return BP_RESULT_NORECORD;

	device_tag = &record->asDeviceTag[device_tag_index];

	info->acpi_device = le32_to_cpu(device_tag->ulACPIDeviceEnum);
	info->dev_id =
		device_type_from_device_id(le16_to_cpu(device_tag->usDeviceID));

	return BP_RESULT_OK;
}

static enum bp_result get_firmware_info_v1_4(
	struct bios_parser *bp,
	struct dc_firmware_info *info);
static enum bp_result get_firmware_info_v2_1(
	struct bios_parser *bp,
	struct dc_firmware_info *info);
static enum bp_result get_firmware_info_v2_2(
	struct bios_parser *bp,
	struct dc_firmware_info *info);

static enum bp_result bios_parser_get_firmware_info(
	struct dc_bios *dcb,
	struct dc_firmware_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	enum bp_result result = BP_RESULT_BADBIOSTABLE;
	ATOM_COMMON_TABLE_HEADER *header;
	struct atom_data_revision revision;

	if (info && DATA_TABLES(FirmwareInfo)) {
		header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER,
			DATA_TABLES(FirmwareInfo));
		get_atom_data_table_revision(header, &revision);
		switch (revision.major) {
		case 1:
			switch (revision.minor) {
			case 4:
				result = get_firmware_info_v1_4(bp, info);
				break;
			default:
				break;
			}
			break;

		case 2:
			switch (revision.minor) {
			case 1:
				result = get_firmware_info_v2_1(bp, info);
				break;
			case 2:
				result = get_firmware_info_v2_2(bp, info);
				break;
			default:
				break;
			}
			break;
		default:
			break;
		}
	}

	return result;
}

static enum bp_result get_firmware_info_v1_4(
	struct bios_parser *bp,
	struct dc_firmware_info *info)
{
	ATOM_FIRMWARE_INFO_V1_4 *firmware_info =
		GET_IMAGE(ATOM_FIRMWARE_INFO_V1_4,
			DATA_TABLES(FirmwareInfo));

	if (!info)
		return BP_RESULT_BADINPUT;

	if (!firmware_info)
		return BP_RESULT_BADBIOSTABLE;

	memset(info, 0, sizeof(*info));

	/* Pixel clock pll information. We need to convert from 10KHz units into
	 * KHz units */
	info->pll_info.crystal_frequency =
		le16_to_cpu(firmware_info->usReferenceClock) * 10;
	info->pll_info.min_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmware_info->usMinPixelClockPLL_Input) * 10;
	info->pll_info.max_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmware_info->usMaxPixelClockPLL_Input) * 10;
	info->pll_info.min_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmware_info->ulMinPixelClockPLL_Output) * 10;
	info->pll_info.max_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmware_info->ulMaxPixelClockPLL_Output) * 10;

	if (firmware_info->usFirmwareCapability.sbfAccess.MemoryClockSS_Support)
		/* Since there is no information on the SS, report conservative
		 * value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.memory_clk_ss_percentage = THREE_PERCENT_OF_10000;

	if (firmware_info->usFirmwareCapability.sbfAccess.EngineClockSS_Support)
		/* Since there is no information on the SS,report conservative
		 * value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.engine_clk_ss_percentage = THREE_PERCENT_OF_10000;

	return BP_RESULT_OK;
}

static enum bp_result get_ss_info_v3_1(
	struct bios_parser *bp,
	uint32_t id,
	uint32_t index,
	struct spread_spectrum_info *ss_info);

static enum bp_result get_firmware_info_v2_1(
	struct bios_parser *bp,
	struct dc_firmware_info *info)
{
	ATOM_FIRMWARE_INFO_V2_1 *firmwareInfo =
		GET_IMAGE(ATOM_FIRMWARE_INFO_V2_1, DATA_TABLES(FirmwareInfo));
	struct spread_spectrum_info internalSS;
	uint32_t index;

	if (!info)
		return BP_RESULT_BADINPUT;

	if (!firmwareInfo)
		return BP_RESULT_BADBIOSTABLE;

	memset(info, 0, sizeof(*info));

	/* Pixel clock pll information. We need to convert from 10KHz units into
	 * KHz units */
	info->pll_info.crystal_frequency =
		le16_to_cpu(firmwareInfo->usCoreReferenceClock) * 10;
	info->pll_info.min_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmwareInfo->usMinPixelClockPLL_Input) * 10;
	info->pll_info.max_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmwareInfo->usMaxPixelClockPLL_Input) * 10;
	info->pll_info.min_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmwareInfo->ulMinPixelClockPLL_Output) * 10;
	info->pll_info.max_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmwareInfo->ulMaxPixelClockPLL_Output) * 10;
	info->default_display_engine_pll_frequency =
		le32_to_cpu(firmwareInfo->ulDefaultDispEngineClkFreq) * 10;
	info->external_clock_source_frequency_for_dp =
		le16_to_cpu(firmwareInfo->usUniphyDPModeExtClkFreq) * 10;
	info->min_allowed_bl_level = firmwareInfo->ucMinAllowedBL_Level;

	/* There should be only one entry in the SS info table for Memory Clock
	 */
	index = 0;
	if (firmwareInfo->usFirmwareCapability.sbfAccess.MemoryClockSS_Support)
		/* Since there is no information for external SS, report
		 *  conservative value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.memory_clk_ss_percentage = THREE_PERCENT_OF_10000;
	else if (get_ss_info_v3_1(bp,
		ASIC_INTERNAL_MEMORY_SS, index, &internalSS) == BP_RESULT_OK) {
		if (internalSS.spread_spectrum_percentage) {
			info->feature.memory_clk_ss_percentage =
				internalSS.spread_spectrum_percentage;
			if (internalSS.type.CENTER_MODE) {
				/* if it is centermode, the exact SS Percentage
				 * will be round up of half of the percentage
				 * reported in the SS table */
				++info->feature.memory_clk_ss_percentage;
				info->feature.memory_clk_ss_percentage /= 2;
			}
		}
	}

	/* There should be only one entry in the SS info table for Engine Clock
	 */
	index = 1;
	if (firmwareInfo->usFirmwareCapability.sbfAccess.EngineClockSS_Support)
		/* Since there is no information for external SS, report
		 * conservative value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.engine_clk_ss_percentage = THREE_PERCENT_OF_10000;
	else if (get_ss_info_v3_1(bp,
		ASIC_INTERNAL_ENGINE_SS, index, &internalSS) == BP_RESULT_OK) {
		if (internalSS.spread_spectrum_percentage) {
			info->feature.engine_clk_ss_percentage =
				internalSS.spread_spectrum_percentage;
			if (internalSS.type.CENTER_MODE) {
				/* if it is centermode, the exact SS Percentage
				 * will be round up of half of the percentage
				 * reported in the SS table */
				++info->feature.engine_clk_ss_percentage;
				info->feature.engine_clk_ss_percentage /= 2;
			}
		}
	}

	return BP_RESULT_OK;
}

static enum bp_result get_firmware_info_v2_2(
	struct bios_parser *bp,
	struct dc_firmware_info *info)
{
	ATOM_FIRMWARE_INFO_V2_2 *firmware_info;
	struct spread_spectrum_info internal_ss;
	uint32_t index;

	if (!info)
		return BP_RESULT_BADINPUT;

	firmware_info = GET_IMAGE(ATOM_FIRMWARE_INFO_V2_2,
		DATA_TABLES(FirmwareInfo));

	if (!firmware_info)
		return BP_RESULT_BADBIOSTABLE;

	memset(info, 0, sizeof(*info));

	/* Pixel clock pll information. We need to convert from 10KHz units into
	 * KHz units */
	info->pll_info.crystal_frequency =
		le16_to_cpu(firmware_info->usCoreReferenceClock) * 10;
	info->pll_info.min_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmware_info->usMinPixelClockPLL_Input) * 10;
	info->pll_info.max_input_pxl_clk_pll_frequency =
		le16_to_cpu(firmware_info->usMaxPixelClockPLL_Input) * 10;
	info->pll_info.min_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmware_info->ulMinPixelClockPLL_Output) * 10;
	info->pll_info.max_output_pxl_clk_pll_frequency =
		le32_to_cpu(firmware_info->ulMaxPixelClockPLL_Output) * 10;
	info->default_display_engine_pll_frequency =
		le32_to_cpu(firmware_info->ulDefaultDispEngineClkFreq) * 10;
	info->external_clock_source_frequency_for_dp =
		le16_to_cpu(firmware_info->usUniphyDPModeExtClkFreq) * 10;

	/* There should be only one entry in the SS info table for Memory Clock
	 */
	index = 0;
	if (firmware_info->usFirmwareCapability.sbfAccess.MemoryClockSS_Support)
		/* Since there is no information for external SS, report
		 *  conservative value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.memory_clk_ss_percentage = THREE_PERCENT_OF_10000;
	else if (get_ss_info_v3_1(bp,
			ASIC_INTERNAL_MEMORY_SS, index, &internal_ss) == BP_RESULT_OK) {
		if (internal_ss.spread_spectrum_percentage) {
			info->feature.memory_clk_ss_percentage =
					internal_ss.spread_spectrum_percentage;
			if (internal_ss.type.CENTER_MODE) {
				/* if it is centermode, the exact SS Percentage
				 * will be round up of half of the percentage
				 * reported in the SS table */
				++info->feature.memory_clk_ss_percentage;
				info->feature.memory_clk_ss_percentage /= 2;
			}
		}
	}

	/* There should be only one entry in the SS info table for Engine Clock
	 */
	index = 1;
	if (firmware_info->usFirmwareCapability.sbfAccess.EngineClockSS_Support)
		/* Since there is no information for external SS, report
		 * conservative value 3% for bandwidth calculation */
		/* unit of 0.01% */
		info->feature.engine_clk_ss_percentage = THREE_PERCENT_OF_10000;
	else if (get_ss_info_v3_1(bp,
			ASIC_INTERNAL_ENGINE_SS, index, &internal_ss) == BP_RESULT_OK) {
		if (internal_ss.spread_spectrum_percentage) {
			info->feature.engine_clk_ss_percentage =
					internal_ss.spread_spectrum_percentage;
			if (internal_ss.type.CENTER_MODE) {
				/* if it is centermode, the exact SS Percentage
				 * will be round up of half of the percentage
				 * reported in the SS table */
				++info->feature.engine_clk_ss_percentage;
				info->feature.engine_clk_ss_percentage /= 2;
			}
		}
	}

	/* Remote Display */
	info->remote_display_config = firmware_info->ucRemoteDisplayConfig;

	/* Is allowed minimum BL level */
	info->min_allowed_bl_level = firmware_info->ucMinAllowedBL_Level;
	/* Used starting from CI */
	info->smu_gpu_pll_output_freq =
			(uint32_t) (le32_to_cpu(firmware_info->ulGPUPLL_OutputFreq) * 10);

	return BP_RESULT_OK;
}

static enum bp_result get_ss_info_v3_1(
	struct bios_parser *bp,
	uint32_t id,
	uint32_t index,
	struct spread_spectrum_info *ss_info)
{
	ATOM_ASIC_INTERNAL_SS_INFO_V3 *ss_table_header_include;
	ATOM_ASIC_SS_ASSIGNMENT_V3 *tbl;
	uint32_t table_size;
	uint32_t i;
	uint32_t table_index = 0;

	if (!ss_info)
		return BP_RESULT_BADINPUT;

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		return BP_RESULT_UNSUPPORTED;

	ss_table_header_include = GET_IMAGE(ATOM_ASIC_INTERNAL_SS_INFO_V3,
		DATA_TABLES(ASIC_InternalSS_Info));
	table_size =
		(le16_to_cpu(ss_table_header_include->sHeader.usStructureSize)
				- sizeof(ATOM_COMMON_TABLE_HEADER))
				/ sizeof(ATOM_ASIC_SS_ASSIGNMENT_V3);

	tbl = (ATOM_ASIC_SS_ASSIGNMENT_V3 *)
				&ss_table_header_include->asSpreadSpectrum[0];

	memset(ss_info, 0, sizeof(struct spread_spectrum_info));

	for (i = 0; i < table_size; i++) {
		if (tbl[i].ucClockIndication != (uint8_t) id)
			continue;

		if (table_index != index) {
			table_index++;
			continue;
		}
		/* VBIOS introduced new defines for Version 3, same values as
		 *  before, so now use these new ones for Version 3.
		 * Shouldn't affect field VBIOS's V3 as define values are still
		 *  same.
		 * #define SS_MODE_V3_CENTRE_SPREAD_MASK                0x01
		 * #define SS_MODE_V3_EXTERNAL_SS_MASK                  0x02

		 * Old VBIOS defines:
		 * #define ATOM_SS_CENTRE_SPREAD_MODE_MASK        0x00000001
		 * #define ATOM_EXTERNAL_SS_MASK                  0x00000002
		 */

		if (SS_MODE_V3_EXTERNAL_SS_MASK & tbl[i].ucSpreadSpectrumMode)
			ss_info->type.EXTERNAL = true;

		if (SS_MODE_V3_CENTRE_SPREAD_MASK & tbl[i].ucSpreadSpectrumMode)
			ss_info->type.CENTER_MODE = true;

		/* Older VBIOS (in field) always provides SS percentage in 0.01%
		 * units set Divider to 100 */
		ss_info->spread_percentage_divider = 100;

		/* #define SS_MODE_V3_PERCENTAGE_DIV_BY_1000_MASK 0x10 */
		if (SS_MODE_V3_PERCENTAGE_DIV_BY_1000_MASK
				& tbl[i].ucSpreadSpectrumMode)
			ss_info->spread_percentage_divider = 1000;

		ss_info->type.STEP_AND_DELAY_INFO = false;
		/* convert [10KHz] into [KHz] */
		ss_info->target_clock_range =
				le32_to_cpu(tbl[i].ulTargetClockRange) * 10;
		ss_info->spread_spectrum_percentage =
				(uint32_t)le16_to_cpu(tbl[i].usSpreadSpectrumPercentage);
		ss_info->spread_spectrum_range =
				(uint32_t)(le16_to_cpu(tbl[i].usSpreadRateIn10Hz) * 10);

		return BP_RESULT_OK;
	}
	return BP_RESULT_NORECORD;
}

static enum bp_result bios_parser_transmitter_control(
	struct dc_bios *dcb,
	struct bp_transmitter_control *cntl)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.transmitter_control)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.transmitter_control(bp, cntl);
}

static enum bp_result bios_parser_encoder_control(
	struct dc_bios *dcb,
	struct bp_encoder_control *cntl)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.dig_encoder_control)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.dig_encoder_control(bp, cntl);
}

static enum bp_result bios_parser_adjust_pixel_clock(
	struct dc_bios *dcb,
	struct bp_adjust_pixel_clock_parameters *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.adjust_display_pll)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.adjust_display_pll(bp, bp_params);
}

static enum bp_result bios_parser_set_pixel_clock(
	struct dc_bios *dcb,
	struct bp_pixel_clock_parameters *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.set_pixel_clock)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.set_pixel_clock(bp, bp_params);
}

static enum bp_result bios_parser_set_dce_clock(
	struct dc_bios *dcb,
	struct bp_set_dce_clock_parameters *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.set_dce_clock)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.set_dce_clock(bp, bp_params);
}

static enum bp_result bios_parser_enable_spread_spectrum_on_ppll(
	struct dc_bios *dcb,
	struct bp_spread_spectrum_parameters *bp_params,
	bool enable)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.enable_spread_spectrum_on_ppll)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.enable_spread_spectrum_on_ppll(
			bp, bp_params, enable);

}

static enum bp_result bios_parser_program_crtc_timing(
	struct dc_bios *dcb,
	struct bp_hw_crtc_timing_parameters *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.set_crtc_timing)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.set_crtc_timing(bp, bp_params);
}

static enum bp_result bios_parser_program_display_engine_pll(
	struct dc_bios *dcb,
	struct bp_pixel_clock_parameters *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.program_clock)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.program_clock(bp, bp_params);

}


static enum bp_result bios_parser_enable_crtc(
	struct dc_bios *dcb,
	enum controller_id id,
	bool enable)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.enable_crtc)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.enable_crtc(bp, id, enable);
}

static enum bp_result bios_parser_crtc_source_select(
	struct dc_bios *dcb,
	struct bp_crtc_source_select *bp_params)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.select_crtc_source)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.select_crtc_source(bp, bp_params);
}

static enum bp_result bios_parser_enable_disp_power_gating(
	struct dc_bios *dcb,
	enum controller_id controller_id,
	enum bp_pipe_control_action action)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	if (!bp->cmd_tbl.enable_disp_power_gating)
		return BP_RESULT_FAILURE;

	return bp->cmd_tbl.enable_disp_power_gating(bp, controller_id,
		action);
}

static bool bios_parser_is_device_id_supported(
	struct dc_bios *dcb,
	struct device_id id)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	uint32_t mask = get_support_mask_for_device_id(id);

	return (le16_to_cpu(bp->object_info_tbl.v1_1->usDeviceSupport) & mask) != 0;
}

static enum bp_result bios_parser_crt_control(
	struct dc_bios *dcb,
	enum engine_id engine_id,
	bool enable,
	uint32_t pixel_clock)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	uint8_t standard;

	if (!bp->cmd_tbl.dac1_encoder_control &&
		engine_id == ENGINE_ID_DACA)
		return BP_RESULT_FAILURE;
	if (!bp->cmd_tbl.dac2_encoder_control &&
		engine_id == ENGINE_ID_DACB)
		return BP_RESULT_FAILURE;
	/* validate params */
	switch (engine_id) {
	case ENGINE_ID_DACA:
	case ENGINE_ID_DACB:
		break;
	default:
		/* unsupported engine */
		return BP_RESULT_FAILURE;
	}

	standard = ATOM_DAC1_PS2; /* == ATOM_DAC2_PS2 */

	if (enable) {
		if (engine_id == ENGINE_ID_DACA) {
			bp->cmd_tbl.dac1_encoder_control(bp, enable,
				pixel_clock, standard);
			if (bp->cmd_tbl.dac1_output_control != NULL)
				bp->cmd_tbl.dac1_output_control(bp, enable);
		} else {
			bp->cmd_tbl.dac2_encoder_control(bp, enable,
				pixel_clock, standard);
			if (bp->cmd_tbl.dac2_output_control != NULL)
				bp->cmd_tbl.dac2_output_control(bp, enable);
		}
	} else {
		if (engine_id == ENGINE_ID_DACA) {
			if (bp->cmd_tbl.dac1_output_control != NULL)
				bp->cmd_tbl.dac1_output_control(bp, enable);
			bp->cmd_tbl.dac1_encoder_control(bp, enable,
				pixel_clock, standard);
		} else {
			if (bp->cmd_tbl.dac2_output_control != NULL)
				bp->cmd_tbl.dac2_output_control(bp, enable);
			bp->cmd_tbl.dac2_encoder_control(bp, enable,
				pixel_clock, standard);
		}
	}

	return BP_RESULT_OK;
}

static ATOM_HPD_INT_RECORD *get_hpd_record(struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	ATOM_COMMON_RECORD_HEADER *header;
	uint32_t offset;

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object */
		return NULL;
	}

	offset = le16_to_cpu(object->usRecordOffset)
			+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return NULL;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
			!header->ucRecordSize)
			break;

		if (ATOM_HPD_INT_RECORD_TYPE == header->ucRecordType
			&& sizeof(ATOM_HPD_INT_RECORD) <= header->ucRecordSize)
			return (ATOM_HPD_INT_RECORD *) header;

		offset += header->ucRecordSize;
	}

	return NULL;
}

/**
 * Get I2C information of input object id
 *
 * search all records to find the ATOM_I2C_RECORD_TYPE record IR
 */
static ATOM_I2C_RECORD *get_i2c_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	uint32_t offset;
	ATOM_COMMON_RECORD_HEADER *record_header;

	if (!object) {
		BREAK_TO_DEBUGGER();
		/* Invalid object */
		return NULL;
	}

	offset = le16_to_cpu(object->usRecordOffset)
			+ bp->object_info_tbl_offset;

	for (;;) {
		record_header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!record_header)
			return NULL;

		if (LAST_RECORD_TYPE == record_header->ucRecordType ||
			0 == record_header->ucRecordSize)
			break;

		if (ATOM_I2C_RECORD_TYPE == record_header->ucRecordType &&
			sizeof(ATOM_I2C_RECORD) <=
			record_header->ucRecordSize) {
			return (ATOM_I2C_RECORD *)record_header;
		}

		offset += record_header->ucRecordSize;
	}

	return NULL;
}

static enum bp_result get_ss_info_from_ss_info_table(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *ss_info);
static enum bp_result get_ss_info_from_tbl(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *ss_info);
/**
 * bios_parser_get_spread_spectrum_info
 * Get spread spectrum information from the ASIC_InternalSS_Info(ver 2.1 or
 * ver 3.1) or SS_Info table from the VBIOS. Currently ASIC_InternalSS_Info
 * ver 2.1 can co-exist with SS_Info table. Expect ASIC_InternalSS_Info ver 3.1,
 * there is only one entry for each signal /ss id.  However, there is
 * no planning of supporting multiple spread Sprectum entry for EverGreen
 * @param [in] this
 * @param [in] signal, ASSignalType to be converted to info index
 * @param [in] index, number of entries that match the converted info index
 * @param [out] ss_info, sprectrum information structure,
 * @return Bios parser result code
 */
static enum bp_result bios_parser_get_spread_spectrum_info(
	struct dc_bios *dcb,
	enum as_signal_type signal,
	uint32_t index,
	struct spread_spectrum_info *ss_info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	enum bp_result result = BP_RESULT_UNSUPPORTED;
	uint32_t clk_id_ss = 0;
	ATOM_COMMON_TABLE_HEADER *header;
	struct atom_data_revision tbl_revision;

	if (!ss_info) /* check for bad input */
		return BP_RESULT_BADINPUT;
	/* signal translation */
	clk_id_ss = signal_to_ss_id(signal);

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		if (!index)
			return get_ss_info_from_ss_info_table(bp, clk_id_ss,
				ss_info);

	header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER,
		DATA_TABLES(ASIC_InternalSS_Info));
	get_atom_data_table_revision(header, &tbl_revision);

	switch (tbl_revision.major) {
	case 2:
		switch (tbl_revision.minor) {
		case 1:
			/* there can not be more then one entry for Internal
			 * SS Info table version 2.1 */
			if (!index)
				return get_ss_info_from_tbl(bp, clk_id_ss,
						ss_info);
			break;
		default:
			break;
		}
		break;

	case 3:
		switch (tbl_revision.minor) {
		case 1:
			return get_ss_info_v3_1(bp, clk_id_ss, index, ss_info);
		default:
			break;
		}
		break;
	default:
		break;
	}
	/* there can not be more then one entry for SS Info table */
	return result;
}

static enum bp_result get_ss_info_from_internal_ss_info_tbl_V2_1(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *info);

/**
 * get_ss_info_from_table
 * Get spread sprectrum information from the ASIC_InternalSS_Info Ver 2.1 or
 * SS_Info table from the VBIOS
 * There can not be more than 1 entry for  ASIC_InternalSS_Info Ver 2.1 or
 * SS_Info.
 *
 * @param this
 * @param id, spread sprectrum info index
 * @param pSSinfo, sprectrum information structure,
 * @return Bios parser result code
 */
static enum bp_result get_ss_info_from_tbl(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *ss_info)
{
	if (!ss_info) /* check for bad input, if ss_info is not NULL */
		return BP_RESULT_BADINPUT;
	/* for SS_Info table only support DP and LVDS */
	if (id == ASIC_INTERNAL_SS_ON_DP || id == ASIC_INTERNAL_SS_ON_LVDS)
		return get_ss_info_from_ss_info_table(bp, id, ss_info);
	else
		return get_ss_info_from_internal_ss_info_tbl_V2_1(bp, id,
			ss_info);
}

/**
 * get_ss_info_from_internal_ss_info_tbl_V2_1
 * Get spread sprectrum information from the ASIC_InternalSS_Info table Ver 2.1
 * from the VBIOS
 * There will not be multiple entry for Ver 2.1
 *
 * @param id, spread sprectrum info index
 * @param pSSinfo, sprectrum information structure,
 * @return Bios parser result code
 */
static enum bp_result get_ss_info_from_internal_ss_info_tbl_V2_1(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *info)
{
	enum bp_result result = BP_RESULT_UNSUPPORTED;
	ATOM_ASIC_INTERNAL_SS_INFO_V2 *header;
	ATOM_ASIC_SS_ASSIGNMENT_V2 *tbl;
	uint32_t tbl_size, i;

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		return result;

	header = GET_IMAGE(ATOM_ASIC_INTERNAL_SS_INFO_V2,
		DATA_TABLES(ASIC_InternalSS_Info));

	memset(info, 0, sizeof(struct spread_spectrum_info));

	tbl_size = (le16_to_cpu(header->sHeader.usStructureSize)
			- sizeof(ATOM_COMMON_TABLE_HEADER))
					/ sizeof(ATOM_ASIC_SS_ASSIGNMENT_V2);

	tbl = (ATOM_ASIC_SS_ASSIGNMENT_V2 *)
					&(header->asSpreadSpectrum[0]);
	for (i = 0; i < tbl_size; i++) {
		result = BP_RESULT_NORECORD;

		if (tbl[i].ucClockIndication != (uint8_t)id)
			continue;

		if (ATOM_EXTERNAL_SS_MASK
			& tbl[i].ucSpreadSpectrumMode) {
			info->type.EXTERNAL = true;
		}
		if (ATOM_SS_CENTRE_SPREAD_MODE_MASK
			& tbl[i].ucSpreadSpectrumMode) {
			info->type.CENTER_MODE = true;
		}
		info->type.STEP_AND_DELAY_INFO = false;
		/* convert [10KHz] into [KHz] */
		info->target_clock_range =
			le32_to_cpu(tbl[i].ulTargetClockRange) * 10;
		info->spread_spectrum_percentage =
			(uint32_t)le16_to_cpu(tbl[i].usSpreadSpectrumPercentage);
		info->spread_spectrum_range =
			(uint32_t)(le16_to_cpu(tbl[i].usSpreadRateIn10Hz) * 10);
		result = BP_RESULT_OK;
		break;
	}

	return result;

}

/**
 * get_ss_info_from_ss_info_table
 * Get spread sprectrum information from the SS_Info table from the VBIOS
 * if the pointer to info is NULL, indicate the caller what to know the number
 * of entries that matches the id
 * for, the SS_Info table, there should not be more than 1 entry match.
 *
 * @param [in] id, spread sprectrum id
 * @param [out] pSSinfo, sprectrum information structure,
 * @return Bios parser result code
 */
static enum bp_result get_ss_info_from_ss_info_table(
	struct bios_parser *bp,
	uint32_t id,
	struct spread_spectrum_info *ss_info)
{
	enum bp_result result = BP_RESULT_UNSUPPORTED;
	ATOM_SPREAD_SPECTRUM_INFO *tbl;
	ATOM_COMMON_TABLE_HEADER *header;
	uint32_t table_size;
	uint32_t i;
	uint32_t id_local = SS_ID_UNKNOWN;
	struct atom_data_revision revision;

	/* exist of the SS_Info table */
	/* check for bad input, pSSinfo can not be NULL */
	if (!DATA_TABLES(SS_Info) || !ss_info)
		return result;

	header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER, DATA_TABLES(SS_Info));
	get_atom_data_table_revision(header, &revision);

	tbl = GET_IMAGE(ATOM_SPREAD_SPECTRUM_INFO, DATA_TABLES(SS_Info));

	if (1 != revision.major || 2 > revision.minor)
		return result;

	/* have to convert from Internal_SS format to SS_Info format */
	switch (id) {
	case ASIC_INTERNAL_SS_ON_DP:
		id_local = SS_ID_DP1;
		break;
	case ASIC_INTERNAL_SS_ON_LVDS:
	{
		struct embedded_panel_info panel_info;

		if (bios_parser_get_embedded_panel_info(&bp->base, &panel_info)
				== BP_RESULT_OK)
			id_local = panel_info.ss_id;
		break;
	}
	default:
		break;
	}

	if (id_local == SS_ID_UNKNOWN)
		return result;

	table_size = (le16_to_cpu(tbl->sHeader.usStructureSize) -
			sizeof(ATOM_COMMON_TABLE_HEADER)) /
					sizeof(ATOM_SPREAD_SPECTRUM_ASSIGNMENT);

	for (i = 0; i < table_size; i++) {
		if (id_local != (uint32_t)tbl->asSS_Info[i].ucSS_Id)
			continue;

		memset(ss_info, 0, sizeof(struct spread_spectrum_info));

		if (ATOM_EXTERNAL_SS_MASK &
				tbl->asSS_Info[i].ucSpreadSpectrumType)
			ss_info->type.EXTERNAL = true;

		if (ATOM_SS_CENTRE_SPREAD_MODE_MASK &
				tbl->asSS_Info[i].ucSpreadSpectrumType)
			ss_info->type.CENTER_MODE = true;

		ss_info->type.STEP_AND_DELAY_INFO = true;
		ss_info->spread_spectrum_percentage =
			(uint32_t)le16_to_cpu(tbl->asSS_Info[i].usSpreadSpectrumPercentage);
		ss_info->step_and_delay_info.step = tbl->asSS_Info[i].ucSS_Step;
		ss_info->step_and_delay_info.delay =
			tbl->asSS_Info[i].ucSS_Delay;
		ss_info->step_and_delay_info.recommended_ref_div =
			tbl->asSS_Info[i].ucRecommendedRef_Div;
		ss_info->spread_spectrum_range =
			(uint32_t)tbl->asSS_Info[i].ucSS_Range * 10000;

		/* there will be only one entry for each display type in SS_info
		 * table */
		result = BP_RESULT_OK;
		break;
	}

	return result;
}
static enum bp_result get_embedded_panel_info_v1_2(
	struct bios_parser *bp,
	struct embedded_panel_info *info);
static enum bp_result get_embedded_panel_info_v1_3(
	struct bios_parser *bp,
	struct embedded_panel_info *info);

static enum bp_result bios_parser_get_embedded_panel_info(
	struct dc_bios *dcb,
	struct embedded_panel_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_COMMON_TABLE_HEADER *hdr;

	if (!DATA_TABLES(LCD_Info))
		return BP_RESULT_FAILURE;

	hdr = GET_IMAGE(ATOM_COMMON_TABLE_HEADER, DATA_TABLES(LCD_Info));

	if (!hdr)
		return BP_RESULT_BADBIOSTABLE;

	switch (hdr->ucTableFormatRevision) {
	case 1:
		switch (hdr->ucTableContentRevision) {
		case 0:
		case 1:
		case 2:
			return get_embedded_panel_info_v1_2(bp, info);
		case 3:
			return get_embedded_panel_info_v1_3(bp, info);
		default:
			break;
		}
	default:
		break;
	}

	return BP_RESULT_FAILURE;
}

static enum bp_result get_embedded_panel_info_v1_2(
	struct bios_parser *bp,
	struct embedded_panel_info *info)
{
	ATOM_LVDS_INFO_V12 *lvds;

	if (!info)
		return BP_RESULT_BADINPUT;

	if (!DATA_TABLES(LVDS_Info))
		return BP_RESULT_UNSUPPORTED;

	lvds =
		GET_IMAGE(ATOM_LVDS_INFO_V12, DATA_TABLES(LVDS_Info));

	if (!lvds)
		return BP_RESULT_BADBIOSTABLE;

	if (1 != lvds->sHeader.ucTableFormatRevision
		|| 2 > lvds->sHeader.ucTableContentRevision)
		return BP_RESULT_UNSUPPORTED;

	memset(info, 0, sizeof(struct embedded_panel_info));

	/* We need to convert from 10KHz units into KHz units*/
	info->lcd_timing.pixel_clk =
		le16_to_cpu(lvds->sLCDTiming.usPixClk) * 10;
	/* usHActive does not include borders, according to VBIOS team*/
	info->lcd_timing.horizontal_addressable =
		le16_to_cpu(lvds->sLCDTiming.usHActive);
	/* usHBlanking_Time includes borders, so we should really be subtracting
	 * borders duing this translation, but LVDS generally*/
	/* doesn't have borders, so we should be okay leaving this as is for
	 * now.  May need to revisit if we ever have LVDS with borders*/
	info->lcd_timing.horizontal_blanking_time =
			le16_to_cpu(lvds->sLCDTiming.usHBlanking_Time);
	/* usVActive does not include borders, according to VBIOS team*/
	info->lcd_timing.vertical_addressable =
			le16_to_cpu(lvds->sLCDTiming.usVActive);
	/* usVBlanking_Time includes borders, so we should really be subtracting
	 * borders duing this translation, but LVDS generally*/
	/* doesn't have borders, so we should be okay leaving this as is for
	 * now. May need to revisit if we ever have LVDS with borders*/
	info->lcd_timing.vertical_blanking_time =
		le16_to_cpu(lvds->sLCDTiming.usVBlanking_Time);
	info->lcd_timing.horizontal_sync_offset =
		le16_to_cpu(lvds->sLCDTiming.usHSyncOffset);
	info->lcd_timing.horizontal_sync_width =
		le16_to_cpu(lvds->sLCDTiming.usHSyncWidth);
	info->lcd_timing.vertical_sync_offset =
		le16_to_cpu(lvds->sLCDTiming.usVSyncOffset);
	info->lcd_timing.vertical_sync_width =
		le16_to_cpu(lvds->sLCDTiming.usVSyncWidth);
	info->lcd_timing.horizontal_border = lvds->sLCDTiming.ucHBorder;
	info->lcd_timing.vertical_border = lvds->sLCDTiming.ucVBorder;
	info->lcd_timing.misc_info.HORIZONTAL_CUT_OFF =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.HorizontalCutOff;
	info->lcd_timing.misc_info.H_SYNC_POLARITY =
		~(uint32_t)
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.HSyncPolarity;
	info->lcd_timing.misc_info.V_SYNC_POLARITY =
		~(uint32_t)
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.VSyncPolarity;
	info->lcd_timing.misc_info.VERTICAL_CUT_OFF =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.VerticalCutOff;
	info->lcd_timing.misc_info.H_REPLICATION_BY2 =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.H_ReplicationBy2;
	info->lcd_timing.misc_info.V_REPLICATION_BY2 =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.V_ReplicationBy2;
	info->lcd_timing.misc_info.COMPOSITE_SYNC =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.CompositeSync;
	info->lcd_timing.misc_info.INTERLACE =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.Interlace;
	info->lcd_timing.misc_info.DOUBLE_CLOCK =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.DoubleClock;
	info->ss_id = lvds->ucSS_Id;

	{
		uint8_t rr = le16_to_cpu(lvds->usSupportedRefreshRate);
		/* Get minimum supported refresh rate*/
		if (SUPPORTED_LCD_REFRESHRATE_30Hz & rr)
			info->supported_rr.REFRESH_RATE_30HZ = 1;
		else if (SUPPORTED_LCD_REFRESHRATE_40Hz & rr)
			info->supported_rr.REFRESH_RATE_40HZ = 1;
		else if (SUPPORTED_LCD_REFRESHRATE_48Hz & rr)
			info->supported_rr.REFRESH_RATE_48HZ = 1;
		else if (SUPPORTED_LCD_REFRESHRATE_50Hz & rr)
			info->supported_rr.REFRESH_RATE_50HZ = 1;
		else if (SUPPORTED_LCD_REFRESHRATE_60Hz & rr)
			info->supported_rr.REFRESH_RATE_60HZ = 1;
	}

	/*Drr panel support can be reported by VBIOS*/
	if (LCDPANEL_CAP_DRR_SUPPORTED
			& lvds->ucLCDPanel_SpecialHandlingCap)
		info->drr_enabled = 1;

	if (ATOM_PANEL_MISC_DUAL & lvds->ucLVDS_Misc)
		info->lcd_timing.misc_info.DOUBLE_CLOCK = true;

	if (ATOM_PANEL_MISC_888RGB & lvds->ucLVDS_Misc)
		info->lcd_timing.misc_info.RGB888 = true;

	info->lcd_timing.misc_info.GREY_LEVEL =
		(uint32_t) (ATOM_PANEL_MISC_GREY_LEVEL &
			lvds->ucLVDS_Misc) >> ATOM_PANEL_MISC_GREY_LEVEL_SHIFT;

	if (ATOM_PANEL_MISC_SPATIAL & lvds->ucLVDS_Misc)
		info->lcd_timing.misc_info.SPATIAL = true;

	if (ATOM_PANEL_MISC_TEMPORAL & lvds->ucLVDS_Misc)
		info->lcd_timing.misc_info.TEMPORAL = true;

	if (ATOM_PANEL_MISC_API_ENABLED & lvds->ucLVDS_Misc)
		info->lcd_timing.misc_info.API_ENABLED = true;

	return BP_RESULT_OK;
}

static enum bp_result get_embedded_panel_info_v1_3(
	struct bios_parser *bp,
	struct embedded_panel_info *info)
{
	ATOM_LCD_INFO_V13 *lvds;

	if (!info)
		return BP_RESULT_BADINPUT;

	if (!DATA_TABLES(LCD_Info))
		return BP_RESULT_UNSUPPORTED;

	lvds = GET_IMAGE(ATOM_LCD_INFO_V13, DATA_TABLES(LCD_Info));

	if (!lvds)
		return BP_RESULT_BADBIOSTABLE;

	if (!((1 == lvds->sHeader.ucTableFormatRevision)
			&& (3 <= lvds->sHeader.ucTableContentRevision)))
		return BP_RESULT_UNSUPPORTED;

	memset(info, 0, sizeof(struct embedded_panel_info));

	/* We need to convert from 10KHz units into KHz units */
	info->lcd_timing.pixel_clk =
			le16_to_cpu(lvds->sLCDTiming.usPixClk) * 10;
	/* usHActive does not include borders, according to VBIOS team */
	info->lcd_timing.horizontal_addressable =
			le16_to_cpu(lvds->sLCDTiming.usHActive);
	/* usHBlanking_Time includes borders, so we should really be subtracting
	 * borders duing this translation, but LVDS generally*/
	/* doesn't have borders, so we should be okay leaving this as is for
	 * now.  May need to revisit if we ever have LVDS with borders*/
	info->lcd_timing.horizontal_blanking_time =
		le16_to_cpu(lvds->sLCDTiming.usHBlanking_Time);
	/* usVActive does not include borders, according to VBIOS team*/
	info->lcd_timing.vertical_addressable =
		le16_to_cpu(lvds->sLCDTiming.usVActive);
	/* usVBlanking_Time includes borders, so we should really be subtracting
	 * borders duing this translation, but LVDS generally*/
	/* doesn't have borders, so we should be okay leaving this as is for
	 * now. May need to revisit if we ever have LVDS with borders*/
	info->lcd_timing.vertical_blanking_time =
		le16_to_cpu(lvds->sLCDTiming.usVBlanking_Time);
	info->lcd_timing.horizontal_sync_offset =
		le16_to_cpu(lvds->sLCDTiming.usHSyncOffset);
	info->lcd_timing.horizontal_sync_width =
		le16_to_cpu(lvds->sLCDTiming.usHSyncWidth);
	info->lcd_timing.vertical_sync_offset =
		le16_to_cpu(lvds->sLCDTiming.usVSyncOffset);
	info->lcd_timing.vertical_sync_width =
		le16_to_cpu(lvds->sLCDTiming.usVSyncWidth);
	info->lcd_timing.horizontal_border = lvds->sLCDTiming.ucHBorder;
	info->lcd_timing.vertical_border = lvds->sLCDTiming.ucVBorder;
	info->lcd_timing.misc_info.HORIZONTAL_CUT_OFF =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.HorizontalCutOff;
	info->lcd_timing.misc_info.H_SYNC_POLARITY =
		~(uint32_t)
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.HSyncPolarity;
	info->lcd_timing.misc_info.V_SYNC_POLARITY =
		~(uint32_t)
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.VSyncPolarity;
	info->lcd_timing.misc_info.VERTICAL_CUT_OFF =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.VerticalCutOff;
	info->lcd_timing.misc_info.H_REPLICATION_BY2 =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.H_ReplicationBy2;
	info->lcd_timing.misc_info.V_REPLICATION_BY2 =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.V_ReplicationBy2;
	info->lcd_timing.misc_info.COMPOSITE_SYNC =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.CompositeSync;
	info->lcd_timing.misc_info.INTERLACE =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.Interlace;
	info->lcd_timing.misc_info.DOUBLE_CLOCK =
		lvds->sLCDTiming.susModeMiscInfo.sbfAccess.DoubleClock;
	info->ss_id = lvds->ucSS_Id;

	/* Drr panel support can be reported by VBIOS*/
	if (LCDPANEL_CAP_V13_DRR_SUPPORTED
			& lvds->ucLCDPanel_SpecialHandlingCap)
		info->drr_enabled = 1;

	/* Get supported refresh rate*/
	if (info->drr_enabled == 1) {
		uint8_t min_rr =
				lvds->sRefreshRateSupport.ucMinRefreshRateForDRR;
		uint8_t rr = lvds->sRefreshRateSupport.ucSupportedRefreshRate;

		if (min_rr != 0) {
			if (SUPPORTED_LCD_REFRESHRATE_30Hz & min_rr)
				info->supported_rr.REFRESH_RATE_30HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_40Hz & min_rr)
				info->supported_rr.REFRESH_RATE_40HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_48Hz & min_rr)
				info->supported_rr.REFRESH_RATE_48HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_50Hz & min_rr)
				info->supported_rr.REFRESH_RATE_50HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_60Hz & min_rr)
				info->supported_rr.REFRESH_RATE_60HZ = 1;
		} else {
			if (SUPPORTED_LCD_REFRESHRATE_30Hz & rr)
				info->supported_rr.REFRESH_RATE_30HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_40Hz & rr)
				info->supported_rr.REFRESH_RATE_40HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_48Hz & rr)
				info->supported_rr.REFRESH_RATE_48HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_50Hz & rr)
				info->supported_rr.REFRESH_RATE_50HZ = 1;
			else if (SUPPORTED_LCD_REFRESHRATE_60Hz & rr)
				info->supported_rr.REFRESH_RATE_60HZ = 1;
		}
	}

	if (ATOM_PANEL_MISC_V13_DUAL & lvds->ucLCD_Misc)
		info->lcd_timing.misc_info.DOUBLE_CLOCK = true;

	if (ATOM_PANEL_MISC_V13_8BIT_PER_COLOR & lvds->ucLCD_Misc)
		info->lcd_timing.misc_info.RGB888 = true;

	info->lcd_timing.misc_info.GREY_LEVEL =
			(uint32_t) (ATOM_PANEL_MISC_V13_GREY_LEVEL &
				lvds->ucLCD_Misc) >> ATOM_PANEL_MISC_V13_GREY_LEVEL_SHIFT;

	return BP_RESULT_OK;
}

/**
 * bios_parser_get_encoder_cap_info
 *
 * @brief
 *  Get encoder capability information of input object id
 *
 * @param object_id, Object id
 * @param object_id, encoder cap information structure
 *
 * @return Bios parser result code
 *
 */
static enum bp_result bios_parser_get_encoder_cap_info(
	struct dc_bios *dcb,
	struct graphics_object_id object_id,
	struct bp_encoder_cap_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_OBJECT *object;
	ATOM_ENCODER_CAP_RECORD_V2 *record = NULL;

	if (!info)
		return BP_RESULT_BADINPUT;

	object = get_bios_object(bp, object_id);

	if (!object)
		return BP_RESULT_BADINPUT;

	record = get_encoder_cap_record(bp, object);
	if (!record)
		return BP_RESULT_NORECORD;

	info->DP_HBR2_EN = record->usHBR2En;
	info->DP_HBR3_EN = record->usHBR3En;
	info->HDMI_6GB_EN = record->usHDMI6GEn;
	return BP_RESULT_OK;
}

/**
 * get_encoder_cap_record
 *
 * @brief
 *  Get encoder cap record for the object
 *
 * @param object, ATOM object
 *
 * @return atom encoder cap record
 *
 * @note
 *  search all records to find the ATOM_ENCODER_CAP_RECORD_V2 record
 */
static ATOM_ENCODER_CAP_RECORD_V2 *get_encoder_cap_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	ATOM_COMMON_RECORD_HEADER *header;
	uint32_t offset;

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object */
		return NULL;
	}

	offset = le16_to_cpu(object->usRecordOffset)
					+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return NULL;

		offset += header->ucRecordSize;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
				!header->ucRecordSize)
			break;

		if (ATOM_ENCODER_CAP_RECORD_TYPE != header->ucRecordType)
			continue;

		if (sizeof(ATOM_ENCODER_CAP_RECORD_V2) <= header->ucRecordSize)
			return (ATOM_ENCODER_CAP_RECORD_V2 *)header;
	}

	return NULL;
}

static uint32_t get_ss_entry_number(
	struct bios_parser *bp,
	uint32_t id);
static uint32_t get_ss_entry_number_from_internal_ss_info_tbl_v2_1(
	struct bios_parser *bp,
	uint32_t id);
static uint32_t get_ss_entry_number_from_internal_ss_info_tbl_V3_1(
	struct bios_parser *bp,
	uint32_t id);
static uint32_t get_ss_entry_number_from_ss_info_tbl(
	struct bios_parser *bp,
	uint32_t id);

/**
 * BiosParserObject::GetNumberofSpreadSpectrumEntry
 * Get Number of SpreadSpectrum Entry from the ASIC_InternalSS_Info table from
 * the VBIOS that match the SSid (to be converted from signal)
 *
 * @param[in] signal, ASSignalType to be converted to SSid
 * @return number of SS Entry that match the signal
 */
static uint32_t bios_parser_get_ss_entry_number(
	struct dc_bios *dcb,
	enum as_signal_type signal)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	uint32_t ss_id = 0;
	ATOM_COMMON_TABLE_HEADER *header;
	struct atom_data_revision revision;

	ss_id = signal_to_ss_id(signal);

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		return get_ss_entry_number_from_ss_info_tbl(bp, ss_id);

	header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER,
			DATA_TABLES(ASIC_InternalSS_Info));
	get_atom_data_table_revision(header, &revision);

	switch (revision.major) {
	case 2:
		switch (revision.minor) {
		case 1:
			return get_ss_entry_number(bp, ss_id);
		default:
			break;
		}
		break;
	case 3:
		switch (revision.minor) {
		case 1:
			return
				get_ss_entry_number_from_internal_ss_info_tbl_V3_1(
						bp, ss_id);
		default:
			break;
		}
		break;
	default:
		break;
	}

	return 0;
}

/**
 * get_ss_entry_number_from_ss_info_tbl
 * Get Number of spread spectrum entry from the SS_Info table from the VBIOS.
 *
 * @note There can only be one entry for each id for SS_Info Table
 *
 * @param [in] id, spread spectrum id
 * @return number of SS Entry that match the id
 */
static uint32_t get_ss_entry_number_from_ss_info_tbl(
	struct bios_parser *bp,
	uint32_t id)
{
	ATOM_SPREAD_SPECTRUM_INFO *tbl;
	ATOM_COMMON_TABLE_HEADER *header;
	uint32_t table_size;
	uint32_t i;
	uint32_t number = 0;
	uint32_t id_local = SS_ID_UNKNOWN;
	struct atom_data_revision revision;

	/* SS_Info table exist */
	if (!DATA_TABLES(SS_Info))
		return number;

	header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER,
			DATA_TABLES(SS_Info));
	get_atom_data_table_revision(header, &revision);

	tbl = GET_IMAGE(ATOM_SPREAD_SPECTRUM_INFO,
			DATA_TABLES(SS_Info));

	if (1 != revision.major || 2 > revision.minor)
		return number;

	/* have to convert from Internal_SS format to SS_Info format */
	switch (id) {
	case ASIC_INTERNAL_SS_ON_DP:
		id_local = SS_ID_DP1;
		break;
	case ASIC_INTERNAL_SS_ON_LVDS: {
		struct embedded_panel_info panel_info;

		if (bios_parser_get_embedded_panel_info(&bp->base, &panel_info)
				== BP_RESULT_OK)
			id_local = panel_info.ss_id;
		break;
	}
	default:
		break;
	}

	if (id_local == SS_ID_UNKNOWN)
		return number;

	table_size = (le16_to_cpu(tbl->sHeader.usStructureSize) -
			sizeof(ATOM_COMMON_TABLE_HEADER)) /
					sizeof(ATOM_SPREAD_SPECTRUM_ASSIGNMENT);

	for (i = 0; i < table_size; i++)
		if (id_local == (uint32_t)tbl->asSS_Info[i].ucSS_Id) {
			number = 1;
			break;
		}

	return number;
}

/**
 * get_ss_entry_number
 * Get spread sprectrum information from the ASIC_InternalSS_Info Ver 2.1 or
 * SS_Info table from the VBIOS
 * There can not be more than 1 entry for  ASIC_InternalSS_Info Ver 2.1 or
 * SS_Info.
 *
 * @param id, spread sprectrum info index
 * @return Bios parser result code
 */
static uint32_t get_ss_entry_number(struct bios_parser *bp, uint32_t id)
{
	if (id == ASIC_INTERNAL_SS_ON_DP || id == ASIC_INTERNAL_SS_ON_LVDS)
		return get_ss_entry_number_from_ss_info_tbl(bp, id);

	return get_ss_entry_number_from_internal_ss_info_tbl_v2_1(bp, id);
}

/**
 * get_ss_entry_number_from_internal_ss_info_tbl_v2_1
 * Get NUmber of spread sprectrum entry from the ASIC_InternalSS_Info table
 * Ver 2.1 from the VBIOS
 * There will not be multiple entry for Ver 2.1
 *
 * @param id, spread sprectrum info index
 * @return number of SS Entry that match the id
 */
static uint32_t get_ss_entry_number_from_internal_ss_info_tbl_v2_1(
	struct bios_parser *bp,
	uint32_t id)
{
	ATOM_ASIC_INTERNAL_SS_INFO_V2 *header_include;
	ATOM_ASIC_SS_ASSIGNMENT_V2 *tbl;
	uint32_t size;
	uint32_t i;

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		return 0;

	header_include = GET_IMAGE(ATOM_ASIC_INTERNAL_SS_INFO_V2,
			DATA_TABLES(ASIC_InternalSS_Info));

	size = (le16_to_cpu(header_include->sHeader.usStructureSize)
			- sizeof(ATOM_COMMON_TABLE_HEADER))
						/ sizeof(ATOM_ASIC_SS_ASSIGNMENT_V2);

	tbl = (ATOM_ASIC_SS_ASSIGNMENT_V2 *)
				&header_include->asSpreadSpectrum[0];
	for (i = 0; i < size; i++)
		if (tbl[i].ucClockIndication == (uint8_t)id)
			return 1;

	return 0;
}
/**
 * get_ss_entry_number_from_internal_ss_info_table_V3_1
 * Get Number of SpreadSpectrum Entry from the ASIC_InternalSS_Info table of
 * the VBIOS that matches id
 *
 * @param[in]  id, spread sprectrum id
 * @return number of SS Entry that match the id
 */
static uint32_t get_ss_entry_number_from_internal_ss_info_tbl_V3_1(
	struct bios_parser *bp,
	uint32_t id)
{
	uint32_t number = 0;
	ATOM_ASIC_INTERNAL_SS_INFO_V3 *header_include;
	ATOM_ASIC_SS_ASSIGNMENT_V3 *tbl;
	uint32_t size;
	uint32_t i;

	if (!DATA_TABLES(ASIC_InternalSS_Info))
		return number;

	header_include = GET_IMAGE(ATOM_ASIC_INTERNAL_SS_INFO_V3,
			DATA_TABLES(ASIC_InternalSS_Info));
	size = (le16_to_cpu(header_include->sHeader.usStructureSize) -
			sizeof(ATOM_COMMON_TABLE_HEADER)) /
					sizeof(ATOM_ASIC_SS_ASSIGNMENT_V3);

	tbl = (ATOM_ASIC_SS_ASSIGNMENT_V3 *)
				&header_include->asSpreadSpectrum[0];

	for (i = 0; i < size; i++)
		if (tbl[i].ucClockIndication == (uint8_t)id)
			number++;

	return number;
}

/**
 * bios_parser_get_gpio_pin_info
 * Get GpioPin information of input gpio id
 *
 * @param gpio_id, GPIO ID
 * @param info, GpioPin information structure
 * @return Bios parser result code
 * @note
 *  to get the GPIO PIN INFO, we need:
 *  1. get the GPIO_ID from other object table, see GetHPDInfo()
 *  2. in DATA_TABLE.GPIO_Pin_LUT, search all records, to get the registerA
 *  offset/mask
 */
static enum bp_result bios_parser_get_gpio_pin_info(
	struct dc_bios *dcb,
	uint32_t gpio_id,
	struct gpio_pin_info *info)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	ATOM_GPIO_PIN_LUT *header;
	uint32_t count = 0;
	uint32_t i = 0;

	if (!DATA_TABLES(GPIO_Pin_LUT))
		return BP_RESULT_BADBIOSTABLE;

	header = GET_IMAGE(ATOM_GPIO_PIN_LUT, DATA_TABLES(GPIO_Pin_LUT));
	if (!header)
		return BP_RESULT_BADBIOSTABLE;

	if (sizeof(ATOM_COMMON_TABLE_HEADER) + sizeof(ATOM_GPIO_PIN_LUT)
			> le16_to_cpu(header->sHeader.usStructureSize))
		return BP_RESULT_BADBIOSTABLE;

	if (1 != header->sHeader.ucTableContentRevision)
		return BP_RESULT_UNSUPPORTED;

	count = (le16_to_cpu(header->sHeader.usStructureSize)
			- sizeof(ATOM_COMMON_TABLE_HEADER))
				/ sizeof(ATOM_GPIO_PIN_ASSIGNMENT);
	for (i = 0; i < count; ++i) {
		if (header->asGPIO_Pin[i].ucGPIO_ID != gpio_id)
			continue;

		info->offset =
			(uint32_t) le16_to_cpu(header->asGPIO_Pin[i].usGpioPin_AIndex);
		info->offset_y = info->offset + 2;
		info->offset_en = info->offset + 1;
		info->offset_mask = info->offset - 1;

		info->mask = (uint32_t) (1 <<
			header->asGPIO_Pin[i].ucGpioPinBitShift);
		info->mask_y = info->mask + 2;
		info->mask_en = info->mask + 1;
		info->mask_mask = info->mask - 1;

		return BP_RESULT_OK;
	}

	return BP_RESULT_NORECORD;
}

static enum bp_result get_gpio_i2c_info(struct bios_parser *bp,
	ATOM_I2C_RECORD *record,
	struct graphics_object_i2c_info *info)
{
	ATOM_GPIO_I2C_INFO *header;
	uint32_t count = 0;

	if (!info)
		return BP_RESULT_BADINPUT;

	/* get the GPIO_I2C info */
	if (!DATA_TABLES(GPIO_I2C_Info))
		return BP_RESULT_BADBIOSTABLE;

	header = GET_IMAGE(ATOM_GPIO_I2C_INFO, DATA_TABLES(GPIO_I2C_Info));
	if (!header)
		return BP_RESULT_BADBIOSTABLE;

	if (sizeof(ATOM_COMMON_TABLE_HEADER) + sizeof(ATOM_GPIO_I2C_ASSIGMENT)
			> le16_to_cpu(header->sHeader.usStructureSize))
		return BP_RESULT_BADBIOSTABLE;

	if (1 != header->sHeader.ucTableContentRevision)
		return BP_RESULT_UNSUPPORTED;

	/* get data count */
	count = (le16_to_cpu(header->sHeader.usStructureSize)
			- sizeof(ATOM_COMMON_TABLE_HEADER))
				/ sizeof(ATOM_GPIO_I2C_ASSIGMENT);
	if (count < record->sucI2cId.bfI2C_LineMux)
		return BP_RESULT_BADBIOSTABLE;

	/* get the GPIO_I2C_INFO */
	info->i2c_hw_assist = record->sucI2cId.bfHW_Capable;
	info->i2c_line = record->sucI2cId.bfI2C_LineMux;
	info->i2c_engine_id = record->sucI2cId.bfHW_EngineID;
	info->i2c_slave_address = record->ucI2CAddr;

	info->gpio_info.clk_mask_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usClkMaskRegisterIndex);
	info->gpio_info.clk_en_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usClkEnRegisterIndex);
	info->gpio_info.clk_y_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usClkY_RegisterIndex);
	info->gpio_info.clk_a_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usClkA_RegisterIndex);
	info->gpio_info.data_mask_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usDataMaskRegisterIndex);
	info->gpio_info.data_en_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usDataEnRegisterIndex);
	info->gpio_info.data_y_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usDataY_RegisterIndex);
	info->gpio_info.data_a_register_index =
			le16_to_cpu(header->asGPIO_Info[info->i2c_line].usDataA_RegisterIndex);

	info->gpio_info.clk_mask_shift =
			header->asGPIO_Info[info->i2c_line].ucClkMaskShift;
	info->gpio_info.clk_en_shift =
			header->asGPIO_Info[info->i2c_line].ucClkEnShift;
	info->gpio_info.clk_y_shift =
			header->asGPIO_Info[info->i2c_line].ucClkY_Shift;
	info->gpio_info.clk_a_shift =
			header->asGPIO_Info[info->i2c_line].ucClkA_Shift;
	info->gpio_info.data_mask_shift =
			header->asGPIO_Info[info->i2c_line].ucDataMaskShift;
	info->gpio_info.data_en_shift =
			header->asGPIO_Info[info->i2c_line].ucDataEnShift;
	info->gpio_info.data_y_shift =
			header->asGPIO_Info[info->i2c_line].ucDataY_Shift;
	info->gpio_info.data_a_shift =
			header->asGPIO_Info[info->i2c_line].ucDataA_Shift;

	return BP_RESULT_OK;
}

static bool dal_graphics_object_id_is_valid(struct graphics_object_id id)
{
	bool rc = true;

	switch (id.type) {
	case OBJECT_TYPE_UNKNOWN:
		rc = false;
		break;
	case OBJECT_TYPE_GPU:
	case OBJECT_TYPE_ENGINE:
		/* do NOT check for id.id == 0 */
		if (id.enum_id == ENUM_ID_UNKNOWN)
			rc = false;
		break;
	default:
		if (id.id == 0 || id.enum_id == ENUM_ID_UNKNOWN)
			rc = false;
		break;
	}

	return rc;
}

static bool dal_graphics_object_id_is_equal(
	struct graphics_object_id id1,
	struct graphics_object_id id2)
{
	if (false == dal_graphics_object_id_is_valid(id1)) {
		dm_output_to_console(
		"%s: Warning: comparing invalid object 'id1'!\n", __func__);
		return false;
	}

	if (false == dal_graphics_object_id_is_valid(id2)) {
		dm_output_to_console(
		"%s: Warning: comparing invalid object 'id2'!\n", __func__);
		return false;
	}

	if (id1.id == id2.id && id1.enum_id == id2.enum_id
		&& id1.type == id2.type)
		return true;

	return false;
}

static ATOM_OBJECT *get_bios_object(struct bios_parser *bp,
	struct graphics_object_id id)
{
	uint32_t offset;
	ATOM_OBJECT_TABLE *tbl;
	uint32_t i;

	switch (id.type) {
	case OBJECT_TYPE_ENCODER:
		offset = le16_to_cpu(bp->object_info_tbl.v1_1->usEncoderObjectTableOffset);
		break;

	case OBJECT_TYPE_CONNECTOR:
		offset = le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset);
		break;

	case OBJECT_TYPE_ROUTER:
		offset = le16_to_cpu(bp->object_info_tbl.v1_1->usRouterObjectTableOffset);
		break;

	case OBJECT_TYPE_GENERIC:
		if (bp->object_info_tbl.revision.minor < 3)
			return NULL;
		offset = le16_to_cpu(bp->object_info_tbl.v1_3->usMiscObjectTableOffset);
		break;

	default:
		return NULL;
	}

	offset += bp->object_info_tbl_offset;

	tbl = GET_IMAGE(ATOM_OBJECT_TABLE, offset);
	if (!tbl)
		return NULL;

	for (i = 0; i < tbl->ucNumberOfObjects; i++)
		if (dal_graphics_object_id_is_equal(id,
				object_id_from_bios_object_id(
						le16_to_cpu(tbl->asObjects[i].usObjectID))))
			return &tbl->asObjects[i];

	return NULL;
}

static uint32_t get_dest_obj_list(struct bios_parser *bp,
	ATOM_OBJECT *object, uint16_t **id_list)
{
	uint32_t offset;
	uint8_t *number;

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object id */
		return 0;
	}

	offset = le16_to_cpu(object->usSrcDstTableOffset)
						+ bp->object_info_tbl_offset;

	number = GET_IMAGE(uint8_t, offset);
	if (!number)
		return 0;

	offset += sizeof(uint8_t);
	offset += sizeof(uint16_t) * (*number);

	number = GET_IMAGE(uint8_t, offset);
	if ((!number) || (!*number))
		return 0;

	offset += sizeof(uint8_t);
	*id_list = (uint16_t *)bios_get_image(&bp->base, offset, *number * sizeof(uint16_t));

	if (!*id_list)
		return 0;

	return *number;
}

static uint32_t get_src_obj_list(struct bios_parser *bp, ATOM_OBJECT *object,
	uint16_t **id_list)
{
	uint32_t offset;
	uint8_t *number;

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid object id */
		return 0;
	}

	offset = le16_to_cpu(object->usSrcDstTableOffset)
					+ bp->object_info_tbl_offset;

	number = GET_IMAGE(uint8_t, offset);
	if (!number)
		return 0;

	offset += sizeof(uint8_t);
	*id_list = (uint16_t *)bios_get_image(&bp->base, offset, *number * sizeof(uint16_t));

	if (!*id_list)
		return 0;

	return *number;
}

static uint32_t get_dst_number_from_object(struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	uint32_t offset;
	uint8_t *number;

	if (!object) {
		BREAK_TO_DEBUGGER(); /* Invalid encoder object id*/
		return 0;
	}

	offset = le16_to_cpu(object->usSrcDstTableOffset)
					+ bp->object_info_tbl_offset;

	number = GET_IMAGE(uint8_t, offset);
	if (!number)
		return 0;

	offset += sizeof(uint8_t);
	offset += sizeof(uint16_t) * (*number);

	number = GET_IMAGE(uint8_t, offset);

	if (!number)
		return 0;

	return *number;
}

static struct device_id device_type_from_device_id(uint16_t device_id)
{

	struct device_id result_device_id;

	switch (device_id) {
	case ATOM_DEVICE_LCD1_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_LCD;
		result_device_id.enum_id = 1;
		break;

	case ATOM_DEVICE_LCD2_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_LCD;
		result_device_id.enum_id = 2;
		break;

	case ATOM_DEVICE_CRT1_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_CRT;
		result_device_id.enum_id = 1;
		break;

	case ATOM_DEVICE_CRT2_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_CRT;
		result_device_id.enum_id = 2;
		break;

	case ATOM_DEVICE_DFP1_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 1;
		break;

	case ATOM_DEVICE_DFP2_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 2;
		break;

	case ATOM_DEVICE_DFP3_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 3;
		break;

	case ATOM_DEVICE_DFP4_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 4;
		break;

	case ATOM_DEVICE_DFP5_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 5;
		break;

	case ATOM_DEVICE_DFP6_SUPPORT:
		result_device_id.device_type = DEVICE_TYPE_DFP;
		result_device_id.enum_id = 6;
		break;

	default:
		BREAK_TO_DEBUGGER(); /* Invalid device Id */
		result_device_id.device_type = DEVICE_TYPE_UNKNOWN;
		result_device_id.enum_id = 0;
	}
	return result_device_id;
}

static void get_atom_data_table_revision(
	ATOM_COMMON_TABLE_HEADER *atom_data_tbl,
	struct atom_data_revision *tbl_revision)
{
	if (!tbl_revision)
		return;

	/* initialize the revision to 0 which is invalid revision */
	tbl_revision->major = 0;
	tbl_revision->minor = 0;

	if (!atom_data_tbl)
		return;

	tbl_revision->major =
			(uint32_t) GET_DATA_TABLE_MAJOR_REVISION(atom_data_tbl);
	tbl_revision->minor =
			(uint32_t) GET_DATA_TABLE_MINOR_REVISION(atom_data_tbl);
}

static uint32_t signal_to_ss_id(enum as_signal_type signal)
{
	uint32_t clk_id_ss = 0;

	switch (signal) {
	case AS_SIGNAL_TYPE_DVI:
		clk_id_ss = ASIC_INTERNAL_SS_ON_TMDS;
		break;
	case AS_SIGNAL_TYPE_HDMI:
		clk_id_ss = ASIC_INTERNAL_SS_ON_HDMI;
		break;
	case AS_SIGNAL_TYPE_LVDS:
		clk_id_ss = ASIC_INTERNAL_SS_ON_LVDS;
		break;
	case AS_SIGNAL_TYPE_DISPLAY_PORT:
		clk_id_ss = ASIC_INTERNAL_SS_ON_DP;
		break;
	case AS_SIGNAL_TYPE_GPU_PLL:
		clk_id_ss = ASIC_INTERNAL_GPUPLL_SS;
		break;
	default:
		break;
	}
	return clk_id_ss;
}

static uint32_t get_support_mask_for_device_id(struct device_id device_id)
{
	enum dal_device_type device_type = device_id.device_type;
	uint32_t enum_id = device_id.enum_id;

	switch (device_type) {
	case DEVICE_TYPE_LCD:
		switch (enum_id) {
		case 1:
			return ATOM_DEVICE_LCD1_SUPPORT;
		case 2:
			return ATOM_DEVICE_LCD2_SUPPORT;
		default:
			break;
		}
		break;
	case DEVICE_TYPE_CRT:
		switch (enum_id) {
		case 1:
			return ATOM_DEVICE_CRT1_SUPPORT;
		case 2:
			return ATOM_DEVICE_CRT2_SUPPORT;
		default:
			break;
		}
		break;
	case DEVICE_TYPE_DFP:
		switch (enum_id) {
		case 1:
			return ATOM_DEVICE_DFP1_SUPPORT;
		case 2:
			return ATOM_DEVICE_DFP2_SUPPORT;
		case 3:
			return ATOM_DEVICE_DFP3_SUPPORT;
		case 4:
			return ATOM_DEVICE_DFP4_SUPPORT;
		case 5:
			return ATOM_DEVICE_DFP5_SUPPORT;
		case 6:
			return ATOM_DEVICE_DFP6_SUPPORT;
		default:
			break;
		}
		break;
	case DEVICE_TYPE_CV:
		switch (enum_id) {
		case 1:
			return ATOM_DEVICE_CV_SUPPORT;
		default:
			break;
		}
		break;
	case DEVICE_TYPE_TV:
		switch (enum_id) {
		case 1:
			return ATOM_DEVICE_TV1_SUPPORT;
		default:
			break;
		}
		break;
	default:
		break;
	};

	/* Unidentified device ID, return empty support mask. */
	return 0;
}

/**
 *  HwContext interface for writing MM registers
 */

static bool i2c_read(
	struct bios_parser *bp,
	struct graphics_object_i2c_info *i2c_info,
	uint8_t *buffer,
	uint32_t length)
{
	struct ddc *ddc;
	uint8_t offset[2] = { 0, 0 };
	bool result = false;
	struct i2c_command cmd;
	struct gpio_ddc_hw_info hw_info = {
		i2c_info->i2c_hw_assist,
		i2c_info->i2c_line };

	ddc = dal_gpio_create_ddc(bp->base.ctx->gpio_service,
		i2c_info->gpio_info.clk_a_register_index,
		(1 << i2c_info->gpio_info.clk_a_shift), &hw_info);

	if (!ddc)
		return result;

	/*Using SW engine */
	cmd.engine = I2C_COMMAND_ENGINE_SW;
	cmd.speed = ddc->ctx->dc->caps.i2c_speed_in_khz;

	{
		struct i2c_payload payloads[] = {
				{
						.address = i2c_info->i2c_slave_address >> 1,
						.data = offset,
						.length = sizeof(offset),
						.write = true
				},
				{
						.address = i2c_info->i2c_slave_address >> 1,
						.data = buffer,
						.length = length,
						.write = false
				}
		};

		cmd.payloads = payloads;
		cmd.number_of_payloads = ARRAY_SIZE(payloads);

		/* TODO route this through drm i2c_adapter */
		result = dal_i2caux_submit_i2c_command(
				ddc->ctx->i2caux,
				ddc,
				&cmd);
	}

	dal_gpio_destroy_ddc(&ddc);

	return result;
}

/**
 * Read external display connection info table through i2c.
 * validate the GUID and checksum.
 *
 * @return enum bp_result whether all data was sucessfully read
 */
static enum bp_result get_ext_display_connection_info(
	struct bios_parser *bp,
	ATOM_OBJECT *opm_object,
	ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO *ext_display_connection_info_tbl)
{
	bool config_tbl_present = false;
	ATOM_I2C_RECORD *i2c_record = NULL;
	uint32_t i = 0;

	if (opm_object == NULL)
		return BP_RESULT_BADINPUT;

	i2c_record = get_i2c_record(bp, opm_object);

	if (i2c_record != NULL) {
		ATOM_GPIO_I2C_INFO *gpio_i2c_header;
		struct graphics_object_i2c_info i2c_info;

		gpio_i2c_header = GET_IMAGE(ATOM_GPIO_I2C_INFO,
				bp->master_data_tbl->ListOfDataTables.GPIO_I2C_Info);

		if (NULL == gpio_i2c_header)
			return BP_RESULT_BADBIOSTABLE;

		if (get_gpio_i2c_info(bp, i2c_record, &i2c_info) !=
				BP_RESULT_OK)
			return BP_RESULT_BADBIOSTABLE;

		if (i2c_read(bp,
			     &i2c_info,
			     (uint8_t *)ext_display_connection_info_tbl,
			     sizeof(ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO))) {
			config_tbl_present = true;
		}
	}

	/* Validate GUID */
	if (config_tbl_present)
		for (i = 0; i < NUMBER_OF_UCHAR_FOR_GUID; i++) {
			if (ext_display_connection_info_tbl->ucGuid[i]
			    != ext_display_connection_guid[i]) {
				config_tbl_present = false;
				break;
			}
		}

	/* Validate checksum */
	if (config_tbl_present) {
		uint8_t check_sum = 0;
		uint8_t *buf =
				(uint8_t *)ext_display_connection_info_tbl;

		for (i = 0; i < sizeof(ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO);
				i++) {
			check_sum += buf[i];
		}

		if (check_sum != 0)
			config_tbl_present = false;
	}

	if (config_tbl_present)
		return BP_RESULT_OK;
	else
		return BP_RESULT_FAILURE;
}

/*
 * Gets the first device ID in the same group as the given ID for enumerating.
 * For instance, if any DFP device ID is passed, returns the device ID for DFP1.
 *
 * The first device ID in the same group as the passed device ID, or 0 if no
 * matching device group found.
 */
static uint32_t enum_first_device_id(uint32_t dev_id)
{
	/* Return the first in the group that this ID belongs to. */
	if (dev_id & ATOM_DEVICE_CRT_SUPPORT)
		return ATOM_DEVICE_CRT1_SUPPORT;
	else if (dev_id & ATOM_DEVICE_DFP_SUPPORT)
		return ATOM_DEVICE_DFP1_SUPPORT;
	else if (dev_id & ATOM_DEVICE_LCD_SUPPORT)
		return ATOM_DEVICE_LCD1_SUPPORT;
	else if (dev_id & ATOM_DEVICE_TV_SUPPORT)
		return ATOM_DEVICE_TV1_SUPPORT;
	else if (dev_id & ATOM_DEVICE_CV_SUPPORT)
		return ATOM_DEVICE_CV_SUPPORT;

	/* No group found for this device ID. */

	dm_error("%s: incorrect input %d\n", __func__, dev_id);
	/* No matching support flag for given device ID */
	return 0;
}

/*
 * Gets the next device ID in the group for a given device ID.
 *
 * The current device ID being enumerated on.
 *
 * The next device ID in the group, or 0 if no device exists.
 */
static uint32_t enum_next_dev_id(uint32_t dev_id)
{
	/* Get next device ID in the group. */
	switch (dev_id) {
	case ATOM_DEVICE_CRT1_SUPPORT:
		return ATOM_DEVICE_CRT2_SUPPORT;
	case ATOM_DEVICE_LCD1_SUPPORT:
		return ATOM_DEVICE_LCD2_SUPPORT;
	case ATOM_DEVICE_DFP1_SUPPORT:
		return ATOM_DEVICE_DFP2_SUPPORT;
	case ATOM_DEVICE_DFP2_SUPPORT:
		return ATOM_DEVICE_DFP3_SUPPORT;
	case ATOM_DEVICE_DFP3_SUPPORT:
		return ATOM_DEVICE_DFP4_SUPPORT;
	case ATOM_DEVICE_DFP4_SUPPORT:
		return ATOM_DEVICE_DFP5_SUPPORT;
	case ATOM_DEVICE_DFP5_SUPPORT:
		return ATOM_DEVICE_DFP6_SUPPORT;
	}

	/* Done enumerating through devices. */
	return 0;
}

/*
 * Returns the new device tag record for patched BIOS object.
 *
 * [IN] pExtDisplayPath - External display path to copy device tag from.
 * [IN] deviceSupport - Bit vector for device ID support flags.
 * [OUT] pDeviceTag - Device tag structure to fill with patched data.
 *
 * True if a compatible device ID was found, false otherwise.
 */
static bool get_patched_device_tag(
	struct bios_parser *bp,
	EXT_DISPLAY_PATH *ext_display_path,
	uint32_t device_support,
	ATOM_CONNECTOR_DEVICE_TAG *device_tag)
{
	uint32_t dev_id;
	/* Use fallback behaviour if not supported. */
	if (!bp->remap_device_tags) {
		device_tag->ulACPIDeviceEnum =
				cpu_to_le32((uint32_t) le16_to_cpu(ext_display_path->usDeviceACPIEnum));
		device_tag->usDeviceID =
				cpu_to_le16(le16_to_cpu(ext_display_path->usDeviceTag));
		return true;
	}

	/* Find the first unused in the same group. */
	dev_id = enum_first_device_id(le16_to_cpu(ext_display_path->usDeviceTag));
	while (dev_id != 0) {
		/* Assign this device ID if supported. */
		if ((device_support & dev_id) != 0) {
			device_tag->ulACPIDeviceEnum =
					cpu_to_le32((uint32_t) le16_to_cpu(ext_display_path->usDeviceACPIEnum));
			device_tag->usDeviceID = cpu_to_le16((USHORT) dev_id);
			return true;
		}

		dev_id = enum_next_dev_id(dev_id);
	}

	/* No compatible device ID found. */
	return false;
}

/*
 * Adds a device tag to a BIOS object's device tag record if there is
 * matching device ID supported.
 *
 * pObject - Pointer to the BIOS object to add the device tag to.
 * pExtDisplayPath - Display path to retrieve base device ID from.
 * pDeviceSupport - Pointer to bit vector for supported device IDs.
 */
static void add_device_tag_from_ext_display_path(
	struct bios_parser *bp,
	ATOM_OBJECT *object,
	EXT_DISPLAY_PATH *ext_display_path,
	uint32_t *device_support)
{
	/* Get device tag record for object. */
	ATOM_CONNECTOR_DEVICE_TAG *device_tag = NULL;
	ATOM_CONNECTOR_DEVICE_TAG_RECORD *device_tag_record = NULL;
	enum bp_result result =
			bios_parser_get_device_tag_record(
					bp, object, &device_tag_record);

	if ((le16_to_cpu(ext_display_path->usDeviceTag) != CONNECTOR_OBJECT_ID_NONE)
			&& (result == BP_RESULT_OK)) {
		uint8_t index;

		if ((device_tag_record->ucNumberOfDevice == 1) &&
				(le16_to_cpu(device_tag_record->asDeviceTag[0].usDeviceID) == 0)) {
			/*Workaround bug in current VBIOS releases where
			 * ucNumberOfDevice = 1 but there is no actual device
			 * tag data. This w/a is temporary until the updated
			 * VBIOS is distributed. */
			device_tag_record->ucNumberOfDevice =
					device_tag_record->ucNumberOfDevice - 1;
		}

		/* Attempt to find a matching device ID. */
		index = device_tag_record->ucNumberOfDevice;
		device_tag = &device_tag_record->asDeviceTag[index];
		if (get_patched_device_tag(
				bp,
				ext_display_path,
				*device_support,
				device_tag)) {
			/* Update cached device support to remove assigned ID.
			 */
			*device_support &= ~le16_to_cpu(device_tag->usDeviceID);
			device_tag_record->ucNumberOfDevice++;
		}
	}
}

/*
 * Read out a single EXT_DISPLAY_PATH from the external display connection info
 * table. The specific entry in the table is determined by the enum_id passed
 * in.
 *
 * EXT_DISPLAY_PATH describing a single Configuration table entry
 */

#define INVALID_CONNECTOR 0xffff

static EXT_DISPLAY_PATH *get_ext_display_path_entry(
	ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO *config_table,
	uint32_t bios_object_id)
{
	EXT_DISPLAY_PATH *ext_display_path;
	uint32_t ext_display_path_index =
			((bios_object_id & ENUM_ID_MASK) >> ENUM_ID_SHIFT) - 1;

	if (ext_display_path_index >= MAX_NUMBER_OF_EXT_DISPLAY_PATH)
		return NULL;

	ext_display_path = &config_table->sPath[ext_display_path_index];

	if (le16_to_cpu(ext_display_path->usDeviceConnector) == INVALID_CONNECTOR)
		ext_display_path->usDeviceConnector = cpu_to_le16(0);

	return ext_display_path;
}

/*
 * Get AUX/DDC information of input object id
 *
 * search all records to find the ATOM_CONNECTOR_AUXDDC_LUT_RECORD_TYPE record
 * IR
 */
static ATOM_CONNECTOR_AUXDDC_LUT_RECORD *get_ext_connector_aux_ddc_lut_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	uint32_t offset;
	ATOM_COMMON_RECORD_HEADER *header;

	if (!object) {
		BREAK_TO_DEBUGGER();
		/* Invalid object */
		return NULL;
	}

	offset = le16_to_cpu(object->usRecordOffset)
					+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return NULL;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
				0 == header->ucRecordSize)
			break;

		if (ATOM_CONNECTOR_AUXDDC_LUT_RECORD_TYPE ==
				header->ucRecordType &&
				sizeof(ATOM_CONNECTOR_AUXDDC_LUT_RECORD) <=
				header->ucRecordSize)
			return (ATOM_CONNECTOR_AUXDDC_LUT_RECORD *)(header);

		offset += header->ucRecordSize;
	}

	return NULL;
}

/*
 * Get AUX/DDC information of input object id
 *
 * search all records to find the ATOM_CONNECTOR_AUXDDC_LUT_RECORD_TYPE record
 * IR
 */
static ATOM_CONNECTOR_HPDPIN_LUT_RECORD *get_ext_connector_hpd_pin_lut_record(
	struct bios_parser *bp,
	ATOM_OBJECT *object)
{
	uint32_t offset;
	ATOM_COMMON_RECORD_HEADER *header;

	if (!object) {
		BREAK_TO_DEBUGGER();
		/* Invalid object */
		return NULL;
	}

	offset = le16_to_cpu(object->usRecordOffset)
					+ bp->object_info_tbl_offset;

	for (;;) {
		header = GET_IMAGE(ATOM_COMMON_RECORD_HEADER, offset);

		if (!header)
			return NULL;

		if (LAST_RECORD_TYPE == header->ucRecordType ||
				0 == header->ucRecordSize)
			break;

		if (ATOM_CONNECTOR_HPDPIN_LUT_RECORD_TYPE ==
				header->ucRecordType &&
				sizeof(ATOM_CONNECTOR_HPDPIN_LUT_RECORD) <=
				header->ucRecordSize)
			return (ATOM_CONNECTOR_HPDPIN_LUT_RECORD *)header;

		offset += header->ucRecordSize;
	}

	return NULL;
}

/*
 * Check whether we need to patch the VBIOS connector info table with
 * data from an external display connection info table.  This is
 * necessary to support MXM boards with an OPM (output personality
 * module).  With these designs, the VBIOS connector info table
 * specifies an MXM_CONNECTOR with a unique ID.  The driver retrieves
 * the external connection info table through i2c and then looks up the
 * connector ID to find the real connector type (e.g. DFP1).
 *
 */
static enum bp_result patch_bios_image_from_ext_display_connection_info(
	struct bios_parser *bp)
{
	ATOM_OBJECT_TABLE *connector_tbl;
	uint32_t connector_tbl_offset;
	struct graphics_object_id object_id;
	ATOM_OBJECT *object;
	ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO ext_display_connection_info_tbl;
	EXT_DISPLAY_PATH *ext_display_path;
	ATOM_CONNECTOR_AUXDDC_LUT_RECORD *aux_ddc_lut_record = NULL;
	ATOM_I2C_RECORD *i2c_record = NULL;
	ATOM_CONNECTOR_HPDPIN_LUT_RECORD *hpd_pin_lut_record = NULL;
	ATOM_HPD_INT_RECORD *hpd_record = NULL;
	ATOM_OBJECT_TABLE *encoder_table;
	uint32_t encoder_table_offset;
	ATOM_OBJECT *opm_object = NULL;
	uint32_t i = 0;
	struct graphics_object_id opm_object_id =
			dal_graphics_object_id_init(
					GENERIC_ID_MXM_OPM,
					ENUM_ID_1,
					OBJECT_TYPE_GENERIC);
	ATOM_CONNECTOR_DEVICE_TAG_RECORD *dev_tag_record;
	uint32_t cached_device_support =
			le16_to_cpu(bp->object_info_tbl.v1_1->usDeviceSupport);

	uint32_t dst_number;
	uint16_t *dst_object_id_list;

	opm_object = get_bios_object(bp, opm_object_id);
	if (!opm_object)
		return BP_RESULT_UNSUPPORTED;

	memset(&ext_display_connection_info_tbl, 0,
			sizeof(ATOM_EXTERNAL_DISPLAY_CONNECTION_INFO));

	connector_tbl_offset = bp->object_info_tbl_offset
			+ le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset);
	connector_tbl = GET_IMAGE(ATOM_OBJECT_TABLE, connector_tbl_offset);

	/* Read Connector info table from EEPROM through i2c */
	if (get_ext_display_connection_info(bp,
					    opm_object,
					    &ext_display_connection_info_tbl) != BP_RESULT_OK) {

		DC_LOG_WARNING("%s: Failed to read Connection Info Table", __func__);
		return BP_RESULT_UNSUPPORTED;
	}

	/* Get pointer to AUX/DDC and HPD LUTs */
	aux_ddc_lut_record =
			get_ext_connector_aux_ddc_lut_record(bp, opm_object);
	hpd_pin_lut_record =
			get_ext_connector_hpd_pin_lut_record(bp, opm_object);

	if ((aux_ddc_lut_record == NULL) || (hpd_pin_lut_record == NULL))
		return BP_RESULT_UNSUPPORTED;

	/* Cache support bits for currently unmapped device types. */
	if (bp->remap_device_tags) {
		for (i = 0; i < connector_tbl->ucNumberOfObjects; ++i) {
			uint32_t j;
			/* Remove support for all non-MXM connectors. */
			object = &connector_tbl->asObjects[i];
			object_id = object_id_from_bios_object_id(
					le16_to_cpu(object->usObjectID));
			if ((OBJECT_TYPE_CONNECTOR != object_id.type) ||
					(CONNECTOR_ID_MXM == object_id.id))
				continue;

			/* Remove support for all device tags. */
			if (bios_parser_get_device_tag_record(
					bp, object, &dev_tag_record) != BP_RESULT_OK)
				continue;

			for (j = 0; j < dev_tag_record->ucNumberOfDevice; ++j) {
				ATOM_CONNECTOR_DEVICE_TAG *device_tag =
						&dev_tag_record->asDeviceTag[j];
				cached_device_support &=
						~le16_to_cpu(device_tag->usDeviceID);
			}
		}
	}

	/* Find all MXM connector objects and patch them with connector info
	 * from the external display connection info table. */
	for (i = 0; i < connector_tbl->ucNumberOfObjects; i++) {
		uint32_t j;

		object = &connector_tbl->asObjects[i];
		object_id = object_id_from_bios_object_id(le16_to_cpu(object->usObjectID));
		if ((OBJECT_TYPE_CONNECTOR != object_id.type) ||
				(CONNECTOR_ID_MXM != object_id.id))
			continue;

		/* Get the correct connection info table entry based on the enum
		 * id. */
		ext_display_path = get_ext_display_path_entry(
				&ext_display_connection_info_tbl,
				le16_to_cpu(object->usObjectID));
		if (!ext_display_path)
			return BP_RESULT_FAILURE;

		/* Patch device connector ID */
		object->usObjectID =
				cpu_to_le16(le16_to_cpu(ext_display_path->usDeviceConnector));

		/* Patch device tag, ulACPIDeviceEnum. */
		add_device_tag_from_ext_display_path(
				bp,
				object,
				ext_display_path,
				&cached_device_support);

		/* Patch HPD info */
		if (ext_display_path->ucExtHPDPINLutIndex <
				MAX_NUMBER_OF_EXT_HPDPIN_LUT_ENTRIES) {
			hpd_record = get_hpd_record(bp, object);
			if (hpd_record) {
				uint8_t index =
						ext_display_path->ucExtHPDPINLutIndex;
				hpd_record->ucHPDIntGPIOID =
						hpd_pin_lut_record->ucHPDPINMap[index];
			} else {
				BREAK_TO_DEBUGGER();
				/* Invalid hpd record */
				return BP_RESULT_FAILURE;
			}
		}

		/* Patch I2C/AUX info */
		if (ext_display_path->ucExtHPDPINLutIndex <
				MAX_NUMBER_OF_EXT_AUXDDC_LUT_ENTRIES) {
			i2c_record = get_i2c_record(bp, object);
			if (i2c_record) {
				uint8_t index =
						ext_display_path->ucExtAUXDDCLutIndex;
				i2c_record->sucI2cId =
						aux_ddc_lut_record->ucAUXDDCMap[index];
			} else {
				BREAK_TO_DEBUGGER();
				/* Invalid I2C record */
				return BP_RESULT_FAILURE;
			}
		}

		/* Merge with other MXM connectors that map to the same physical
		 * connector. */
		for (j = i + 1;
				j < connector_tbl->ucNumberOfObjects; j++) {
			ATOM_OBJECT *next_object;
			struct graphics_object_id next_object_id;
			EXT_DISPLAY_PATH *next_ext_display_path;

			next_object = &connector_tbl->asObjects[j];
			next_object_id = object_id_from_bios_object_id(
					le16_to_cpu(next_object->usObjectID));

			if ((OBJECT_TYPE_CONNECTOR != next_object_id.type) &&
					(CONNECTOR_ID_MXM == next_object_id.id))
				continue;

			next_ext_display_path = get_ext_display_path_entry(
					&ext_display_connection_info_tbl,
					le16_to_cpu(next_object->usObjectID));

			if (next_ext_display_path == NULL)
				return BP_RESULT_FAILURE;

			/* Merge if using same connector. */
			if ((le16_to_cpu(next_ext_display_path->usDeviceConnector) ==
					le16_to_cpu(ext_display_path->usDeviceConnector)) &&
					(le16_to_cpu(ext_display_path->usDeviceConnector) != 0)) {
				/* Clear duplicate connector from table. */
				next_object->usObjectID = cpu_to_le16(0);
				add_device_tag_from_ext_display_path(
						bp,
						object,
						ext_display_path,
						&cached_device_support);
			}
		}
	}

	/* Find all encoders which have an MXM object as their destination.
	 *  Replace the MXM object with the real connector Id from the external
	 *  display connection info table */

	encoder_table_offset = bp->object_info_tbl_offset
			+ le16_to_cpu(bp->object_info_tbl.v1_1->usEncoderObjectTableOffset);
	encoder_table = GET_IMAGE(ATOM_OBJECT_TABLE, encoder_table_offset);

	for (i = 0; i < encoder_table->ucNumberOfObjects; i++) {
		uint32_t j;

		object = &encoder_table->asObjects[i];

		dst_number = get_dest_obj_list(bp, object, &dst_object_id_list);

		for (j = 0; j < dst_number; j++) {
			object_id = object_id_from_bios_object_id(
					dst_object_id_list[j]);

			if ((OBJECT_TYPE_CONNECTOR != object_id.type) ||
					(CONNECTOR_ID_MXM != object_id.id))
				continue;

			/* Get the correct connection info table entry based on
			 * the enum id. */
			ext_display_path =
					get_ext_display_path_entry(
							&ext_display_connection_info_tbl,
							dst_object_id_list[j]);

			if (ext_display_path == NULL)
				return BP_RESULT_FAILURE;

			dst_object_id_list[j] =
					le16_to_cpu(ext_display_path->usDeviceConnector);
		}
	}

	return BP_RESULT_OK;
}

/*
 * Check whether we need to patch the VBIOS connector info table with
 * data from an external display connection info table.  This is
 * necessary to support MXM boards with an OPM (output personality
 * module).  With these designs, the VBIOS connector info table
 * specifies an MXM_CONNECTOR with a unique ID.  The driver retrieves
 * the external connection info table through i2c and then looks up the
 * connector ID to find the real connector type (e.g. DFP1).
 *
 */

static void process_ext_display_connection_info(struct bios_parser *bp)
{
	ATOM_OBJECT_TABLE *connector_tbl;
	uint32_t connector_tbl_offset;
	struct graphics_object_id object_id;
	ATOM_OBJECT *object;
	bool mxm_connector_found = false;
	bool null_entry_found = false;
	uint32_t i = 0;

	connector_tbl_offset = bp->object_info_tbl_offset +
			le16_to_cpu(bp->object_info_tbl.v1_1->usConnectorObjectTableOffset);
	connector_tbl = GET_IMAGE(ATOM_OBJECT_TABLE, connector_tbl_offset);

	/* Look for MXM connectors to determine whether we need patch the VBIOS
	 * connector info table. Look for null entries to determine whether we
	 * need to compact connector table. */
	for (i = 0; i < connector_tbl->ucNumberOfObjects; i++) {
		object = &connector_tbl->asObjects[i];
		object_id = object_id_from_bios_object_id(le16_to_cpu(object->usObjectID));

		if ((OBJECT_TYPE_CONNECTOR == object_id.type) &&
				(CONNECTOR_ID_MXM == object_id.id)) {
			/* Once we found MXM connector - we can break */
			mxm_connector_found = true;
			break;
		} else if (OBJECT_TYPE_CONNECTOR != object_id.type) {
			/* We need to continue looping - to check if MXM
			 * connector present */
			null_entry_found = true;
		}
	}

	/* Patch BIOS image */
	if (mxm_connector_found || null_entry_found) {
		uint32_t connectors_num = 0;
		uint8_t *original_bios;
		/* Step 1: Replace bios image with the new copy which will be
		 * patched */
		bp->base.bios_local_image = kzalloc(bp->base.bios_size,
						    GFP_KERNEL);
		if (bp->base.bios_local_image == NULL) {
			BREAK_TO_DEBUGGER();
			/* Failed to alloc bp->base.bios_local_image */
			return;
		}

		memmove(bp->base.bios_local_image, bp->base.bios, bp->base.bios_size);
		original_bios = bp->base.bios;
		bp->base.bios = bp->base.bios_local_image;
		connector_tbl =
				GET_IMAGE(ATOM_OBJECT_TABLE, connector_tbl_offset);

		/* Step 2: (only if MXM connector found) Patch BIOS image with
		 * info from external module */
		if (mxm_connector_found &&
		    patch_bios_image_from_ext_display_connection_info(bp) !=
						BP_RESULT_OK) {
			/* Patching the bios image has failed. We will copy
			 * again original image provided and afterwards
			 * only remove null entries */
			memmove(
					bp->base.bios_local_image,
					original_bios,
					bp->base.bios_size);
		}

		/* Step 3: Compact connector table (remove null entries, valid
		 * entries moved to beginning) */
		for (i = 0; i < connector_tbl->ucNumberOfObjects; i++) {
			object = &connector_tbl->asObjects[i];
			object_id = object_id_from_bios_object_id(
					le16_to_cpu(object->usObjectID));

			if (OBJECT_TYPE_CONNECTOR != object_id.type)
				continue;

			if (i != connectors_num) {
				memmove(
						&connector_tbl->
						asObjects[connectors_num],
						object,
						sizeof(ATOM_OBJECT));
			}
			++connectors_num;
		}
		connector_tbl->ucNumberOfObjects = (uint8_t)connectors_num;
	}
}

static void bios_parser_post_init(struct dc_bios *dcb)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);

	process_ext_display_connection_info(bp);
}

/**
 * bios_parser_set_scratch_critical_state
 *
 * @brief
 *  update critical state bit in VBIOS scratch register
 *
 * @param
 *  bool - to set or reset state
 */
static void bios_parser_set_scratch_critical_state(
	struct dc_bios *dcb,
	bool state)
{
	bios_set_scratch_critical_state(dcb, state);
}

/*
 * get_integrated_info_v8
 *
 * @brief
 * Get V8 integrated BIOS information
 *
 * @param
 * bios_parser *bp - [in]BIOS parser handler to get master data table
 * integrated_info *info - [out] store and output integrated info
 *
 * @return
 * enum bp_result - BP_RESULT_OK if information is available,
 *                  BP_RESULT_BADBIOSTABLE otherwise.
 */
static enum bp_result get_integrated_info_v8(
	struct bios_parser *bp,
	struct integrated_info *info)
{
	ATOM_INTEGRATED_SYSTEM_INFO_V1_8 *info_v8;
	uint32_t i;

	info_v8 = GET_IMAGE(ATOM_INTEGRATED_SYSTEM_INFO_V1_8,
			bp->master_data_tbl->ListOfDataTables.IntegratedSystemInfo);

	if (info_v8 == NULL)
		return BP_RESULT_BADBIOSTABLE;
	info->boot_up_engine_clock = le32_to_cpu(info_v8->ulBootUpEngineClock) * 10;
	info->dentist_vco_freq = le32_to_cpu(info_v8->ulDentistVCOFreq) * 10;
	info->boot_up_uma_clock = le32_to_cpu(info_v8->ulBootUpUMAClock) * 10;

	for (i = 0; i < NUMBER_OF_DISP_CLK_VOLTAGE; ++i) {
		/* Convert [10KHz] into [KHz] */
		info->disp_clk_voltage[i].max_supported_clk =
			le32_to_cpu(info_v8->sDISPCLK_Voltage[i].
				    ulMaximumSupportedCLK) * 10;
		info->disp_clk_voltage[i].voltage_index =
			le32_to_cpu(info_v8->sDISPCLK_Voltage[i].ulVoltageIndex);
	}

	info->boot_up_req_display_vector =
		le32_to_cpu(info_v8->ulBootUpReqDisplayVector);
	info->gpu_cap_info =
		le32_to_cpu(info_v8->ulGPUCapInfo);

	/*
	 * system_config: Bit[0] = 0 : PCIE power gating disabled
	 *                       = 1 : PCIE power gating enabled
	 *                Bit[1] = 0 : DDR-PLL shut down disabled
	 *                       = 1 : DDR-PLL shut down enabled
	 *                Bit[2] = 0 : DDR-PLL power down disabled
	 *                       = 1 : DDR-PLL power down enabled
	 */
	info->system_config = le32_to_cpu(info_v8->ulSystemConfig);
	info->cpu_cap_info = le32_to_cpu(info_v8->ulCPUCapInfo);
	info->boot_up_nb_voltage =
		le16_to_cpu(info_v8->usBootUpNBVoltage);
	info->ext_disp_conn_info_offset =
		le16_to_cpu(info_v8->usExtDispConnInfoOffset);
	info->memory_type = info_v8->ucMemoryType;
	info->ma_channel_number = info_v8->ucUMAChannelNumber;
	info->gmc_restore_reset_time =
		le32_to_cpu(info_v8->ulGMCRestoreResetTime);

	info->minimum_n_clk =
		le32_to_cpu(info_v8->ulNbpStateNClkFreq[0]);
	for (i = 1; i < 4; ++i)
		info->minimum_n_clk =
			info->minimum_n_clk < le32_to_cpu(info_v8->ulNbpStateNClkFreq[i]) ?
			info->minimum_n_clk : le32_to_cpu(info_v8->ulNbpStateNClkFreq[i]);

	info->idle_n_clk = le32_to_cpu(info_v8->ulIdleNClk);
	info->ddr_dll_power_up_time =
		le32_to_cpu(info_v8->ulDDR_DLL_PowerUpTime);
	info->ddr_pll_power_up_time =
		le32_to_cpu(info_v8->ulDDR_PLL_PowerUpTime);
	info->pcie_clk_ss_type = le16_to_cpu(info_v8->usPCIEClkSSType);
	info->lvds_ss_percentage =
		le16_to_cpu(info_v8->usLvdsSSPercentage);
	info->lvds_sspread_rate_in_10hz =
		le16_to_cpu(info_v8->usLvdsSSpreadRateIn10Hz);
	info->hdmi_ss_percentage =
		le16_to_cpu(info_v8->usHDMISSPercentage);
	info->hdmi_sspread_rate_in_10hz =
		le16_to_cpu(info_v8->usHDMISSpreadRateIn10Hz);
	info->dvi_ss_percentage =
		le16_to_cpu(info_v8->usDVISSPercentage);
	info->dvi_sspread_rate_in_10_hz =
		le16_to_cpu(info_v8->usDVISSpreadRateIn10Hz);

	info->max_lvds_pclk_freq_in_single_link =
		le16_to_cpu(info_v8->usMaxLVDSPclkFreqInSingleLink);
	info->lvds_misc = info_v8->ucLvdsMisc;
	info->lvds_pwr_on_seq_dig_on_to_de_in_4ms =
		info_v8->ucLVDSPwrOnSeqDIGONtoDE_in4Ms;
	info->lvds_pwr_on_seq_de_to_vary_bl_in_4ms =
		info_v8->ucLVDSPwrOnSeqDEtoVARY_BL_in4Ms;
	info->lvds_pwr_on_seq_vary_bl_to_blon_in_4ms =
		info_v8->ucLVDSPwrOnSeqVARY_BLtoBLON_in4Ms;
	info->lvds_pwr_off_seq_vary_bl_to_de_in4ms =
		info_v8->ucLVDSPwrOffSeqVARY_BLtoDE_in4Ms;
	info->lvds_pwr_off_seq_de_to_dig_on_in4ms =
		info_v8->ucLVDSPwrOffSeqDEtoDIGON_in4Ms;
	info->lvds_pwr_off_seq_blon_to_vary_bl_in_4ms =
		info_v8->ucLVDSPwrOffSeqBLONtoVARY_BL_in4Ms;
	info->lvds_off_to_on_delay_in_4ms =
		info_v8->ucLVDSOffToOnDelay_in4Ms;
	info->lvds_bit_depth_control_val =
		le32_to_cpu(info_v8->ulLCDBitDepthControlVal);

	for (i = 0; i < NUMBER_OF_AVAILABLE_SCLK; ++i) {
		/* Convert [10KHz] into [KHz] */
		info->avail_s_clk[i].supported_s_clk =
			le32_to_cpu(info_v8->sAvail_SCLK[i].ulSupportedSCLK) * 10;
		info->avail_s_clk[i].voltage_index =
			le16_to_cpu(info_v8->sAvail_SCLK[i].usVoltageIndex);
		info->avail_s_clk[i].voltage_id =
			le16_to_cpu(info_v8->sAvail_SCLK[i].usVoltageID);
	}

	for (i = 0; i < NUMBER_OF_UCHAR_FOR_GUID; ++i) {
		info->ext_disp_conn_info.gu_id[i] =
			info_v8->sExtDispConnInfo.ucGuid[i];
	}

	for (i = 0; i < MAX_NUMBER_OF_EXT_DISPLAY_PATH; ++i) {
		info->ext_disp_conn_info.path[i].device_connector_id =
			object_id_from_bios_object_id(
				le16_to_cpu(info_v8->sExtDispConnInfo.sPath[i].usDeviceConnector));

		info->ext_disp_conn_info.path[i].ext_encoder_obj_id =
			object_id_from_bios_object_id(
				le16_to_cpu(info_v8->sExtDispConnInfo.sPath[i].usExtEncoderObjId));

		info->ext_disp_conn_info.path[i].device_tag =
			le16_to_cpu(info_v8->sExtDispConnInfo.sPath[i].usDeviceTag);
		info->ext_disp_conn_info.path[i].device_acpi_enum =
			le16_to_cpu(info_v8->sExtDispConnInfo.sPath[i].usDeviceACPIEnum);
		info->ext_disp_conn_info.path[i].ext_aux_ddc_lut_index =
			info_v8->sExtDispConnInfo.sPath[i].ucExtAUXDDCLutIndex;
		info->ext_disp_conn_info.path[i].ext_hpd_pin_lut_index =
			info_v8->sExtDispConnInfo.sPath[i].ucExtHPDPINLutIndex;
		info->ext_disp_conn_info.path[i].channel_mapping.raw =
			info_v8->sExtDispConnInfo.sPath[i].ucChannelMapping;
	}
	info->ext_disp_conn_info.checksum =
		info_v8->sExtDispConnInfo.ucChecksum;

	return BP_RESULT_OK;
}

/*
 * get_integrated_info_v8
 *
 * @brief
 * Get V8 integrated BIOS information
 *
 * @param
 * bios_parser *bp - [in]BIOS parser handler to get master data table
 * integrated_info *info - [out] store and output integrated info
 *
 * @return
 * enum bp_result - BP_RESULT_OK if information is available,
 *                  BP_RESULT_BADBIOSTABLE otherwise.
 */
static enum bp_result get_integrated_info_v9(
	struct bios_parser *bp,
	struct integrated_info *info)
{
	ATOM_INTEGRATED_SYSTEM_INFO_V1_9 *info_v9;
	uint32_t i;

	info_v9 = GET_IMAGE(ATOM_INTEGRATED_SYSTEM_INFO_V1_9,
			bp->master_data_tbl->ListOfDataTables.IntegratedSystemInfo);

	if (!info_v9)
		return BP_RESULT_BADBIOSTABLE;

	info->boot_up_engine_clock = le32_to_cpu(info_v9->ulBootUpEngineClock) * 10;
	info->dentist_vco_freq = le32_to_cpu(info_v9->ulDentistVCOFreq) * 10;
	info->boot_up_uma_clock = le32_to_cpu(info_v9->ulBootUpUMAClock) * 10;

	for (i = 0; i < NUMBER_OF_DISP_CLK_VOLTAGE; ++i) {
		/* Convert [10KHz] into [KHz] */
		info->disp_clk_voltage[i].max_supported_clk =
			le32_to_cpu(info_v9->sDISPCLK_Voltage[i].ulMaximumSupportedCLK) * 10;
		info->disp_clk_voltage[i].voltage_index =
			le32_to_cpu(info_v9->sDISPCLK_Voltage[i].ulVoltageIndex);
	}

	info->boot_up_req_display_vector =
		le32_to_cpu(info_v9->ulBootUpReqDisplayVector);
	info->gpu_cap_info = le32_to_cpu(info_v9->ulGPUCapInfo);

	/*
	 * system_config: Bit[0] = 0 : PCIE power gating disabled
	 *                       = 1 : PCIE power gating enabled
	 *                Bit[1] = 0 : DDR-PLL shut down disabled
	 *                       = 1 : DDR-PLL shut down enabled
	 *                Bit[2] = 0 : DDR-PLL power down disabled
	 *                       = 1 : DDR-PLL power down enabled
	 */
	info->system_config = le32_to_cpu(info_v9->ulSystemConfig);
	info->cpu_cap_info = le32_to_cpu(info_v9->ulCPUCapInfo);
	info->boot_up_nb_voltage = le16_to_cpu(info_v9->usBootUpNBVoltage);
	info->ext_disp_conn_info_offset = le16_to_cpu(info_v9->usExtDispConnInfoOffset);
	info->memory_type = info_v9->ucMemoryType;
	info->ma_channel_number = info_v9->ucUMAChannelNumber;
	info->gmc_restore_reset_time = le32_to_cpu(info_v9->ulGMCRestoreResetTime);

	info->minimum_n_clk = le32_to_cpu(info_v9->ulNbpStateNClkFreq[0]);
	for (i = 1; i < 4; ++i)
		info->minimum_n_clk =
			info->minimum_n_clk < le32_to_cpu(info_v9->ulNbpStateNClkFreq[i]) ?
			info->minimum_n_clk : le32_to_cpu(info_v9->ulNbpStateNClkFreq[i]);

	info->idle_n_clk = le32_to_cpu(info_v9->ulIdleNClk);
	info->ddr_dll_power_up_time = le32_to_cpu(info_v9->ulDDR_DLL_PowerUpTime);
	info->ddr_pll_power_up_time = le32_to_cpu(info_v9->ulDDR_PLL_PowerUpTime);
	info->pcie_clk_ss_type = le16_to_cpu(info_v9->usPCIEClkSSType);
	info->lvds_ss_percentage = le16_to_cpu(info_v9->usLvdsSSPercentage);
	info->lvds_sspread_rate_in_10hz = le16_to_cpu(info_v9->usLvdsSSpreadRateIn10Hz);
	info->hdmi_ss_percentage = le16_to_cpu(info_v9->usHDMISSPercentage);
	info->hdmi_sspread_rate_in_10hz = le16_to_cpu(info_v9->usHDMISSpreadRateIn10Hz);
	info->dvi_ss_percentage = le16_to_cpu(info_v9->usDVISSPercentage);
	info->dvi_sspread_rate_in_10_hz = le16_to_cpu(info_v9->usDVISSpreadRateIn10Hz);

	info->max_lvds_pclk_freq_in_single_link =
		le16_to_cpu(info_v9->usMaxLVDSPclkFreqInSingleLink);
	info->lvds_misc = info_v9->ucLvdsMisc;
	info->lvds_pwr_on_seq_dig_on_to_de_in_4ms =
		info_v9->ucLVDSPwrOnSeqDIGONtoDE_in4Ms;
	info->lvds_pwr_on_seq_de_to_vary_bl_in_4ms =
		info_v9->ucLVDSPwrOnSeqDEtoVARY_BL_in4Ms;
	info->lvds_pwr_on_seq_vary_bl_to_blon_in_4ms =
		info_v9->ucLVDSPwrOnSeqVARY_BLtoBLON_in4Ms;
	info->lvds_pwr_off_seq_vary_bl_to_de_in4ms =
		info_v9->ucLVDSPwrOffSeqVARY_BLtoDE_in4Ms;
	info->lvds_pwr_off_seq_de_to_dig_on_in4ms =
		info_v9->ucLVDSPwrOffSeqDEtoDIGON_in4Ms;
	info->lvds_pwr_off_seq_blon_to_vary_bl_in_4ms =
		info_v9->ucLVDSPwrOffSeqBLONtoVARY_BL_in4Ms;
	info->lvds_off_to_on_delay_in_4ms =
		info_v9->ucLVDSOffToOnDelay_in4Ms;
	info->lvds_bit_depth_control_val =
		le32_to_cpu(info_v9->ulLCDBitDepthControlVal);

	for (i = 0; i < NUMBER_OF_AVAILABLE_SCLK; ++i) {
		/* Convert [10KHz] into [KHz] */
		info->avail_s_clk[i].supported_s_clk =
			le32_to_cpu(info_v9->sAvail_SCLK[i].ulSupportedSCLK) * 10;
		info->avail_s_clk[i].voltage_index =
			le16_to_cpu(info_v9->sAvail_SCLK[i].usVoltageIndex);
		info->avail_s_clk[i].voltage_id =
			le16_to_cpu(info_v9->sAvail_SCLK[i].usVoltageID);
	}

	for (i = 0; i < NUMBER_OF_UCHAR_FOR_GUID; ++i) {
		info->ext_disp_conn_info.gu_id[i] =
			info_v9->sExtDispConnInfo.ucGuid[i];
	}

	for (i = 0; i < MAX_NUMBER_OF_EXT_DISPLAY_PATH; ++i) {
		info->ext_disp_conn_info.path[i].device_connector_id =
			object_id_from_bios_object_id(
				le16_to_cpu(info_v9->sExtDispConnInfo.sPath[i].usDeviceConnector));

		info->ext_disp_conn_info.path[i].ext_encoder_obj_id =
			object_id_from_bios_object_id(
				le16_to_cpu(info_v9->sExtDispConnInfo.sPath[i].usExtEncoderObjId));

		info->ext_disp_conn_info.path[i].device_tag =
			le16_to_cpu(info_v9->sExtDispConnInfo.sPath[i].usDeviceTag);
		info->ext_disp_conn_info.path[i].device_acpi_enum =
			le16_to_cpu(info_v9->sExtDispConnInfo.sPath[i].usDeviceACPIEnum);
		info->ext_disp_conn_info.path[i].ext_aux_ddc_lut_index =
			info_v9->sExtDispConnInfo.sPath[i].ucExtAUXDDCLutIndex;
		info->ext_disp_conn_info.path[i].ext_hpd_pin_lut_index =
			info_v9->sExtDispConnInfo.sPath[i].ucExtHPDPINLutIndex;
		info->ext_disp_conn_info.path[i].channel_mapping.raw =
			info_v9->sExtDispConnInfo.sPath[i].ucChannelMapping;
	}
	info->ext_disp_conn_info.checksum =
		info_v9->sExtDispConnInfo.ucChecksum;

	return BP_RESULT_OK;
}

/*
 * construct_integrated_info
 *
 * @brief
 * Get integrated BIOS information based on table revision
 *
 * @param
 * bios_parser *bp - [in]BIOS parser handler to get master data table
 * integrated_info *info - [out] store and output integrated info
 *
 * @return
 * enum bp_result - BP_RESULT_OK if information is available,
 *                  BP_RESULT_BADBIOSTABLE otherwise.
 */
static enum bp_result construct_integrated_info(
	struct bios_parser *bp,
	struct integrated_info *info)
{
	enum bp_result result = BP_RESULT_BADBIOSTABLE;

	ATOM_COMMON_TABLE_HEADER *header;
	struct atom_data_revision revision;

	if (bp->master_data_tbl->ListOfDataTables.IntegratedSystemInfo) {
		header = GET_IMAGE(ATOM_COMMON_TABLE_HEADER,
				bp->master_data_tbl->ListOfDataTables.IntegratedSystemInfo);

		get_atom_data_table_revision(header, &revision);

		/* Don't need to check major revision as they are all 1 */
		switch (revision.minor) {
		case 8:
			result = get_integrated_info_v8(bp, info);
			break;
		case 9:
			result = get_integrated_info_v9(bp, info);
			break;
		default:
			return result;

		}
	}

	/* Sort voltage table from low to high*/
	if (result == BP_RESULT_OK) {
		struct clock_voltage_caps temp = {0, 0};
		uint32_t i;
		uint32_t j;

		for (i = 1; i < NUMBER_OF_DISP_CLK_VOLTAGE; ++i) {
			for (j = i; j > 0; --j) {
				if (
						info->disp_clk_voltage[j].max_supported_clk <
						info->disp_clk_voltage[j-1].max_supported_clk) {
					/* swap j and j - 1*/
					temp = info->disp_clk_voltage[j-1];
					info->disp_clk_voltage[j-1] =
							info->disp_clk_voltage[j];
					info->disp_clk_voltage[j] = temp;
				}
			}
		}

	}

	return result;
}

static struct integrated_info *bios_parser_create_integrated_info(
	struct dc_bios *dcb)
{
	struct bios_parser *bp = BP_FROM_DCB(dcb);
	struct integrated_info *info = NULL;

	info = kzalloc(sizeof(struct integrated_info), GFP_KERNEL);

	if (info == NULL) {
		ASSERT_CRITICAL(0);
		return NULL;
	}

	if (construct_integrated_info(bp, info) == BP_RESULT_OK)
		return info;

	kfree(info);

	return NULL;
}

enum bp_result update_slot_layout_info(
	struct dc_bios *dcb,
	unsigned int i,
	struct slot_layout_info *slot_layout_info,
	unsigned int record_offset)
{
	unsigned int j;
	struct bios_parser *bp;
	ATOM_BRACKET_LAYOUT_RECORD *record;
	ATOM_COMMON_RECORD_HEADER *record_header;
	enum bp_result result = BP_RESULT_NORECORD;

	bp = BP_FROM_DCB(dcb);
	record = NULL;
	record_header = NULL;

	for (;;) {

		record_header = (ATOM_COMMON_RECORD_HEADER *)
			GET_IMAGE(ATOM_COMMON_RECORD_HEADER, record_offset);
		if (record_header == NULL) {
			result = BP_RESULT_BADBIOSTABLE;
			break;
		}

		/* the end of the list */
		if (record_header->ucRecordType == 0xff ||
			record_header->ucRecordSize == 0)	{
			break;
		}

		if (record_header->ucRecordType ==
			ATOM_BRACKET_LAYOUT_RECORD_TYPE &&
			sizeof(ATOM_BRACKET_LAYOUT_RECORD)
			<= record_header->ucRecordSize) {
			record = (ATOM_BRACKET_LAYOUT_RECORD *)
				(record_header);
			result = BP_RESULT_OK;
			break;
		}

		record_offset += record_header->ucRecordSize;
	}

	/* return if the record not found */
	if (result != BP_RESULT_OK)
		return result;

	/* get slot sizes */
	slot_layout_info->length = record->ucLength;
	slot_layout_info->width = record->ucWidth;

	/* get info for each connector in the slot */
	slot_layout_info->num_of_connectors = record->ucConnNum;
	for (j = 0; j < slot_layout_info->num_of_connectors; ++j) {
		slot_layout_info->connectors[j].connector_type =
			(enum connector_layout_type)
			(record->asConnInfo[j].ucConnectorType);
		switch (record->asConnInfo[j].ucConnectorType) {
		case CONNECTOR_TYPE_DVI_D:
			slot_layout_info->connectors[j].connector_type =
				CONNECTOR_LAYOUT_TYPE_DVI_D;
			slot_layout_info->connectors[j].length =
				CONNECTOR_SIZE_DVI;
			break;

		case CONNECTOR_TYPE_HDMI:
			slot_layout_info->connectors[j].connector_type =
				CONNECTOR_LAYOUT_TYPE_HDMI;
			slot_layout_info->connectors[j].length =
				CONNECTOR_SIZE_HDMI;
			break;

		case CONNECTOR_TYPE_DISPLAY_PORT:
			slot_layout_info->connectors[j].connector_type =
				CONNECTOR_LAYOUT_TYPE_DP;
			slot_layout_info->connectors[j].length =
				CONNECTOR_SIZE_DP;
			break;

		case CONNECTOR_TYPE_MINI_DISPLAY_PORT:
			slot_layout_info->connectors[j].connector_type =
				CONNECTOR_LAYOUT_TYPE_MINI_DP;
			slot_layout_info->connectors[j].length =
				CONNECTOR_SIZE_MINI_DP;
			break;

		default:
			slot_layout_info->connectors[j].connector_type =
				CONNECTOR_LAYOUT_TYPE_UNKNOWN;
			slot_layout_info->connectors[j].length =
				CONNECTOR_SIZE_UNKNOWN;
		}

		slot_layout_info->connectors[j].position =
			record->asConnInfo[j].ucPosition;
		slot_layout_info->connectors[j].connector_id =
			object_id_from_bios_object_id(
				record->asConnInfo[j].usConnectorObjectId);
	}
	return result;
}


enum bp_result get_bracket_layout_record(
	struct dc_bios *dcb,
	unsigned int bracket_layout_id,
	struct slot_layout_info *slot_layout_info)
{
	unsigned int i;
	unsigned int record_offset;
	struct bios_parser *bp;
	enum bp_result result;
	ATOM_OBJECT *object;
	ATOM_OBJECT_TABLE *object_table;
	unsigned int genericTableOffset;

	bp = BP_FROM_DCB(dcb);
	object = NULL;
	if (slot_layout_info == NULL) {
		DC_LOG_DETECTION_EDID_PARSER("Invalid slot_layout_info\n");
		return BP_RESULT_BADINPUT;
	}


	genericTableOffset = bp->object_info_tbl_offset +
		bp->object_info_tbl.v1_3->usMiscObjectTableOffset;
	object_table = (ATOM_OBJECT_TABLE *)
		GET_IMAGE(ATOM_OBJECT_TABLE, genericTableOffset);
	if (!object_table)
		return BP_RESULT_FAILURE;

	result = BP_RESULT_NORECORD;
	for (i = 0; i < object_table->ucNumberOfObjects; ++i) {

		if (bracket_layout_id ==
			object_table->asObjects[i].usObjectID) {

			object = &object_table->asObjects[i];
			record_offset = object->usRecordOffset +
				bp->object_info_tbl_offset;

			result = update_slot_layout_info(dcb, i,
				slot_layout_info, record_offset);
			break;
		}
	}
	return result;
}

static enum bp_result bios_get_board_layout_info(
	struct dc_bios *dcb,
	struct board_layout_info *board_layout_info)
{
	unsigned int i;
	struct bios_parser *bp;
	enum bp_result record_result;

	const unsigned int slot_index_to_vbios_id[MAX_BOARD_SLOTS] = {
		GENERICOBJECT_BRACKET_LAYOUT_ENUM_ID1,
		GENERICOBJECT_BRACKET_LAYOUT_ENUM_ID2,
		0, 0
	};

	bp = BP_FROM_DCB(dcb);
	if (board_layout_info == NULL) {
		DC_LOG_DETECTION_EDID_PARSER("Invalid board_layout_info\n");
		return BP_RESULT_BADINPUT;
	}

	board_layout_info->num_of_slots = 0;

	for (i = 0; i < MAX_BOARD_SLOTS; ++i) {
		record_result = get_bracket_layout_record(dcb,
			slot_index_to_vbios_id[i],
			&board_layout_info->slots[i]);

		if (record_result == BP_RESULT_NORECORD && i > 0)
			break; /* no more slots present in bios */
		else if (record_result != BP_RESULT_OK)
			return record_result;  /* fail */

		++board_layout_info->num_of_slots;
	}

	/* all data is valid */
	board_layout_info->is_number_of_slots_valid = 1;
	board_layout_info->is_slots_size_valid = 1;
	board_layout_info->is_connector_offsets_valid = 1;
	board_layout_info->is_connector_lengths_valid = 1;

	return BP_RESULT_OK;
}

/******************************************************************************/

static const struct dc_vbios_funcs vbios_funcs = {
	.get_connectors_number = bios_parser_get_connectors_number,

	.get_encoder_id = bios_parser_get_encoder_id,

	.get_connector_id = bios_parser_get_connector_id,

	.get_dst_number = bios_parser_get_dst_number,

	.get_src_obj = bios_parser_get_src_obj,

	.get_dst_obj = bios_parser_get_dst_obj,

	.get_i2c_info = bios_parser_get_i2c_info,

	.get_voltage_ddc_info = bios_parser_get_voltage_ddc_info,

	.get_thermal_ddc_info = bios_parser_get_thermal_ddc_info,

	.get_hpd_info = bios_parser_get_hpd_info,

	.get_device_tag = bios_parser_get_device_tag,

	.get_firmware_info = bios_parser_get_firmware_info,

	.get_spread_spectrum_info = bios_parser_get_spread_spectrum_info,

	.get_ss_entry_number = bios_parser_get_ss_entry_number,

	.get_embedded_panel_info = bios_parser_get_embedded_panel_info,

	.get_gpio_pin_info = bios_parser_get_gpio_pin_info,

	.get_encoder_cap_info = bios_parser_get_encoder_cap_info,

	/* bios scratch register communication */
	.is_accelerated_mode = bios_is_accelerated_mode,
	.get_vga_enabled_displays = bios_get_vga_enabled_displays,

	.set_scratch_critical_state = bios_parser_set_scratch_critical_state,

	.is_device_id_supported = bios_parser_is_device_id_supported,

	/* COMMANDS */
	.encoder_control = bios_parser_encoder_control,

	.transmitter_control = bios_parser_transmitter_control,

	.crt_control = bios_parser_crt_control,  /* not used in DAL3.  keep for now in case we need to support VGA on Bonaire */

	.enable_crtc = bios_parser_enable_crtc,

	.adjust_pixel_clock = bios_parser_adjust_pixel_clock,

	.set_pixel_clock = bios_parser_set_pixel_clock,

	.set_dce_clock = bios_parser_set_dce_clock,

	.enable_spread_spectrum_on_ppll = bios_parser_enable_spread_spectrum_on_ppll,

	.program_crtc_timing = bios_parser_program_crtc_timing, /* still use.  should probably retire and program directly */

	.crtc_source_select = bios_parser_crtc_source_select,  /* still use.  should probably retire and program directly */

	.program_display_engine_pll = bios_parser_program_display_engine_pll,

	.enable_disp_power_gating = bios_parser_enable_disp_power_gating,

	/* SW init and patch */
	.post_init = bios_parser_post_init,  /* patch vbios table for mxm module by reading i2c */

	.bios_parser_destroy = bios_parser_destroy,

	.get_board_layout_info = bios_get_board_layout_info,
};

static bool bios_parser_construct(
	struct bios_parser *bp,
	struct bp_init_data *init,
	enum dce_version dce_version)
{
	uint16_t *rom_header_offset = NULL;
	ATOM_ROM_HEADER *rom_header = NULL;
	ATOM_OBJECT_HEADER *object_info_tbl;
	struct atom_data_revision tbl_rev = {0};

	if (!init)
		return false;

	if (!init->bios)
		return false;

	bp->base.funcs = &vbios_funcs;
	bp->base.bios = init->bios;
	bp->base.bios_size = bp->base.bios[BIOS_IMAGE_SIZE_OFFSET] * BIOS_IMAGE_SIZE_UNIT;

	bp->base.ctx = init->ctx;
	bp->base.bios_local_image = NULL;

	rom_header_offset =
	GET_IMAGE(uint16_t, OFFSET_TO_POINTER_TO_ATOM_ROM_HEADER);

	if (!rom_header_offset)
		return false;

	rom_header = GET_IMAGE(ATOM_ROM_HEADER, *rom_header_offset);

	if (!rom_header)
		return false;

	get_atom_data_table_revision(&rom_header->sHeader, &tbl_rev);
	if (tbl_rev.major >= 2 && tbl_rev.minor >= 2)
		return false;

	bp->master_data_tbl =
	GET_IMAGE(ATOM_MASTER_DATA_TABLE,
		rom_header->usMasterDataTableOffset);

	if (!bp->master_data_tbl)
		return false;

	bp->object_info_tbl_offset = DATA_TABLES(Object_Header);

	if (!bp->object_info_tbl_offset)
		return false;

	object_info_tbl =
	GET_IMAGE(ATOM_OBJECT_HEADER, bp->object_info_tbl_offset);

	if (!object_info_tbl)
		return false;

	get_atom_data_table_revision(&object_info_tbl->sHeader,
		&bp->object_info_tbl.revision);

	if (bp->object_info_tbl.revision.major == 1
		&& bp->object_info_tbl.revision.minor >= 3) {
		ATOM_OBJECT_HEADER_V3 *tbl_v3;

		tbl_v3 = GET_IMAGE(ATOM_OBJECT_HEADER_V3,
			bp->object_info_tbl_offset);
		if (!tbl_v3)
			return false;

		bp->object_info_tbl.v1_3 = tbl_v3;
	} else if (bp->object_info_tbl.revision.major == 1
		&& bp->object_info_tbl.revision.minor >= 1)
		bp->object_info_tbl.v1_1 = object_info_tbl;
	else
		return false;

	dal_bios_parser_init_cmd_tbl(bp);
	dal_bios_parser_init_cmd_tbl_helper(&bp->cmd_helper, dce_version);

	bp->base.integrated_info = bios_parser_create_integrated_info(&bp->base);

	return true;
}

/******************************************************************************/
