/*
 * H/W layer of ISHTP provider device (ISH)
 *
 * Copyright (c) 2014-2016, Intel Corporation.
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms and conditions of the GNU General Public License,
 * version 2, as published by the Free Software Foundation.
 *
 * This program is distributed in the hope 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 <linux/sched.h>
#include <linux/spinlock.h>
#include <linux/delay.h>
#include <linux/jiffies.h>
#include "client.h"
#include "hw-ish.h"
#include "hbm.h"

/* For FW reset flow */
static struct work_struct fw_reset_work;
static struct ishtp_device *ishtp_dev;

/**
 * ish_reg_read() - Read register
 * @dev: ISHTP device pointer
 * @offset: Register offset
 *
 * Read 32 bit register at a given offset
 *
 * Return: Read register value
 */
static inline uint32_t ish_reg_read(const struct ishtp_device *dev,
	unsigned long offset)
{
	struct ish_hw *hw = to_ish_hw(dev);

	return readl(hw->mem_addr + offset);
}

/**
 * ish_reg_write() - Write register
 * @dev: ISHTP device pointer
 * @offset: Register offset
 * @value: Value to write
 *
 * Writes 32 bit register at a give offset
 */
static inline void ish_reg_write(struct ishtp_device *dev,
				 unsigned long offset,
				 uint32_t value)
{
	struct ish_hw *hw = to_ish_hw(dev);

	writel(value, hw->mem_addr + offset);
}

/**
 * _ish_read_fw_sts_reg() - Read FW status register
 * @dev: ISHTP device pointer
 *
 * Read FW status register
 *
 * Return: Read register value
 */
static inline uint32_t _ish_read_fw_sts_reg(struct ishtp_device *dev)
{
	return ish_reg_read(dev, IPC_REG_ISH_HOST_FWSTS);
}

/**
 * check_generated_interrupt() - Check if ISH interrupt
 * @dev: ISHTP device pointer
 *
 * Check if an interrupt was generated for ISH
 *
 * Return: Read true or false
 */
static bool check_generated_interrupt(struct ishtp_device *dev)
{
	bool interrupt_generated = true;
	uint32_t pisr_val = 0;

	if (dev->pdev->device == CHV_DEVICE_ID) {
		pisr_val = ish_reg_read(dev, IPC_REG_PISR_CHV_AB);
		interrupt_generated =
			IPC_INT_FROM_ISH_TO_HOST_CHV_AB(pisr_val);
	} else {
		pisr_val = ish_reg_read(dev, IPC_REG_PISR_BXT);
		interrupt_generated = IPC_INT_FROM_ISH_TO_HOST_BXT(pisr_val);
	}

	return interrupt_generated;
}

/**
 * ish_is_input_ready() - Check if FW ready for RX
 * @dev: ISHTP device pointer
 *
 * Check if ISH FW is ready for receiving data
 *
 * Return: Read true or false
 */
static bool ish_is_input_ready(struct ishtp_device *dev)
{
	uint32_t doorbell_val;

	doorbell_val = ish_reg_read(dev, IPC_REG_HOST2ISH_DRBL);
	return !IPC_IS_BUSY(doorbell_val);
}

/**
 * set_host_ready() - Indicate host ready
 * @dev: ISHTP device pointer
 *
 * Set host ready indication to FW
 */
static void set_host_ready(struct ishtp_device *dev)
{
	if (dev->pdev->device == CHV_DEVICE_ID) {
		if (dev->pdev->revision == REVISION_ID_CHT_A0 ||
				(dev->pdev->revision & REVISION_ID_SI_MASK) ==
				REVISION_ID_CHT_Ax_SI)
			ish_reg_write(dev, IPC_REG_HOST_COMM, 0x81);
		else if (dev->pdev->revision == REVISION_ID_CHT_B0 ||
				(dev->pdev->revision & REVISION_ID_SI_MASK) ==
				REVISION_ID_CHT_Bx_SI ||
				(dev->pdev->revision & REVISION_ID_SI_MASK) ==
				REVISION_ID_CHT_Kx_SI ||
				(dev->pdev->revision & REVISION_ID_SI_MASK) ==
				REVISION_ID_CHT_Dx_SI) {
			uint32_t host_comm_val;

			host_comm_val = ish_reg_read(dev, IPC_REG_HOST_COMM);
			host_comm_val |= IPC_HOSTCOMM_INT_EN_BIT_CHV_AB | 0x81;
			ish_reg_write(dev, IPC_REG_HOST_COMM, host_comm_val);
		}
	} else {
			uint32_t host_pimr_val;

			host_pimr_val = ish_reg_read(dev, IPC_REG_PIMR_BXT);
			host_pimr_val |= IPC_PIMR_INT_EN_BIT_BXT;
			/*
			 * disable interrupt generated instead of
			 * RX_complete_msg
			 */
			host_pimr_val &= ~IPC_HOST2ISH_BUSYCLEAR_MASK_BIT;

			ish_reg_write(dev, IPC_REG_PIMR_BXT, host_pimr_val);
	}
}

/**
 * ishtp_fw_is_ready() - Check if FW ready
 * @dev: ISHTP device pointer
 *
 * Check if ISH FW is ready
 *
 * Return: Read true or false
 */
static bool ishtp_fw_is_ready(struct ishtp_device *dev)
{
	uint32_t ish_status = _ish_read_fw_sts_reg(dev);

	return IPC_IS_ISH_ILUP(ish_status) &&
		IPC_IS_ISH_ISHTP_READY(ish_status);
}

/**
 * ish_set_host_rdy() - Indicate host ready
 * @dev: ISHTP device pointer
 *
 * Set host ready indication to FW
 */
static void ish_set_host_rdy(struct ishtp_device *dev)
{
	uint32_t host_status = ish_reg_read(dev, IPC_REG_HOST_COMM);

	IPC_SET_HOST_READY(host_status);
	ish_reg_write(dev, IPC_REG_HOST_COMM, host_status);
}

/**
 * ish_clr_host_rdy() - Indicate host not ready
 * @dev: ISHTP device pointer
 *
 * Send host not ready indication to FW
 */
static void ish_clr_host_rdy(struct ishtp_device *dev)
{
	uint32_t host_status = ish_reg_read(dev, IPC_REG_HOST_COMM);

	IPC_CLEAR_HOST_READY(host_status);
	ish_reg_write(dev, IPC_REG_HOST_COMM, host_status);
}

/**
 * _ishtp_read_hdr() - Read message header
 * @dev: ISHTP device pointer
 *
 * Read header of 32bit length
 *
 * Return: Read register value
 */
static uint32_t _ishtp_read_hdr(const struct ishtp_device *dev)
{
	return ish_reg_read(dev, IPC_REG_ISH2HOST_MSG);
}

/**
 * _ishtp_read - Read message
 * @dev: ISHTP device pointer
 * @buffer: message buffer
 * @buffer_length: length of message buffer
 *
 * Read message from FW
 *
 * Return: Always 0
 */
static int _ishtp_read(struct ishtp_device *dev, unsigned char *buffer,
	unsigned long buffer_length)
{
	uint32_t	i;
	uint32_t	*r_buf = (uint32_t *)buffer;
	uint32_t	msg_offs;

	msg_offs = IPC_REG_ISH2HOST_MSG + sizeof(struct ishtp_msg_hdr);
	for (i = 0; i < buffer_length; i += sizeof(uint32_t))
		*r_buf++ = ish_reg_read(dev, msg_offs + i);

	return 0;
}

/**
 * write_ipc_from_queue() - try to write ipc msg from Tx queue to device
 * @dev: ishtp device pointer
 *
 * Check if DRBL is cleared. if it is - write the first IPC msg,  then call
 * the callback function (unless it's NULL)
 *
 * Return: 0 for success else failure code
 */
static int write_ipc_from_queue(struct ishtp_device *dev)
{
	struct wr_msg_ctl_info	*ipc_link;
	unsigned long	length;
	unsigned long	rem;
	unsigned long	flags;
	uint32_t	doorbell_val;
	uint32_t	*r_buf;
	uint32_t	reg_addr;
	int	i;
	void	(*ipc_send_compl)(void *);
	void	*ipc_send_compl_prm;
	static int	out_ipc_locked;
	unsigned long	out_ipc_flags;

	if (dev->dev_state == ISHTP_DEV_DISABLED)
		return	-EINVAL;

	spin_lock_irqsave(&dev->out_ipc_spinlock, out_ipc_flags);
	if (out_ipc_locked) {
		spin_unlock_irqrestore(&dev->out_ipc_spinlock, out_ipc_flags);
		return -EBUSY;
	}
	out_ipc_locked = 1;
	if (!ish_is_input_ready(dev)) {
		out_ipc_locked = 0;
		spin_unlock_irqrestore(&dev->out_ipc_spinlock, out_ipc_flags);
		return -EBUSY;
	}
	spin_unlock_irqrestore(&dev->out_ipc_spinlock, out_ipc_flags);

	spin_lock_irqsave(&dev->wr_processing_spinlock, flags);
	/*
	 * if tx send list is empty - return 0;
	 * may happen, as RX_COMPLETE handler doesn't check list emptiness.
	 */
	if (list_empty(&dev->wr_processing_list)) {
		spin_unlock_irqrestore(&dev->wr_processing_spinlock, flags);
		out_ipc_locked = 0;
		return	0;
	}

	ipc_link = list_first_entry(&dev->wr_processing_list,
				    struct wr_msg_ctl_info, link);
	/* first 4 bytes of the data is the doorbell value (IPC header) */
	length = ipc_link->length - sizeof(uint32_t);
	doorbell_val = *(uint32_t *)ipc_link->inline_data;
	r_buf = (uint32_t *)(ipc_link->inline_data + sizeof(uint32_t));

	/* If sending MNG_SYNC_FW_CLOCK, update clock again */
	if (IPC_HEADER_GET_PROTOCOL(doorbell_val) == IPC_PROTOCOL_MNG &&
		IPC_HEADER_GET_MNG_CMD(doorbell_val) == MNG_SYNC_FW_CLOCK) {
		uint64_t usec_system, usec_utc;
		struct ipc_time_update_msg time_update;
		struct time_sync_format ts_format;

		usec_system = ktime_to_us(ktime_get_boottime());
		usec_utc = ktime_to_us(ktime_get_real());
		ts_format.ts1_source = HOST_SYSTEM_TIME_USEC;
		ts_format.ts2_source = HOST_UTC_TIME_USEC;
		ts_format.reserved = 0;

		time_update.primary_host_time = usec_system;
		time_update.secondary_host_time = usec_utc;
		time_update.sync_info = ts_format;

		memcpy(r_buf, &time_update,
		       sizeof(struct ipc_time_update_msg));
	}

	for (i = 0, reg_addr = IPC_REG_HOST2ISH_MSG; i < length >> 2; i++,
			reg_addr += 4)
		ish_reg_write(dev, reg_addr, r_buf[i]);

	rem = length & 0x3;
	if (rem > 0) {
		uint32_t reg = 0;

		memcpy(&reg, &r_buf[length >> 2], rem);
		ish_reg_write(dev, reg_addr, reg);
	}
	/* Flush writes to msg registers and doorbell */
	ish_reg_read(dev, IPC_REG_ISH_HOST_FWSTS);

	/* Update IPC counters */
	++dev->ipc_tx_cnt;
	dev->ipc_tx_bytes_cnt += IPC_HEADER_GET_LENGTH(doorbell_val);

	ish_reg_write(dev, IPC_REG_HOST2ISH_DRBL, doorbell_val);
	out_ipc_locked = 0;

	ipc_send_compl = ipc_link->ipc_send_compl;
	ipc_send_compl_prm = ipc_link->ipc_send_compl_prm;
	list_del_init(&ipc_link->link);
	list_add(&ipc_link->link, &dev->wr_free_list);
	spin_unlock_irqrestore(&dev->wr_processing_spinlock, flags);

	/*
	 * callback will be called out of spinlock,
	 * after ipc_link returned to free list
	 */
	if (ipc_send_compl)
		ipc_send_compl(ipc_send_compl_prm);

	return 0;
}

/**
 * write_ipc_to_queue() - write ipc msg to Tx queue
 * @dev: ishtp device instance
 * @ipc_send_compl: Send complete callback
 * @ipc_send_compl_prm:	Parameter to send in complete callback
 * @msg: Pointer to message
 * @length: Length of message
 *
 * Recived msg with IPC (and upper protocol) header  and add it to the device
 *  Tx-to-write list then try to send the first IPC waiting msg
 *  (if DRBL is cleared)
 * This function returns negative value for failure (means free list
 *  is empty, or msg too long) and 0 for success.
 *
 * Return: 0 for success else failure code
 */
static int write_ipc_to_queue(struct ishtp_device *dev,
	void (*ipc_send_compl)(void *), void *ipc_send_compl_prm,
	unsigned char *msg, int length)
{
	struct wr_msg_ctl_info *ipc_link;
	unsigned long flags;

	if (length > IPC_FULL_MSG_SIZE)
		return -EMSGSIZE;

	spin_lock_irqsave(&dev->wr_processing_spinlock, flags);
	if (list_empty(&dev->wr_free_list)) {
		spin_unlock_irqrestore(&dev->wr_processing_spinlock, flags);
		return -ENOMEM;
	}
	ipc_link = list_first_entry(&dev->wr_free_list,
				    struct wr_msg_ctl_info, link);
	list_del_init(&ipc_link->link);

	ipc_link->ipc_send_compl = ipc_send_compl;
	ipc_link->ipc_send_compl_prm = ipc_send_compl_prm;
	ipc_link->length = length;
	memcpy(ipc_link->inline_data, msg, length);

	list_add_tail(&ipc_link->link, &dev->wr_processing_list);
	spin_unlock_irqrestore(&dev->wr_processing_spinlock, flags);

	write_ipc_from_queue(dev);

	return 0;
}

/**
 * ipc_send_mng_msg() - Send management message
 * @dev: ishtp device instance
 * @msg_code: Message code
 * @msg: Pointer to message
 * @size: Length of message
 *
 * Send management message to FW
 *
 * Return: 0 for success else failure code
 */
static int ipc_send_mng_msg(struct ishtp_device *dev, uint32_t msg_code,
	void *msg, size_t size)
{
	unsigned char	ipc_msg[IPC_FULL_MSG_SIZE];
	uint32_t	drbl_val = IPC_BUILD_MNG_MSG(msg_code, size);

	memcpy(ipc_msg, &drbl_val, sizeof(uint32_t));
	memcpy(ipc_msg + sizeof(uint32_t), msg, size);
	return	write_ipc_to_queue(dev, NULL, NULL, ipc_msg,
		sizeof(uint32_t) + size);
}

#define WAIT_FOR_FW_RDY			0x1
#define WAIT_FOR_INPUT_RDY		0x2

/**
 * timed_wait_for_timeout() - wait special event with timeout
 * @dev: ISHTP device pointer
 * @condition: indicate the condition for waiting
 * @timeinc: time slice for every wait cycle, in ms
 * @timeout: time in ms for timeout
 *
 * This function will check special event to be ready in a loop, the loop
 * period is specificd in timeinc. Wait timeout will causes failure.
 *
 * Return: 0 for success else failure code
 */
static int timed_wait_for_timeout(struct ishtp_device *dev, int condition,
				unsigned int timeinc, unsigned int timeout)
{
	bool complete = false;
	int ret;

	do {
		if (condition == WAIT_FOR_FW_RDY) {
			complete = ishtp_fw_is_ready(dev);
		} else if (condition == WAIT_FOR_INPUT_RDY) {
			complete = ish_is_input_ready(dev);
		} else {
			ret = -EINVAL;
			goto out;
		}

		if (!complete) {
			unsigned long left_time;

			left_time = msleep_interruptible(timeinc);
			timeout -= (timeinc - left_time);
		}
	} while (!complete && timeout > 0);

	if (complete)
		ret = 0;
	else
		ret = -EBUSY;

out:
	return ret;
}

#define TIME_SLICE_FOR_FW_RDY_MS		100
#define TIME_SLICE_FOR_INPUT_RDY_MS		100
#define TIMEOUT_FOR_FW_RDY_MS			2000
#define TIMEOUT_FOR_INPUT_RDY_MS		2000

/**
 * ish_fw_reset_handler() - FW reset handler
 * @dev: ishtp device pointer
 *
 * Handle FW reset
 *
 * Return: 0 for success else failure code
 */
static int ish_fw_reset_handler(struct ishtp_device *dev)
{
	uint32_t	reset_id;
	unsigned long	flags;

	/* Read reset ID */
	reset_id = ish_reg_read(dev, IPC_REG_ISH2HOST_MSG) & 0xFFFF;

	/* Clear IPC output queue */
	spin_lock_irqsave(&dev->wr_processing_spinlock, flags);
	list_splice_init(&dev->wr_processing_list, &dev->wr_free_list);
	spin_unlock_irqrestore(&dev->wr_processing_spinlock, flags);

	/* ISHTP notification in IPC_RESET */
	ishtp_reset_handler(dev);

	if (!ish_is_input_ready(dev))
		timed_wait_for_timeout(dev, WAIT_FOR_INPUT_RDY,
			TIME_SLICE_FOR_INPUT_RDY_MS, TIMEOUT_FOR_INPUT_RDY_MS);

	/* ISH FW is dead */
	if (!ish_is_input_ready(dev))
		return	-EPIPE;
	/*
	 * Set HOST2ISH.ILUP. Apparently we need this BEFORE sending
	 * RESET_NOTIFY_ACK - FW will be checking for it
	 */
	ish_set_host_rdy(dev);
	/* Send RESET_NOTIFY_ACK (with reset_id) */
	ipc_send_mng_msg(dev, MNG_RESET_NOTIFY_ACK, &reset_id,
			 sizeof(uint32_t));

	/* Wait for ISH FW'es ILUP and ISHTP_READY */
	timed_wait_for_timeout(dev, WAIT_FOR_FW_RDY,
			TIME_SLICE_FOR_FW_RDY_MS, TIMEOUT_FOR_FW_RDY_MS);
	if (!ishtp_fw_is_ready(dev)) {
		/* ISH FW is dead */
		uint32_t	ish_status;

		ish_status = _ish_read_fw_sts_reg(dev);
		dev_err(dev->devc,
			"[ishtp-ish]: completed reset, ISH is dead (FWSTS = %08X)\n",
			ish_status);
		return -ENODEV;
	}
	return	0;
}

#define TIMEOUT_FOR_HW_RDY_MS			300

/**
 * ish_fw_reset_work_fn() - FW reset worker function
 * @unused: not used
 *
 * Call ish_fw_reset_handler to complete FW reset
 */
static void fw_reset_work_fn(struct work_struct *unused)
{
	int	rv;

	rv = ish_fw_reset_handler(ishtp_dev);
	if (!rv) {
		/* ISH is ILUP & ISHTP-ready. Restart ISHTP */
		msleep_interruptible(TIMEOUT_FOR_HW_RDY_MS);
		ishtp_dev->recvd_hw_ready = 1;
		wake_up_interruptible(&ishtp_dev->wait_hw_ready);

		/* ISHTP notification in IPC_RESET sequence completion */
		ishtp_reset_compl_handler(ishtp_dev);
	} else
		dev_err(ishtp_dev->devc, "[ishtp-ish]: FW reset failed (%d)\n",
			rv);
}

/**
 * _ish_sync_fw_clock() -Sync FW clock with the OS clock
 * @dev: ishtp device pointer
 *
 * Sync FW and OS time
 */
static void _ish_sync_fw_clock(struct ishtp_device *dev)
{
	static unsigned long	prev_sync;
	uint64_t	usec;

	if (prev_sync && jiffies - prev_sync < 20 * HZ)
		return;

	prev_sync = jiffies;
	usec = ktime_to_us(ktime_get_boottime());
	ipc_send_mng_msg(dev, MNG_SYNC_FW_CLOCK, &usec, sizeof(uint64_t));
}

/**
 * recv_ipc() - Receive and process IPC management messages
 * @dev: ishtp device instance
 * @doorbell_val: doorbell value
 *
 * This function runs in ISR context.
 * NOTE: Any other mng command than reset_notify and reset_notify_ack
 * won't wake BH handler
 */
static void	recv_ipc(struct ishtp_device *dev, uint32_t doorbell_val)
{
	uint32_t	mng_cmd;

	mng_cmd = IPC_HEADER_GET_MNG_CMD(doorbell_val);

	switch (mng_cmd) {
	default:
		break;

	case MNG_RX_CMPL_INDICATION:
		if (dev->suspend_flag) {
			dev->suspend_flag = 0;
			wake_up_interruptible(&dev->suspend_wait);
		}
		if (dev->resume_flag) {
			dev->resume_flag = 0;
			wake_up_interruptible(&dev->resume_wait);
		}

		write_ipc_from_queue(dev);
		break;

	case MNG_RESET_NOTIFY:
		if (!ishtp_dev) {
			ishtp_dev = dev;
			INIT_WORK(&fw_reset_work, fw_reset_work_fn);
		}
		schedule_work(&fw_reset_work);
		break;

	case MNG_RESET_NOTIFY_ACK:
		dev->recvd_hw_ready = 1;
		wake_up_interruptible(&dev->wait_hw_ready);
		break;
	}
}

/**
 * ish_irq_handler() - ISH IRQ handler
 * @irq: irq number
 * @dev_id: ishtp device pointer
 *
 * ISH IRQ handler. If interrupt is generated and is for ISH it will process
 * the interrupt.
 */
irqreturn_t ish_irq_handler(int irq, void *dev_id)
{
	struct ishtp_device	*dev = dev_id;
	uint32_t	doorbell_val;
	bool	interrupt_generated;

	/* Check that it's interrupt from ISH (may be shared) */
	interrupt_generated = check_generated_interrupt(dev);

	if (!interrupt_generated)
		return IRQ_NONE;

	doorbell_val = ish_reg_read(dev, IPC_REG_ISH2HOST_DRBL);
	if (!IPC_IS_BUSY(doorbell_val))
		return IRQ_HANDLED;

	if (dev->dev_state == ISHTP_DEV_DISABLED)
		return	IRQ_HANDLED;

	/* Sanity check: IPC dgram length in header */
	if (IPC_HEADER_GET_LENGTH(doorbell_val) > IPC_PAYLOAD_SIZE) {
		dev_err(dev->devc,
			"IPC hdr - bad length: %u; dropped\n",
			(unsigned int)IPC_HEADER_GET_LENGTH(doorbell_val));
		goto	eoi;
	}

	switch (IPC_HEADER_GET_PROTOCOL(doorbell_val)) {
	default:
		break;
	case IPC_PROTOCOL_MNG:
		recv_ipc(dev, doorbell_val);
		break;
	case IPC_PROTOCOL_ISHTP:
		ishtp_recv(dev);
		break;
	}

eoi:
	/* Update IPC counters */
	++dev->ipc_rx_cnt;
	dev->ipc_rx_bytes_cnt += IPC_HEADER_GET_LENGTH(doorbell_val);

	ish_reg_write(dev, IPC_REG_ISH2HOST_DRBL, 0);
	/* Flush write to doorbell */
	ish_reg_read(dev, IPC_REG_ISH_HOST_FWSTS);

	return	IRQ_HANDLED;
}

/**
 * ish_disable_dma() - disable dma communication between host and ISHFW
 * @dev: ishtp device pointer
 *
 * Clear the dma enable bit and wait for dma inactive.
 *
 * Return: 0 for success else error code.
 */
static int ish_disable_dma(struct ishtp_device *dev)
{
	unsigned int	dma_delay;

	/* Clear the dma enable bit */
	ish_reg_write(dev, IPC_REG_ISH_RMP2, 0);

	/* wait for dma inactive */
	for (dma_delay = 0; dma_delay < MAX_DMA_DELAY &&
		_ish_read_fw_sts_reg(dev) & (IPC_ISH_IN_DMA);
		dma_delay += 5)
		mdelay(5);

	if (dma_delay >= MAX_DMA_DELAY) {
		dev_err(dev->devc,
			"Wait for DMA inactive timeout\n");
		return	-EBUSY;
	}

	return 0;
}

/**
 * ish_wakeup() - wakeup ishfw from waiting-for-host state
 * @dev: ishtp device pointer
 *
 * Set the dma enable bit and send a void message to FW,
 * it wil wakeup FW from waiting-for-host state.
 */
static void ish_wakeup(struct ishtp_device *dev)
{
	/* Set dma enable bit */
	ish_reg_write(dev, IPC_REG_ISH_RMP2, IPC_RMP2_DMA_ENABLED);

	/*
	 * Send 0 IPC message so that ISH FW wakes up if it was already
	 * asleep.
	 */
	ish_reg_write(dev, IPC_REG_HOST2ISH_DRBL, IPC_DRBL_BUSY_BIT);

	/* Flush writes to doorbell and REMAP2 */
	ish_reg_read(dev, IPC_REG_ISH_HOST_FWSTS);
}

/**
 * _ish_hw_reset() - HW reset
 * @dev: ishtp device pointer
 *
 * Reset ISH HW to recover if any error
 *
 * Return: 0 for success else error fault code
 */
static int _ish_hw_reset(struct ishtp_device *dev)
{
	struct pci_dev *pdev = dev->pdev;
	int	rv;
	uint16_t csr;

	if (!pdev)
		return	-ENODEV;

	rv = pci_reset_function(pdev);
	if (!rv)
		dev->dev_state = ISHTP_DEV_RESETTING;

	if (!pdev->pm_cap) {
		dev_err(&pdev->dev, "Can't reset - no PM caps\n");
		return	-EINVAL;
	}

	/* Disable dma communication between FW and host */
	if (ish_disable_dma(dev)) {
		dev_err(&pdev->dev,
			"Can't reset - stuck with DMA in-progress\n");
		return	-EBUSY;
	}

	pci_read_config_word(pdev, pdev->pm_cap + PCI_PM_CTRL, &csr);

	csr &= ~PCI_PM_CTRL_STATE_MASK;
	csr |= PCI_D3hot;
	pci_write_config_word(pdev, pdev->pm_cap + PCI_PM_CTRL, csr);

	mdelay(pdev->d3_delay);

	csr &= ~PCI_PM_CTRL_STATE_MASK;
	csr |= PCI_D0;
	pci_write_config_word(pdev, pdev->pm_cap + PCI_PM_CTRL, csr);

	/* Now we can enable ISH DMA operation and wakeup ISHFW */
	ish_wakeup(dev);

	return	0;
}

/**
 * _ish_ipc_reset() - IPC reset
 * @dev: ishtp device pointer
 *
 * Resets host and fw IPC and upper layers
 *
 * Return: 0 for success else error fault code
 */
static int _ish_ipc_reset(struct ishtp_device *dev)
{
	struct ipc_rst_payload_type ipc_mng_msg;
	int	rv = 0;

	ipc_mng_msg.reset_id = 1;
	ipc_mng_msg.reserved = 0;

	set_host_ready(dev);

	/* Clear the incoming doorbell */
	ish_reg_write(dev, IPC_REG_ISH2HOST_DRBL, 0);
	/* Flush write to doorbell */
	ish_reg_read(dev, IPC_REG_ISH_HOST_FWSTS);

	dev->recvd_hw_ready = 0;

	/* send message */
	rv = ipc_send_mng_msg(dev, MNG_RESET_NOTIFY, &ipc_mng_msg,
		sizeof(struct ipc_rst_payload_type));
	if (rv) {
		dev_err(dev->devc, "Failed to send IPC MNG_RESET_NOTIFY\n");
		return	rv;
	}

	wait_event_interruptible_timeout(dev->wait_hw_ready,
					 dev->recvd_hw_ready, 2 * HZ);
	if (!dev->recvd_hw_ready) {
		dev_err(dev->devc, "Timed out waiting for HW ready\n");
		rv = -ENODEV;
	}

	return rv;
}

/**
 * ish_hw_start() -Start ISH HW
 * @dev: ishtp device pointer
 *
 * Set host to ready state and wait for FW reset
 *
 * Return: 0 for success else error fault code
 */
int ish_hw_start(struct ishtp_device *dev)
{
	ish_set_host_rdy(dev);

	/* After that we can enable ISH DMA operation and wakeup ISHFW */
	ish_wakeup(dev);

	set_host_ready(dev);

	/* wait for FW-initiated reset flow */
	if (!dev->recvd_hw_ready)
		wait_event_interruptible_timeout(dev->wait_hw_ready,
						 dev->recvd_hw_ready,
						 10 * HZ);

	if (!dev->recvd_hw_ready) {
		dev_err(dev->devc,
			"[ishtp-ish]: Timed out waiting for FW-initiated reset\n");
		return	-ENODEV;
	}

	return 0;
}

/**
 * ish_ipc_get_header() -Get doorbell value
 * @dev: ishtp device pointer
 * @length: length of message
 * @busy: busy status
 *
 * Get door bell value from message header
 *
 * Return: door bell value
 */
static uint32_t ish_ipc_get_header(struct ishtp_device *dev, int length,
				   int busy)
{
	uint32_t drbl_val;

	drbl_val = IPC_BUILD_HEADER(length, IPC_PROTOCOL_ISHTP, busy);

	return drbl_val;
}

static const struct ishtp_hw_ops ish_hw_ops = {
	.hw_reset = _ish_hw_reset,
	.ipc_reset = _ish_ipc_reset,
	.ipc_get_header = ish_ipc_get_header,
	.ishtp_read = _ishtp_read,
	.write = write_ipc_to_queue,
	.get_fw_status = _ish_read_fw_sts_reg,
	.sync_fw_clock = _ish_sync_fw_clock,
	.ishtp_read_hdr = _ishtp_read_hdr
};

/**
 * ish_dev_init() -Initialize ISH devoce
 * @pdev: PCI device
 *
 * Allocate ISHTP device and initialize IPC processing
 *
 * Return: ISHTP device instance on success else NULL
 */
struct ishtp_device *ish_dev_init(struct pci_dev *pdev)
{
	struct ishtp_device *dev;
	int	i;

	dev = devm_kzalloc(&pdev->dev,
			   sizeof(struct ishtp_device) + sizeof(struct ish_hw),
			   GFP_KERNEL);
	if (!dev)
		return NULL;

	ishtp_device_init(dev);

	init_waitqueue_head(&dev->wait_hw_ready);

	spin_lock_init(&dev->wr_processing_spinlock);
	spin_lock_init(&dev->out_ipc_spinlock);

	/* Init IPC processing and free lists */
	INIT_LIST_HEAD(&dev->wr_processing_list);
	INIT_LIST_HEAD(&dev->wr_free_list);
	for (i = 0; i < IPC_TX_FIFO_SIZE; i++) {
		struct wr_msg_ctl_info	*tx_buf;

		tx_buf = devm_kzalloc(&pdev->dev,
				      sizeof(struct wr_msg_ctl_info),
				      GFP_KERNEL);
		if (!tx_buf) {
			/*
			 * IPC buffers may be limited or not available
			 * at all - although this shouldn't happen
			 */
			dev_err(dev->devc,
				"[ishtp-ish]: failure in Tx FIFO allocations (%d)\n",
				i);
			break;
		}
		list_add_tail(&tx_buf->link, &dev->wr_free_list);
	}

	dev->ops = &ish_hw_ops;
	dev->devc = &pdev->dev;
	dev->mtu = IPC_PAYLOAD_SIZE - sizeof(struct ishtp_msg_hdr);
	return dev;
}

/**
 * ish_device_disable() - Disable ISH device
 * @dev: ISHTP device pointer
 *
 * Disable ISH by clearing host ready to inform firmware.
 */
void	ish_device_disable(struct ishtp_device *dev)
{
	struct pci_dev *pdev = dev->pdev;

	if (!pdev)
		return;

	/* Disable dma communication between FW and host */
	if (ish_disable_dma(dev)) {
		dev_err(&pdev->dev,
			"Can't reset - stuck with DMA in-progress\n");
		return;
	}

	/* Put ISH to D3hot state for power saving */
	pci_set_power_state(pdev, PCI_D3hot);

	dev->dev_state = ISHTP_DEV_DISABLED;
	ish_clr_host_rdy(dev);
}
