/* Copyright (c) 2010-2015, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
 * only version 2 as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 */

#include "hdmi.h"
#include <linux/qcom_scm.h>

#define HDCP_REG_ENABLE 0x01
#define HDCP_REG_DISABLE 0x00
#define HDCP_PORT_ADDR 0x74

#define HDCP_INT_STATUS_MASK ( \
		HDMI_HDCP_INT_CTRL_AUTH_SUCCESS_INT | \
		HDMI_HDCP_INT_CTRL_AUTH_FAIL_INT | \
		HDMI_HDCP_INT_CTRL_AUTH_XFER_REQ_INT | \
		HDMI_HDCP_INT_CTRL_AUTH_XFER_DONE_INT)

#define AUTH_WORK_RETRIES_TIME 100
#define AUTH_RETRIES_TIME 30

/* QFPROM Registers for HDMI/HDCP */
#define QFPROM_RAW_FEAT_CONFIG_ROW0_LSB  0x000000F8
#define QFPROM_RAW_FEAT_CONFIG_ROW0_MSB  0x000000FC
#define HDCP_KSV_LSB                     0x000060D8
#define HDCP_KSV_MSB                     0x000060DC

enum DS_TYPE {  /* type of downstream device */
	DS_UNKNOWN,
	DS_RECEIVER,
	DS_REPEATER,
};

enum hdmi_hdcp_state {
	HDCP_STATE_NO_AKSV,
	HDCP_STATE_INACTIVE,
	HDCP_STATE_AUTHENTICATING,
	HDCP_STATE_AUTHENTICATED,
	HDCP_STATE_AUTH_FAILED
};

struct hdmi_hdcp_reg_data {
	u32 reg_id;
	u32 off;
	char *name;
	u32 reg_val;
};

struct hdmi_hdcp_ctrl {
	struct hdmi *hdmi;
	u32 auth_retries;
	bool tz_hdcp;
	enum hdmi_hdcp_state hdcp_state;
	struct work_struct hdcp_auth_work;
	struct work_struct hdcp_reauth_work;

#define AUTH_ABORT_EV 1
#define AUTH_RESULT_RDY_EV 2
	unsigned long auth_event;
	wait_queue_head_t auth_event_queue;

	u32 ksv_fifo_w_index;
	/*
	 * store aksv from qfprom
	 */
	u32 aksv_lsb;
	u32 aksv_msb;
	bool aksv_valid;
	u32 ds_type;
	u32 bksv_lsb;
	u32 bksv_msb;
	u8 dev_count;
	u8 depth;
	u8 ksv_list[5 * 127];
	bool max_cascade_exceeded;
	bool max_dev_exceeded;
};

static int msm_hdmi_ddc_read(struct hdmi *hdmi, u16 addr, u8 offset,
	u8 *data, u16 data_len)
{
	int rc;
	int retry = 5;
	struct i2c_msg msgs[] = {
		{
			.addr	= addr >> 1,
			.flags	= 0,
			.len	= 1,
			.buf	= &offset,
		}, {
			.addr	= addr >> 1,
			.flags	= I2C_M_RD,
			.len	= data_len,
			.buf	= data,
		}
	};

	DBG("Start DDC read");
retry:
	rc = i2c_transfer(hdmi->i2c, msgs, 2);

	retry--;
	if (rc == 2)
		rc = 0;
	else if (retry > 0)
		goto retry;
	else
		rc = -EIO;

	DBG("End DDC read %d", rc);

	return rc;
}

#define HDCP_DDC_WRITE_MAX_BYTE_NUM 32

static int msm_hdmi_ddc_write(struct hdmi *hdmi, u16 addr, u8 offset,
	u8 *data, u16 data_len)
{
	int rc;
	int retry = 10;
	u8 buf[HDCP_DDC_WRITE_MAX_BYTE_NUM];
	struct i2c_msg msgs[] = {
		{
			.addr	= addr >> 1,
			.flags	= 0,
			.len	= 1,
		}
	};

	DBG("Start DDC write");
	if (data_len > (HDCP_DDC_WRITE_MAX_BYTE_NUM - 1)) {
		pr_err("%s: write size too big\n", __func__);
		return -ERANGE;
	}

	buf[0] = offset;
	memcpy(&buf[1], data, data_len);
	msgs[0].buf = buf;
	msgs[0].len = data_len + 1;
retry:
	rc = i2c_transfer(hdmi->i2c, msgs, 1);

	retry--;
	if (rc == 1)
		rc = 0;
	else if (retry > 0)
		goto retry;
	else
		rc = -EIO;

	DBG("End DDC write %d", rc);

	return rc;
}

static int msm_hdmi_hdcp_scm_wr(struct hdmi_hdcp_ctrl *hdcp_ctrl, u32 *preg,
	u32 *pdata, u32 count)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	struct qcom_scm_hdcp_req scm_buf[QCOM_SCM_HDCP_MAX_REQ_CNT];
	u32 resp, phy_addr, idx = 0;
	int i, ret = 0;

	WARN_ON(!pdata || !preg || (count == 0));

	if (hdcp_ctrl->tz_hdcp) {
		phy_addr = (u32)hdmi->mmio_phy_addr;

		while (count) {
			memset(scm_buf, 0, sizeof(scm_buf));
			for (i = 0; i < count && i < QCOM_SCM_HDCP_MAX_REQ_CNT;
				i++) {
				scm_buf[i].addr = phy_addr + preg[idx];
				scm_buf[i].val  = pdata[idx];
				idx++;
			}
			ret = qcom_scm_hdcp_req(scm_buf, i, &resp);

			if (ret || resp) {
				pr_err("%s: error: scm_call ret=%d resp=%u\n",
					__func__, ret, resp);
				ret = -EINVAL;
				break;
			}

			count -= i;
		}
	} else {
		for (i = 0; i < count; i++)
			hdmi_write(hdmi, preg[i], pdata[i]);
	}

	return ret;
}

void msm_hdmi_hdcp_irq(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg_val, hdcp_int_status;
	unsigned long flags;

	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_INT_CTRL);
	hdcp_int_status = reg_val & HDCP_INT_STATUS_MASK;
	if (!hdcp_int_status) {
		spin_unlock_irqrestore(&hdmi->reg_lock, flags);
		return;
	}
	/* Clear Interrupts */
	reg_val |= hdcp_int_status << 1;
	/* Clear AUTH_FAIL_INFO as well */
	if (hdcp_int_status & HDMI_HDCP_INT_CTRL_AUTH_FAIL_INT)
		reg_val |= HDMI_HDCP_INT_CTRL_AUTH_FAIL_INFO_ACK;
	hdmi_write(hdmi, REG_HDMI_HDCP_INT_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	DBG("hdcp irq %x", hdcp_int_status);

	if (hdcp_int_status & HDMI_HDCP_INT_CTRL_AUTH_SUCCESS_INT) {
		pr_info("%s:AUTH_SUCCESS_INT received\n", __func__);
		if (HDCP_STATE_AUTHENTICATING == hdcp_ctrl->hdcp_state) {
			set_bit(AUTH_RESULT_RDY_EV, &hdcp_ctrl->auth_event);
			wake_up_all(&hdcp_ctrl->auth_event_queue);
		}
	}

	if (hdcp_int_status & HDMI_HDCP_INT_CTRL_AUTH_FAIL_INT) {
		reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
		pr_info("%s: AUTH_FAIL_INT rcvd, LINK0_STATUS=0x%08x\n",
			__func__, reg_val);
		if (HDCP_STATE_AUTHENTICATED == hdcp_ctrl->hdcp_state)
			queue_work(hdmi->workq, &hdcp_ctrl->hdcp_reauth_work);
		else if (HDCP_STATE_AUTHENTICATING ==
				hdcp_ctrl->hdcp_state) {
			set_bit(AUTH_RESULT_RDY_EV, &hdcp_ctrl->auth_event);
			wake_up_all(&hdcp_ctrl->auth_event_queue);
		}
	}
}

static int msm_hdmi_hdcp_msleep(struct hdmi_hdcp_ctrl *hdcp_ctrl, u32 ms, u32 ev)
{
	int rc;

	rc = wait_event_timeout(hdcp_ctrl->auth_event_queue,
		!!test_bit(ev, &hdcp_ctrl->auth_event),
		msecs_to_jiffies(ms));
	if (rc) {
		pr_info("%s: msleep is canceled by event %d\n",
				__func__, ev);
		clear_bit(ev, &hdcp_ctrl->auth_event);
		return -ECANCELED;
	}

	return 0;
}

static int msm_hdmi_hdcp_read_validate_aksv(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;

	/* Fetch aksv from QFPROM, this info should be public. */
	hdcp_ctrl->aksv_lsb = hdmi_qfprom_read(hdmi, HDCP_KSV_LSB);
	hdcp_ctrl->aksv_msb = hdmi_qfprom_read(hdmi, HDCP_KSV_MSB);

	/* check there are 20 ones in AKSV */
	if ((hweight32(hdcp_ctrl->aksv_lsb) + hweight32(hdcp_ctrl->aksv_msb))
			!= 20) {
		pr_err("%s: AKSV QFPROM doesn't have 20 1's, 20 0's\n",
			__func__);
		pr_err("%s: QFPROM AKSV chk failed (AKSV=%02x%08x)\n",
			__func__, hdcp_ctrl->aksv_msb,
			hdcp_ctrl->aksv_lsb);
		return -EINVAL;
	}
	DBG("AKSV=%02x%08x", hdcp_ctrl->aksv_msb, hdcp_ctrl->aksv_lsb);

	return 0;
}

static int msm_reset_hdcp_ddc_failures(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg_val, failure, nack0;
	int rc = 0;

	/* Check for any DDC transfer failures */
	reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_DDC_STATUS);
	failure = reg_val & HDMI_HDCP_DDC_STATUS_FAILED;
	nack0 = reg_val & HDMI_HDCP_DDC_STATUS_NACK0;
	DBG("HDCP_DDC_STATUS=0x%x, FAIL=%d, NACK0=%d",
		reg_val, failure, nack0);

	if (failure) {
		/*
		 * Indicates that the last HDCP HW DDC transfer failed.
		 * This occurs when a transfer is attempted with HDCP DDC
		 * disabled (HDCP_DDC_DISABLE=1) or the number of retries
		 * matches HDCP_DDC_RETRY_CNT.
		 * Failure occurred,  let's clear it.
		 */
		DBG("DDC failure detected");

		/* First, Disable DDC */
		hdmi_write(hdmi, REG_HDMI_HDCP_DDC_CTRL_0,
			HDMI_HDCP_DDC_CTRL_0_DISABLE);

		/* ACK the Failure to Clear it */
		reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_DDC_CTRL_1);
		reg_val |= HDMI_HDCP_DDC_CTRL_1_FAILED_ACK;
		hdmi_write(hdmi, REG_HDMI_HDCP_DDC_CTRL_1, reg_val);

		/* Check if the FAILURE got Cleared */
		reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_DDC_STATUS);
		if (reg_val & HDMI_HDCP_DDC_STATUS_FAILED)
			pr_info("%s: Unable to clear HDCP DDC Failure\n",
				__func__);

		/* Re-Enable HDCP DDC */
		hdmi_write(hdmi, REG_HDMI_HDCP_DDC_CTRL_0, 0);
	}

	if (nack0) {
		DBG("Before: HDMI_DDC_SW_STATUS=0x%08x",
			hdmi_read(hdmi, REG_HDMI_DDC_SW_STATUS));
		/* Reset HDMI DDC software status */
		reg_val = hdmi_read(hdmi, REG_HDMI_DDC_CTRL);
		reg_val |= HDMI_DDC_CTRL_SW_STATUS_RESET;
		hdmi_write(hdmi, REG_HDMI_DDC_CTRL, reg_val);

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);

		reg_val = hdmi_read(hdmi, REG_HDMI_DDC_CTRL);
		reg_val &= ~HDMI_DDC_CTRL_SW_STATUS_RESET;
		hdmi_write(hdmi, REG_HDMI_DDC_CTRL, reg_val);

		/* Reset HDMI DDC Controller */
		reg_val = hdmi_read(hdmi, REG_HDMI_DDC_CTRL);
		reg_val |= HDMI_DDC_CTRL_SOFT_RESET;
		hdmi_write(hdmi, REG_HDMI_DDC_CTRL, reg_val);

		/* If previous msleep is aborted, skip this msleep */
		if (!rc)
			rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);

		reg_val = hdmi_read(hdmi, REG_HDMI_DDC_CTRL);
		reg_val &= ~HDMI_DDC_CTRL_SOFT_RESET;
		hdmi_write(hdmi, REG_HDMI_DDC_CTRL, reg_val);
		DBG("After: HDMI_DDC_SW_STATUS=0x%08x",
			hdmi_read(hdmi, REG_HDMI_DDC_SW_STATUS));
	}

	return rc;
}

static int msm_hdmi_hdcp_hw_ddc_clean(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	u32 hdcp_ddc_status, ddc_hw_status;
	u32 xfer_done, xfer_req, hw_done;
	bool hw_not_ready;
	u32 timeout_count;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;

	if (hdmi_read(hdmi, REG_HDMI_DDC_HW_STATUS) == 0)
		return 0;

	/* Wait to be clean on DDC HW engine */
	timeout_count = 100;
	do {
		hdcp_ddc_status = hdmi_read(hdmi, REG_HDMI_HDCP_DDC_STATUS);
		ddc_hw_status = hdmi_read(hdmi, REG_HDMI_DDC_HW_STATUS);

		xfer_done = hdcp_ddc_status & HDMI_HDCP_DDC_STATUS_XFER_DONE;
		xfer_req = hdcp_ddc_status & HDMI_HDCP_DDC_STATUS_XFER_REQ;
		hw_done = ddc_hw_status & HDMI_DDC_HW_STATUS_DONE;
		hw_not_ready = !xfer_done || xfer_req || !hw_done;

		if (hw_not_ready)
			break;

		timeout_count--;
		if (!timeout_count) {
			pr_warn("%s: hw_ddc_clean failed\n", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	return 0;
}

static void msm_hdmi_hdcp_reauth_work(struct work_struct *work)
{
	struct hdmi_hdcp_ctrl *hdcp_ctrl = container_of(work,
		struct hdmi_hdcp_ctrl, hdcp_reauth_work);
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	unsigned long flags;
	u32 reg_val;

	DBG("HDCP REAUTH WORK");
	/*
	 * Disable HPD circuitry.
	 * This is needed to reset the HDCP cipher engine so that when we
	 * attempt a re-authentication, HW would clear the AN0_READY and
	 * AN1_READY bits in HDMI_HDCP_LINK0_STATUS register
	 */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_HPD_CTRL);
	reg_val &= ~HDMI_HPD_CTRL_ENABLE;
	hdmi_write(hdmi, REG_HDMI_HPD_CTRL, reg_val);

	/* Disable HDCP interrupts */
	hdmi_write(hdmi, REG_HDMI_HDCP_INT_CTRL, 0);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	hdmi_write(hdmi, REG_HDMI_HDCP_RESET,
		HDMI_HDCP_RESET_LINK0_DEAUTHENTICATE);

	/* Wait to be clean on DDC HW engine */
	if (msm_hdmi_hdcp_hw_ddc_clean(hdcp_ctrl)) {
		pr_info("%s: reauth work aborted\n", __func__);
		return;
	}

	/* Disable encryption and disable the HDCP block */
	hdmi_write(hdmi, REG_HDMI_HDCP_CTRL, 0);

	/* Enable HPD circuitry */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_HPD_CTRL);
	reg_val |= HDMI_HPD_CTRL_ENABLE;
	hdmi_write(hdmi, REG_HDMI_HPD_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	/*
	 * Only retry defined times then abort current authenticating process
	 */
	if (++hdcp_ctrl->auth_retries == AUTH_RETRIES_TIME) {
		hdcp_ctrl->hdcp_state = HDCP_STATE_INACTIVE;
		hdcp_ctrl->auth_retries = 0;
		pr_info("%s: abort reauthentication!\n", __func__);

		return;
	}

	DBG("Queue AUTH WORK");
	hdcp_ctrl->hdcp_state = HDCP_STATE_AUTHENTICATING;
	queue_work(hdmi->workq, &hdcp_ctrl->hdcp_auth_work);
}

static int msm_hdmi_hdcp_auth_prepare(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 link0_status;
	u32 reg_val;
	unsigned long flags;
	int rc;

	if (!hdcp_ctrl->aksv_valid) {
		rc = msm_hdmi_hdcp_read_validate_aksv(hdcp_ctrl);
		if (rc) {
			pr_err("%s: ASKV validation failed\n", __func__);
			hdcp_ctrl->hdcp_state = HDCP_STATE_NO_AKSV;
			return -ENOTSUPP;
		}
		hdcp_ctrl->aksv_valid = true;
	}

	spin_lock_irqsave(&hdmi->reg_lock, flags);
	/* disable HDMI Encrypt */
	reg_val = hdmi_read(hdmi, REG_HDMI_CTRL);
	reg_val &= ~HDMI_CTRL_ENCRYPTED;
	hdmi_write(hdmi, REG_HDMI_CTRL, reg_val);

	/* Enabling Software DDC */
	reg_val = hdmi_read(hdmi, REG_HDMI_DDC_ARBITRATION);
	reg_val &= ~HDMI_DDC_ARBITRATION_HW_ARBITRATION;
	hdmi_write(hdmi, REG_HDMI_DDC_ARBITRATION, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	/*
	 * Write AKSV read from QFPROM to the HDCP registers.
	 * This step is needed for HDCP authentication and must be
	 * written before enabling HDCP.
	 */
	hdmi_write(hdmi, REG_HDMI_HDCP_SW_LOWER_AKSV, hdcp_ctrl->aksv_lsb);
	hdmi_write(hdmi, REG_HDMI_HDCP_SW_UPPER_AKSV, hdcp_ctrl->aksv_msb);

	/*
	 * HDCP setup prior to enabling HDCP_CTRL.
	 * Setup seed values for random number An.
	 */
	hdmi_write(hdmi, REG_HDMI_HDCP_ENTROPY_CTRL0, 0xB1FFB0FF);
	hdmi_write(hdmi, REG_HDMI_HDCP_ENTROPY_CTRL1, 0xF00DFACE);

	/* Disable the RngCipher state */
	reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_DEBUG_CTRL);
	reg_val &= ~HDMI_HDCP_DEBUG_CTRL_RNG_CIPHER;
	hdmi_write(hdmi, REG_HDMI_HDCP_DEBUG_CTRL, reg_val);
	DBG("HDCP_DEBUG_CTRL=0x%08x",
		hdmi_read(hdmi, REG_HDMI_HDCP_DEBUG_CTRL));

	/*
	 * Ensure that all register writes are completed before
	 * enabling HDCP cipher
	 */
	wmb();

	/*
	 * Enable HDCP
	 * This needs to be done as early as possible in order for the
	 * hardware to make An available to read
	 */
	hdmi_write(hdmi, REG_HDMI_HDCP_CTRL, HDMI_HDCP_CTRL_ENABLE);

	/*
	 * If we had stale values for the An ready bit, it should most
	 * likely be cleared now after enabling HDCP cipher
	 */
	link0_status = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
	DBG("After enabling HDCP Link0_Status=0x%08x", link0_status);
	if (!(link0_status &
		(HDMI_HDCP_LINK0_STATUS_AN_0_READY |
		HDMI_HDCP_LINK0_STATUS_AN_1_READY)))
		DBG("An not ready after enabling HDCP");

	/* Clear any DDC failures from previous tries before enable HDCP*/
	rc = msm_reset_hdcp_ddc_failures(hdcp_ctrl);

	return rc;
}

static void msm_hdmi_hdcp_auth_fail(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg_val;
	unsigned long flags;

	DBG("hdcp auth failed, queue reauth work");
	/* clear HDMI Encrypt */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_CTRL);
	reg_val &= ~HDMI_CTRL_ENCRYPTED;
	hdmi_write(hdmi, REG_HDMI_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	hdcp_ctrl->hdcp_state = HDCP_STATE_AUTH_FAILED;
	queue_work(hdmi->workq, &hdcp_ctrl->hdcp_reauth_work);
}

static void msm_hdmi_hdcp_auth_done(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg_val;
	unsigned long flags;

	/*
	 * Disable software DDC before going into part3 to make sure
	 * there is no Arbitration between software and hardware for DDC
	 */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_DDC_ARBITRATION);
	reg_val |= HDMI_DDC_ARBITRATION_HW_ARBITRATION;
	hdmi_write(hdmi, REG_HDMI_DDC_ARBITRATION, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	/* enable HDMI Encrypt */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_CTRL);
	reg_val |= HDMI_CTRL_ENCRYPTED;
	hdmi_write(hdmi, REG_HDMI_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	hdcp_ctrl->hdcp_state = HDCP_STATE_AUTHENTICATED;
	hdcp_ctrl->auth_retries = 0;
}

/*
 * hdcp authenticating part 1
 * Wait Key/An ready
 * Read BCAPS from sink
 * Write BCAPS and AKSV into HDCP engine
 * Write An and AKSV to sink
 * Read BKSV from sink and write into HDCP engine
 */
static int msm_hdmi_hdcp_wait_key_an_ready(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 link0_status, keys_state;
	u32 timeout_count;
	bool an_ready;

	/* Wait for HDCP keys to be checked and validated */
	timeout_count = 100;
	do {
		link0_status = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
		keys_state = (link0_status >> 28) & 0x7;
		if (keys_state == HDCP_KEYS_STATE_VALID)
			break;

		DBG("Keys not ready(%d). s=%d, l0=%0x08x",
			timeout_count, keys_state, link0_status);

		timeout_count--;
		if (!timeout_count) {
			pr_err("%s: Wait key state timedout", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	timeout_count = 100;
	do {
		link0_status = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
		an_ready = (link0_status & HDMI_HDCP_LINK0_STATUS_AN_0_READY)
			&& (link0_status & HDMI_HDCP_LINK0_STATUS_AN_1_READY);
		if (an_ready)
			break;

		DBG("An not ready(%d). l0_status=0x%08x",
			timeout_count, link0_status);

		timeout_count--;
		if (!timeout_count) {
			pr_err("%s: Wait An timedout", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	return 0;
}

static int msm_hdmi_hdcp_send_aksv_an(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc = 0;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 link0_aksv_0, link0_aksv_1;
	u32 link0_an[2];
	u8 aksv[5];

	/* Read An0 and An1 */
	link0_an[0] = hdmi_read(hdmi, REG_HDMI_HDCP_RCVPORT_DATA5);
	link0_an[1] = hdmi_read(hdmi, REG_HDMI_HDCP_RCVPORT_DATA6);

	/* Read AKSV */
	link0_aksv_0 = hdmi_read(hdmi, REG_HDMI_HDCP_RCVPORT_DATA3);
	link0_aksv_1 = hdmi_read(hdmi, REG_HDMI_HDCP_RCVPORT_DATA4);

	DBG("Link ASKV=%08x%08x", link0_aksv_0, link0_aksv_1);
	/* Copy An and AKSV to byte arrays for transmission */
	aksv[0] =  link0_aksv_0        & 0xFF;
	aksv[1] = (link0_aksv_0 >> 8)  & 0xFF;
	aksv[2] = (link0_aksv_0 >> 16) & 0xFF;
	aksv[3] = (link0_aksv_0 >> 24) & 0xFF;
	aksv[4] =  link0_aksv_1        & 0xFF;

	/* Write An to offset 0x18 */
	rc = msm_hdmi_ddc_write(hdmi, HDCP_PORT_ADDR, 0x18, (u8 *)link0_an,
		(u16)sizeof(link0_an));
	if (rc) {
		pr_err("%s:An write failed\n", __func__);
		return rc;
	}
	DBG("Link0-An=%08x%08x", link0_an[0], link0_an[1]);

	/* Write AKSV to offset 0x10 */
	rc = msm_hdmi_ddc_write(hdmi, HDCP_PORT_ADDR, 0x10, aksv, 5);
	if (rc) {
		pr_err("%s:AKSV write failed\n", __func__);
		return rc;
	}
	DBG("Link0-AKSV=%02x%08x", link0_aksv_1 & 0xFF, link0_aksv_0);

	return 0;
}

static int msm_hdmi_hdcp_recv_bksv(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc = 0;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u8 bksv[5];
	u32 reg[2], data[2];

	/* Read BKSV at offset 0x00 */
	rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x00, bksv, 5);
	if (rc) {
		pr_err("%s:BKSV read failed\n", __func__);
		return rc;
	}

	hdcp_ctrl->bksv_lsb = bksv[0] | (bksv[1] << 8) |
		(bksv[2] << 16) | (bksv[3] << 24);
	hdcp_ctrl->bksv_msb = bksv[4];
	DBG(":BKSV=%02x%08x", hdcp_ctrl->bksv_msb, hdcp_ctrl->bksv_lsb);

	/* check there are 20 ones in BKSV */
	if ((hweight32(hdcp_ctrl->bksv_lsb) + hweight32(hdcp_ctrl->bksv_msb))
			!= 20) {
		pr_err(": BKSV doesn't have 20 1's and 20 0's\n");
		pr_err(": BKSV chk fail. BKSV=%02x%02x%02x%02x%02x\n",
			bksv[4], bksv[3], bksv[2], bksv[1], bksv[0]);
		return -EINVAL;
	}

	/* Write BKSV read from sink to HDCP registers */
	reg[0] = REG_HDMI_HDCP_RCVPORT_DATA0;
	data[0] = hdcp_ctrl->bksv_lsb;
	reg[1] = REG_HDMI_HDCP_RCVPORT_DATA1;
	data[1] = hdcp_ctrl->bksv_msb;
	rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, reg, data, 2);

	return rc;
}

static int msm_hdmi_hdcp_recv_bcaps(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc = 0;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg, data;
	u8 bcaps;

	rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x40, &bcaps, 1);
	if (rc) {
		pr_err("%s:BCAPS read failed\n", __func__);
		return rc;
	}
	DBG("BCAPS=%02x", bcaps);

	/* receiver (0), repeater (1) */
	hdcp_ctrl->ds_type = (bcaps & BIT(6)) ? DS_REPEATER : DS_RECEIVER;

	/* Write BCAPS to the hardware */
	reg = REG_HDMI_HDCP_RCVPORT_DATA12;
	data = (u32)bcaps;
	rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, &reg, &data, 1);

	return rc;
}

static int msm_hdmi_hdcp_auth_part1_key_exchange(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	unsigned long flags;
	int rc;

	/* Wait for AKSV key and An ready */
	rc = msm_hdmi_hdcp_wait_key_an_ready(hdcp_ctrl);
	if (rc) {
		pr_err("%s: wait key and an ready failed\n", __func__);
		return rc;
	};

	/* Read BCAPS and send to HDCP engine */
	rc = msm_hdmi_hdcp_recv_bcaps(hdcp_ctrl);
	if (rc) {
		pr_err("%s: read bcaps error, abort\n", __func__);
		return rc;
	}

	/*
	 * 1.1_Features turned off by default.
	 * No need to write AInfo since 1.1_Features is disabled.
	 */
	hdmi_write(hdmi, REG_HDMI_HDCP_RCVPORT_DATA4, 0);

	/* Send AKSV and An to sink */
	rc = msm_hdmi_hdcp_send_aksv_an(hdcp_ctrl);
	if (rc) {
		pr_err("%s:An/Aksv write failed\n", __func__);
		return rc;
	}

	/* Read BKSV and send to HDCP engine*/
	rc = msm_hdmi_hdcp_recv_bksv(hdcp_ctrl);
	if (rc) {
		pr_err("%s:BKSV Process failed\n", __func__);
		return rc;
	}

	/* Enable HDCP interrupts and ack/clear any stale interrupts */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	hdmi_write(hdmi, REG_HDMI_HDCP_INT_CTRL,
		HDMI_HDCP_INT_CTRL_AUTH_SUCCESS_ACK |
		HDMI_HDCP_INT_CTRL_AUTH_SUCCESS_MASK |
		HDMI_HDCP_INT_CTRL_AUTH_FAIL_ACK |
		HDMI_HDCP_INT_CTRL_AUTH_FAIL_MASK |
		HDMI_HDCP_INT_CTRL_AUTH_FAIL_INFO_ACK);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	return 0;
}

/* read R0' from sink and pass it to HDCP engine */
static int msm_hdmi_hdcp_auth_part1_recv_r0(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	int rc = 0;
	u8 buf[2];

	/*
	 * HDCP Compliance Test case 1A-01:
	 * Wait here at least 100ms before reading R0'
	 */
	rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 125, AUTH_ABORT_EV);
	if (rc)
		return rc;

	/* Read R0' at offset 0x08 */
	rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x08, buf, 2);
	if (rc) {
		pr_err("%s:R0' read failed\n", __func__);
		return rc;
	}
	DBG("R0'=%02x%02x", buf[1], buf[0]);

	/* Write R0' to HDCP registers and check to see if it is a match */
	hdmi_write(hdmi, REG_HDMI_HDCP_RCVPORT_DATA2_0,
		(((u32)buf[1]) << 8) | buf[0]);

	return 0;
}

/* Wait for authenticating result: R0/R0' are matched or not */
static int msm_hdmi_hdcp_auth_part1_verify_r0(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 link0_status;
	int rc;

	/* wait for hdcp irq, 10 sec should be long enough */
	rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 10000, AUTH_RESULT_RDY_EV);
	if (!rc) {
		pr_err("%s: Wait Auth IRQ timeout\n", __func__);
		return -ETIMEDOUT;
	}

	link0_status = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
	if (!(link0_status & HDMI_HDCP_LINK0_STATUS_RI_MATCHES)) {
		pr_err("%s: Authentication Part I failed\n", __func__);
		return -EINVAL;
	}

	/* Enable HDCP Encryption */
	hdmi_write(hdmi, REG_HDMI_HDCP_CTRL,
		HDMI_HDCP_CTRL_ENABLE |
		HDMI_HDCP_CTRL_ENCRYPTION_ENABLE);

	return 0;
}

static int msm_hdmi_hdcp_recv_check_bstatus(struct hdmi_hdcp_ctrl *hdcp_ctrl,
	u16 *pbstatus)
{
	int rc;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	bool max_devs_exceeded = false, max_cascade_exceeded = false;
	u32 repeater_cascade_depth = 0, down_stream_devices = 0;
	u16 bstatus;
	u8 buf[2];

	/* Read BSTATUS at offset 0x41 */
	rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x41, buf, 2);
	if (rc) {
		pr_err("%s: BSTATUS read failed\n", __func__);
		goto error;
	}
	*pbstatus = bstatus = (buf[1] << 8) | buf[0];


	down_stream_devices = bstatus & 0x7F;
	repeater_cascade_depth = (bstatus >> 8) & 0x7;
	max_devs_exceeded = (bstatus & BIT(7)) ? true : false;
	max_cascade_exceeded = (bstatus & BIT(11)) ? true : false;

	if (down_stream_devices == 0) {
		/*
		 * If no downstream devices are attached to the repeater
		 * then part II fails.
		 * todo: The other approach would be to continue PART II.
		 */
		pr_err("%s: No downstream devices\n", __func__);
		rc = -EINVAL;
		goto error;
	}

	/*
	 * HDCP Compliance 1B-05:
	 * Check if no. of devices connected to repeater
	 * exceed max_devices_connected from bit 7 of Bstatus.
	 */
	if (max_devs_exceeded) {
		pr_err("%s: no. of devs connected exceeds max allowed",
			__func__);
		rc = -EINVAL;
		goto error;
	}

	/*
	 * HDCP Compliance 1B-06:
	 * Check if no. of cascade connected to repeater
	 * exceed max_cascade_connected from bit 11 of Bstatus.
	 */
	if (max_cascade_exceeded) {
		pr_err("%s: no. of cascade conn exceeds max allowed",
			__func__);
		rc = -EINVAL;
		goto error;
	}

error:
	hdcp_ctrl->dev_count = down_stream_devices;
	hdcp_ctrl->max_cascade_exceeded = max_cascade_exceeded;
	hdcp_ctrl->max_dev_exceeded = max_devs_exceeded;
	hdcp_ctrl->depth = repeater_cascade_depth;
	return rc;
}

static int msm_hdmi_hdcp_auth_part2_wait_ksv_fifo_ready(
	struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg, data;
	u32 timeout_count;
	u16 bstatus;
	u8 bcaps;

	/*
	 * Wait until READY bit is set in BCAPS, as per HDCP specifications
	 * maximum permitted time to check for READY bit is five seconds.
	 */
	timeout_count = 100;
	do {
		/* Read BCAPS at offset 0x40 */
		rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x40, &bcaps, 1);
		if (rc) {
			pr_err("%s: BCAPS read failed\n", __func__);
			return rc;
		}

		if (bcaps & BIT(5))
			break;

		timeout_count--;
		if (!timeout_count) {
			pr_err("%s: Wait KSV fifo ready timedout", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	rc = msm_hdmi_hdcp_recv_check_bstatus(hdcp_ctrl, &bstatus);
	if (rc) {
		pr_err("%s: bstatus error\n", __func__);
		return rc;
	}

	/* Write BSTATUS and BCAPS to HDCP registers */
	reg = REG_HDMI_HDCP_RCVPORT_DATA12;
	data = bcaps | (bstatus << 8);
	rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, &reg, &data, 1);
	if (rc) {
		pr_err("%s: BSTATUS write failed\n", __func__);
		return rc;
	}

	return 0;
}

/*
 * hdcp authenticating part 2: 2nd
 * read ksv fifo from sink
 * transfer V' from sink to HDCP engine
 * reset SHA engine
 */
static int msm_hdmi_hdcp_transfer_v_h(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	int rc = 0;
	struct hdmi_hdcp_reg_data reg_data[]  = {
		{REG_HDMI_HDCP_RCVPORT_DATA7,  0x20, "V' H0"},
		{REG_HDMI_HDCP_RCVPORT_DATA8,  0x24, "V' H1"},
		{REG_HDMI_HDCP_RCVPORT_DATA9,  0x28, "V' H2"},
		{REG_HDMI_HDCP_RCVPORT_DATA10, 0x2C, "V' H3"},
		{REG_HDMI_HDCP_RCVPORT_DATA11, 0x30, "V' H4"},
	};
	struct hdmi_hdcp_reg_data *rd;
	u32 size = ARRAY_SIZE(reg_data);
	u32 reg[ARRAY_SIZE(reg_data)];
	u32 data[ARRAY_SIZE(reg_data)];
	int i;

	for (i = 0; i < size; i++) {
		rd = &reg_data[i];
		rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR,
			rd->off, (u8 *)&data[i], (u16)sizeof(data[i]));
		if (rc) {
			pr_err("%s: Read %s failed\n", __func__, rd->name);
			goto error;
		}

		DBG("%s =%x", rd->name, data[i]);
		reg[i] = reg_data[i].reg_id;
	}

	rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, reg, data, size);

error:
	return rc;
}

static int msm_hdmi_hdcp_recv_ksv_fifo(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 ksv_bytes;

	ksv_bytes = 5 * hdcp_ctrl->dev_count;

	rc = msm_hdmi_ddc_read(hdmi, HDCP_PORT_ADDR, 0x43,
		hdcp_ctrl->ksv_list, ksv_bytes);
	if (rc)
		pr_err("%s: KSV FIFO read failed\n", __func__);

	return rc;
}

static int msm_hdmi_hdcp_reset_sha_engine(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	u32 reg[2], data[2];
	u32 rc  = 0;

	reg[0] = REG_HDMI_HDCP_SHA_CTRL;
	data[0] = HDCP_REG_ENABLE;
	reg[1] = REG_HDMI_HDCP_SHA_CTRL;
	data[1] = HDCP_REG_DISABLE;

	rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, reg, data, 2);

	return rc;
}

static int msm_hdmi_hdcp_auth_part2_recv_ksv_fifo(
	struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	u32 timeout_count;

	/*
	 * Read KSV FIFO over DDC
	 * Key Selection vector FIFO Used to pull downstream KSVs
	 * from HDCP Repeaters.
	 * All bytes (DEVICE_COUNT * 5) must be read in a single,
	 * auto incrementing access.
	 * All bytes read as 0x00 for HDCP Receivers that are not
	 * HDCP Repeaters (REPEATER == 0).
	 */
	timeout_count = 100;
	do {
		rc = msm_hdmi_hdcp_recv_ksv_fifo(hdcp_ctrl);
		if (!rc)
			break;

		timeout_count--;
		if (!timeout_count) {
			pr_err("%s: Recv ksv fifo timedout", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 25, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	rc = msm_hdmi_hdcp_transfer_v_h(hdcp_ctrl);
	if (rc) {
		pr_err("%s: transfer V failed\n", __func__);
		return rc;
	}

	/* reset SHA engine before write ksv fifo */
	rc = msm_hdmi_hdcp_reset_sha_engine(hdcp_ctrl);
	if (rc) {
		pr_err("%s: fail to reset sha engine\n", __func__);
		return rc;
	}

	return 0;
}

/*
 * Write KSV FIFO to HDCP_SHA_DATA.
 * This is done 1 byte at time starting with the LSB.
 * Once 64 bytes have been written, we need to poll for
 * HDCP_SHA_BLOCK_DONE before writing any further
 * If the last byte is written, we need to poll for
 * HDCP_SHA_COMP_DONE to wait until HW finish
 */
static int msm_hdmi_hdcp_write_ksv_fifo(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int i;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 ksv_bytes, last_byte = 0;
	u8 *ksv_fifo = NULL;
	u32 reg_val, data, reg;
	u32 rc  = 0;

	ksv_bytes  = 5 * hdcp_ctrl->dev_count;

	/* Check if need to wait for HW completion */
	if (hdcp_ctrl->ksv_fifo_w_index) {
		reg_val = hdmi_read(hdmi, REG_HDMI_HDCP_SHA_STATUS);
		DBG("HDCP_SHA_STATUS=%08x", reg_val);
		if (hdcp_ctrl->ksv_fifo_w_index == ksv_bytes) {
			/* check COMP_DONE if last write */
			if (reg_val & HDMI_HDCP_SHA_STATUS_COMP_DONE) {
				DBG("COMP_DONE");
				return 0;
			} else {
				return -EAGAIN;
			}
		} else {
			/* check BLOCK_DONE if not last write */
			if (!(reg_val & HDMI_HDCP_SHA_STATUS_BLOCK_DONE))
				return -EAGAIN;

			DBG("BLOCK_DONE");
		}
	}

	ksv_bytes  -= hdcp_ctrl->ksv_fifo_w_index;
	if (ksv_bytes <= 64)
		last_byte = 1;
	else
		ksv_bytes = 64;

	ksv_fifo = hdcp_ctrl->ksv_list;
	ksv_fifo += hdcp_ctrl->ksv_fifo_w_index;

	for (i = 0; i < ksv_bytes; i++) {
		/* Write KSV byte and set DONE bit[0] for last byte*/
		reg_val = ksv_fifo[i] << 16;
		if ((i == (ksv_bytes - 1)) && last_byte)
			reg_val |= HDMI_HDCP_SHA_DATA_DONE;

		reg = REG_HDMI_HDCP_SHA_DATA;
		data = reg_val;
		rc = msm_hdmi_hdcp_scm_wr(hdcp_ctrl, &reg, &data, 1);

		if (rc)
			return rc;
	}

	hdcp_ctrl->ksv_fifo_w_index += ksv_bytes;

	/*
	 *return -EAGAIN to notify caller to wait for COMP_DONE or BLOCK_DONE
	 */
	return -EAGAIN;
}

/* write ksv fifo into HDCP engine */
static int msm_hdmi_hdcp_auth_part2_write_ksv_fifo(
	struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc;
	u32 timeout_count;

	hdcp_ctrl->ksv_fifo_w_index = 0;
	timeout_count = 100;
	do {
		rc = msm_hdmi_hdcp_write_ksv_fifo(hdcp_ctrl);
		if (!rc)
			break;

		if (rc != -EAGAIN)
			return rc;

		timeout_count--;
		if (!timeout_count) {
			pr_err("%s: Write KSV fifo timedout", __func__);
			return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	return 0;
}

static int msm_hdmi_hdcp_auth_part2_check_v_match(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	int rc = 0;
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 link0_status;
	u32 timeout_count = 100;

	do {
		link0_status = hdmi_read(hdmi, REG_HDMI_HDCP_LINK0_STATUS);
		if (link0_status & HDMI_HDCP_LINK0_STATUS_V_MATCHES)
			break;

		timeout_count--;
		if (!timeout_count) {
				pr_err("%s: HDCP V Match timedout", __func__);
				return -ETIMEDOUT;
		}

		rc = msm_hdmi_hdcp_msleep(hdcp_ctrl, 20, AUTH_ABORT_EV);
		if (rc)
			return rc;
	} while (1);

	return 0;
}

static void msm_hdmi_hdcp_auth_work(struct work_struct *work)
{
	struct hdmi_hdcp_ctrl *hdcp_ctrl = container_of(work,
		struct hdmi_hdcp_ctrl, hdcp_auth_work);
	int rc;

	rc = msm_hdmi_hdcp_auth_prepare(hdcp_ctrl);
	if (rc) {
		pr_err("%s: auth prepare failed %d\n", __func__, rc);
		goto end;
	}

	/* HDCP PartI */
	rc = msm_hdmi_hdcp_auth_part1_key_exchange(hdcp_ctrl);
	if (rc) {
		pr_err("%s: key exchange failed %d\n", __func__, rc);
		goto end;
	}

	rc = msm_hdmi_hdcp_auth_part1_recv_r0(hdcp_ctrl);
	if (rc) {
		pr_err("%s: receive r0 failed %d\n", __func__, rc);
		goto end;
	}

	rc = msm_hdmi_hdcp_auth_part1_verify_r0(hdcp_ctrl);
	if (rc) {
		pr_err("%s: verify r0 failed %d\n", __func__, rc);
		goto end;
	}
	pr_info("%s: Authentication Part I successful\n", __func__);
	if (hdcp_ctrl->ds_type == DS_RECEIVER)
		goto end;

	/* HDCP PartII */
	rc = msm_hdmi_hdcp_auth_part2_wait_ksv_fifo_ready(hdcp_ctrl);
	if (rc) {
		pr_err("%s: wait ksv fifo ready failed %d\n", __func__, rc);
		goto end;
	}

	rc = msm_hdmi_hdcp_auth_part2_recv_ksv_fifo(hdcp_ctrl);
	if (rc) {
		pr_err("%s: recv ksv fifo failed %d\n", __func__, rc);
		goto end;
	}

	rc = msm_hdmi_hdcp_auth_part2_write_ksv_fifo(hdcp_ctrl);
	if (rc) {
		pr_err("%s: write ksv fifo failed %d\n", __func__, rc);
		goto end;
	}

	rc = msm_hdmi_hdcp_auth_part2_check_v_match(hdcp_ctrl);
	if (rc)
		pr_err("%s: check v match failed %d\n", __func__, rc);

end:
	if (rc == -ECANCELED) {
		pr_info("%s: hdcp authentication canceled\n", __func__);
	} else if (rc == -ENOTSUPP) {
		pr_info("%s: hdcp is not supported\n", __func__);
	} else if (rc) {
		pr_err("%s: hdcp authentication failed\n", __func__);
		msm_hdmi_hdcp_auth_fail(hdcp_ctrl);
	} else {
		msm_hdmi_hdcp_auth_done(hdcp_ctrl);
	}
}

void msm_hdmi_hdcp_on(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	u32 reg_val;
	unsigned long flags;

	if ((HDCP_STATE_INACTIVE != hdcp_ctrl->hdcp_state) ||
		(HDCP_STATE_NO_AKSV == hdcp_ctrl->hdcp_state)) {
		DBG("still active or activating or no askv. returning");
		return;
	}

	/* clear HDMI Encrypt */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_CTRL);
	reg_val &= ~HDMI_CTRL_ENCRYPTED;
	hdmi_write(hdmi, REG_HDMI_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	hdcp_ctrl->auth_event = 0;
	hdcp_ctrl->hdcp_state = HDCP_STATE_AUTHENTICATING;
	hdcp_ctrl->auth_retries = 0;
	queue_work(hdmi->workq, &hdcp_ctrl->hdcp_auth_work);
}

void msm_hdmi_hdcp_off(struct hdmi_hdcp_ctrl *hdcp_ctrl)
{
	struct hdmi *hdmi = hdcp_ctrl->hdmi;
	unsigned long flags;
	u32 reg_val;

	if ((HDCP_STATE_INACTIVE == hdcp_ctrl->hdcp_state) ||
		(HDCP_STATE_NO_AKSV == hdcp_ctrl->hdcp_state)) {
		DBG("hdcp inactive or no aksv. returning");
		return;
	}

	/*
	 * Disable HPD circuitry.
	 * This is needed to reset the HDCP cipher engine so that when we
	 * attempt a re-authentication, HW would clear the AN0_READY and
	 * AN1_READY bits in HDMI_HDCP_LINK0_STATUS register
	 */
	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_HPD_CTRL);
	reg_val &= ~HDMI_HPD_CTRL_ENABLE;
	hdmi_write(hdmi, REG_HDMI_HPD_CTRL, reg_val);

	/*
	 * Disable HDCP interrupts.
	 * Also, need to set the state to inactive here so that any ongoing
	 * reauth works will know that the HDCP session has been turned off.
	 */
	hdmi_write(hdmi, REG_HDMI_HDCP_INT_CTRL, 0);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	/*
	 * Cancel any pending auth/reauth attempts.
	 * If one is ongoing, this will wait for it to finish.
	 * No more reauthentication attempts will be scheduled since we
	 * set the current state to inactive.
	 */
	set_bit(AUTH_ABORT_EV, &hdcp_ctrl->auth_event);
	wake_up_all(&hdcp_ctrl->auth_event_queue);
	cancel_work_sync(&hdcp_ctrl->hdcp_auth_work);
	cancel_work_sync(&hdcp_ctrl->hdcp_reauth_work);

	hdmi_write(hdmi, REG_HDMI_HDCP_RESET,
		HDMI_HDCP_RESET_LINK0_DEAUTHENTICATE);

	/* Disable encryption and disable the HDCP block */
	hdmi_write(hdmi, REG_HDMI_HDCP_CTRL, 0);

	spin_lock_irqsave(&hdmi->reg_lock, flags);
	reg_val = hdmi_read(hdmi, REG_HDMI_CTRL);
	reg_val &= ~HDMI_CTRL_ENCRYPTED;
	hdmi_write(hdmi, REG_HDMI_CTRL, reg_val);

	/* Enable HPD circuitry */
	reg_val = hdmi_read(hdmi, REG_HDMI_HPD_CTRL);
	reg_val |= HDMI_HPD_CTRL_ENABLE;
	hdmi_write(hdmi, REG_HDMI_HPD_CTRL, reg_val);
	spin_unlock_irqrestore(&hdmi->reg_lock, flags);

	hdcp_ctrl->hdcp_state = HDCP_STATE_INACTIVE;

	DBG("HDCP: Off");
}

struct hdmi_hdcp_ctrl *msm_hdmi_hdcp_init(struct hdmi *hdmi)
{
	struct hdmi_hdcp_ctrl *hdcp_ctrl = NULL;

	if (!hdmi->qfprom_mmio) {
		pr_err("%s: HDCP is not supported without qfprom\n",
			__func__);
		return ERR_PTR(-EINVAL);
	}

	hdcp_ctrl = kzalloc(sizeof(*hdcp_ctrl), GFP_KERNEL);
	if (!hdcp_ctrl)
		return ERR_PTR(-ENOMEM);

	INIT_WORK(&hdcp_ctrl->hdcp_auth_work, msm_hdmi_hdcp_auth_work);
	INIT_WORK(&hdcp_ctrl->hdcp_reauth_work, msm_hdmi_hdcp_reauth_work);
	init_waitqueue_head(&hdcp_ctrl->auth_event_queue);
	hdcp_ctrl->hdmi = hdmi;
	hdcp_ctrl->hdcp_state = HDCP_STATE_INACTIVE;
	hdcp_ctrl->aksv_valid = false;

	if (qcom_scm_hdcp_available())
		hdcp_ctrl->tz_hdcp = true;
	else
		hdcp_ctrl->tz_hdcp = false;

	return hdcp_ctrl;
}

void msm_hdmi_hdcp_destroy(struct hdmi *hdmi)
{
	if (hdmi) {
		kfree(hdmi->hdcp_ctrl);
		hdmi->hdcp_ctrl = NULL;
	}
}
