/*
 * Marvell 88SE64xx/88SE94xx main function
 *
 * Copyright 2007 Red Hat, Inc.
 * Copyright 2008 Marvell. <kewei@marvell.com>
 * Copyright 2009-2011 Marvell. <yuxiangl@marvell.com>
 *
 * This file is licensed under GPLv2.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; version 2 of the
 * License.
 *
 * 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.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
 * USA
*/

#include "mv_sas.h"

static int mvs_find_tag(struct mvs_info *mvi, struct sas_task *task, u32 *tag)
{
	if (task->lldd_task) {
		struct mvs_slot_info *slot;
		slot = task->lldd_task;
		*tag = slot->slot_tag;
		return 1;
	}
	return 0;
}

void mvs_tag_clear(struct mvs_info *mvi, u32 tag)
{
	void *bitmap = mvi->tags;
	clear_bit(tag, bitmap);
}

void mvs_tag_free(struct mvs_info *mvi, u32 tag)
{
	mvs_tag_clear(mvi, tag);
}

void mvs_tag_set(struct mvs_info *mvi, unsigned int tag)
{
	void *bitmap = mvi->tags;
	set_bit(tag, bitmap);
}

inline int mvs_tag_alloc(struct mvs_info *mvi, u32 *tag_out)
{
	unsigned int index, tag;
	void *bitmap = mvi->tags;

	index = find_first_zero_bit(bitmap, mvi->tags_num);
	tag = index;
	if (tag >= mvi->tags_num)
		return -SAS_QUEUE_FULL;
	mvs_tag_set(mvi, tag);
	*tag_out = tag;
	return 0;
}

void mvs_tag_init(struct mvs_info *mvi)
{
	int i;
	for (i = 0; i < mvi->tags_num; ++i)
		mvs_tag_clear(mvi, i);
}

struct mvs_info *mvs_find_dev_mvi(struct domain_device *dev)
{
	unsigned long i = 0, j = 0, hi = 0;
	struct sas_ha_struct *sha = dev->port->ha;
	struct mvs_info *mvi = NULL;
	struct asd_sas_phy *phy;

	while (sha->sas_port[i]) {
		if (sha->sas_port[i] == dev->port) {
			phy =  container_of(sha->sas_port[i]->phy_list.next,
				struct asd_sas_phy, port_phy_el);
			j = 0;
			while (sha->sas_phy[j]) {
				if (sha->sas_phy[j] == phy)
					break;
				j++;
			}
			break;
		}
		i++;
	}
	hi = j/((struct mvs_prv_info *)sha->lldd_ha)->n_phy;
	mvi = ((struct mvs_prv_info *)sha->lldd_ha)->mvi[hi];

	return mvi;

}

int mvs_find_dev_phyno(struct domain_device *dev, int *phyno)
{
	unsigned long i = 0, j = 0, n = 0, num = 0;
	struct mvs_device *mvi_dev = (struct mvs_device *)dev->lldd_dev;
	struct mvs_info *mvi = mvi_dev->mvi_info;
	struct sas_ha_struct *sha = dev->port->ha;

	while (sha->sas_port[i]) {
		if (sha->sas_port[i] == dev->port) {
			struct asd_sas_phy *phy;
			list_for_each_entry(phy,
				&sha->sas_port[i]->phy_list, port_phy_el) {
				j = 0;
				while (sha->sas_phy[j]) {
					if (sha->sas_phy[j] == phy)
						break;
					j++;
				}
				phyno[n] = (j >= mvi->chip->n_phy) ?
					(j - mvi->chip->n_phy) : j;
				num++;
				n++;
			}
			break;
		}
		i++;
	}
	return num;
}

struct mvs_device *mvs_find_dev_by_reg_set(struct mvs_info *mvi,
						u8 reg_set)
{
	u32 dev_no;
	for (dev_no = 0; dev_no < MVS_MAX_DEVICES; dev_no++) {
		if (mvi->devices[dev_no].taskfileset == MVS_ID_NOT_MAPPED)
			continue;

		if (mvi->devices[dev_no].taskfileset == reg_set)
			return &mvi->devices[dev_no];
	}
	return NULL;
}

static inline void mvs_free_reg_set(struct mvs_info *mvi,
				struct mvs_device *dev)
{
	if (!dev) {
		mv_printk("device has been free.\n");
		return;
	}
	if (dev->taskfileset == MVS_ID_NOT_MAPPED)
		return;
	MVS_CHIP_DISP->free_reg_set(mvi, &dev->taskfileset);
}

static inline u8 mvs_assign_reg_set(struct mvs_info *mvi,
				struct mvs_device *dev)
{
	if (dev->taskfileset != MVS_ID_NOT_MAPPED)
		return 0;
	return MVS_CHIP_DISP->assign_reg_set(mvi, &dev->taskfileset);
}

void mvs_phys_reset(struct mvs_info *mvi, u32 phy_mask, int hard)
{
	u32 no;
	for_each_phy(phy_mask, phy_mask, no) {
		if (!(phy_mask & 1))
			continue;
		MVS_CHIP_DISP->phy_reset(mvi, no, hard);
	}
}

int mvs_phy_control(struct asd_sas_phy *sas_phy, enum phy_func func,
			void *funcdata)
{
	int rc = 0, phy_id = sas_phy->id;
	u32 tmp, i = 0, hi;
	struct sas_ha_struct *sha = sas_phy->ha;
	struct mvs_info *mvi = NULL;

	while (sha->sas_phy[i]) {
		if (sha->sas_phy[i] == sas_phy)
			break;
		i++;
	}
	hi = i/((struct mvs_prv_info *)sha->lldd_ha)->n_phy;
	mvi = ((struct mvs_prv_info *)sha->lldd_ha)->mvi[hi];

	switch (func) {
	case PHY_FUNC_SET_LINK_RATE:
		MVS_CHIP_DISP->phy_set_link_rate(mvi, phy_id, funcdata);
		break;

	case PHY_FUNC_HARD_RESET:
		tmp = MVS_CHIP_DISP->read_phy_ctl(mvi, phy_id);
		if (tmp & PHY_RST_HARD)
			break;
		MVS_CHIP_DISP->phy_reset(mvi, phy_id, MVS_HARD_RESET);
		break;

	case PHY_FUNC_LINK_RESET:
		MVS_CHIP_DISP->phy_enable(mvi, phy_id);
		MVS_CHIP_DISP->phy_reset(mvi, phy_id, MVS_SOFT_RESET);
		break;

	case PHY_FUNC_DISABLE:
		MVS_CHIP_DISP->phy_disable(mvi, phy_id);
		break;
	case PHY_FUNC_RELEASE_SPINUP_HOLD:
	default:
		rc = -ENOSYS;
	}
	msleep(200);
	return rc;
}

void mvs_set_sas_addr(struct mvs_info *mvi, int port_id, u32 off_lo,
		      u32 off_hi, u64 sas_addr)
{
	u32 lo = (u32)sas_addr;
	u32 hi = (u32)(sas_addr>>32);

	MVS_CHIP_DISP->write_port_cfg_addr(mvi, port_id, off_lo);
	MVS_CHIP_DISP->write_port_cfg_data(mvi, port_id, lo);
	MVS_CHIP_DISP->write_port_cfg_addr(mvi, port_id, off_hi);
	MVS_CHIP_DISP->write_port_cfg_data(mvi, port_id, hi);
}

static void mvs_bytes_dmaed(struct mvs_info *mvi, int i)
{
	struct mvs_phy *phy = &mvi->phy[i];
	struct asd_sas_phy *sas_phy = &phy->sas_phy;
	struct sas_ha_struct *sas_ha;
	if (!phy->phy_attached)
		return;

	if (!(phy->att_dev_info & PORT_DEV_TRGT_MASK)
		&& phy->phy_type & PORT_TYPE_SAS) {
		return;
	}

	sas_ha = mvi->sas;
	sas_ha->notify_phy_event(sas_phy, PHYE_OOB_DONE);

	if (sas_phy->phy) {
		struct sas_phy *sphy = sas_phy->phy;

		sphy->negotiated_linkrate = sas_phy->linkrate;
		sphy->minimum_linkrate = phy->minimum_linkrate;
		sphy->minimum_linkrate_hw = SAS_LINK_RATE_1_5_GBPS;
		sphy->maximum_linkrate = phy->maximum_linkrate;
		sphy->maximum_linkrate_hw = MVS_CHIP_DISP->phy_max_link_rate();
	}

	if (phy->phy_type & PORT_TYPE_SAS) {
		struct sas_identify_frame *id;

		id = (struct sas_identify_frame *)phy->frame_rcvd;
		id->dev_type = phy->identify.device_type;
		id->initiator_bits = SAS_PROTOCOL_ALL;
		id->target_bits = phy->identify.target_port_protocols;

		/* direct attached SAS device */
		if (phy->att_dev_info & PORT_SSP_TRGT_MASK) {
			MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_PHY_STAT);
			MVS_CHIP_DISP->write_port_cfg_data(mvi, i, 0x00);
		}
	} else if (phy->phy_type & PORT_TYPE_SATA) {
		/*Nothing*/
	}
	mv_dprintk("phy %d byte dmaded.\n", i + mvi->id * mvi->chip->n_phy);

	sas_phy->frame_rcvd_size = phy->frame_rcvd_size;

	mvi->sas->notify_port_event(sas_phy,
				   PORTE_BYTES_DMAED);
}

void mvs_scan_start(struct Scsi_Host *shost)
{
	int i, j;
	unsigned short core_nr;
	struct mvs_info *mvi;
	struct sas_ha_struct *sha = SHOST_TO_SAS_HA(shost);
	struct mvs_prv_info *mvs_prv = sha->lldd_ha;

	core_nr = ((struct mvs_prv_info *)sha->lldd_ha)->n_host;

	for (j = 0; j < core_nr; j++) {
		mvi = ((struct mvs_prv_info *)sha->lldd_ha)->mvi[j];
		for (i = 0; i < mvi->chip->n_phy; ++i)
			mvs_bytes_dmaed(mvi, i);
	}
	mvs_prv->scan_finished = 1;
}

int mvs_scan_finished(struct Scsi_Host *shost, unsigned long time)
{
	struct sas_ha_struct *sha = SHOST_TO_SAS_HA(shost);
	struct mvs_prv_info *mvs_prv = sha->lldd_ha;

	if (mvs_prv->scan_finished == 0)
		return 0;

	sas_drain_work(sha);
	return 1;
}

static int mvs_task_prep_smp(struct mvs_info *mvi,
			     struct mvs_task_exec_info *tei)
{
	int elem, rc, i;
	struct sas_ha_struct *sha = mvi->sas;
	struct sas_task *task = tei->task;
	struct mvs_cmd_hdr *hdr = tei->hdr;
	struct domain_device *dev = task->dev;
	struct asd_sas_port *sas_port = dev->port;
	struct sas_phy *sphy = dev->phy;
	struct asd_sas_phy *sas_phy = sha->sas_phy[sphy->number];
	struct scatterlist *sg_req, *sg_resp;
	u32 req_len, resp_len, tag = tei->tag;
	void *buf_tmp;
	u8 *buf_oaf;
	dma_addr_t buf_tmp_dma;
	void *buf_prd;
	struct mvs_slot_info *slot = &mvi->slot_info[tag];
	u32 flags = (tei->n_elem << MCH_PRD_LEN_SHIFT);

	/*
	 * DMA-map SMP request, response buffers
	 */
	sg_req = &task->smp_task.smp_req;
	elem = dma_map_sg(mvi->dev, sg_req, 1, PCI_DMA_TODEVICE);
	if (!elem)
		return -ENOMEM;
	req_len = sg_dma_len(sg_req);

	sg_resp = &task->smp_task.smp_resp;
	elem = dma_map_sg(mvi->dev, sg_resp, 1, PCI_DMA_FROMDEVICE);
	if (!elem) {
		rc = -ENOMEM;
		goto err_out;
	}
	resp_len = SB_RFB_MAX;

	/* must be in dwords */
	if ((req_len & 0x3) || (resp_len & 0x3)) {
		rc = -EINVAL;
		goto err_out_2;
	}

	/*
	 * arrange MVS_SLOT_BUF_SZ-sized DMA buffer according to our needs
	 */

	/* region 1: command table area (MVS_SSP_CMD_SZ bytes) ***** */
	buf_tmp = slot->buf;
	buf_tmp_dma = slot->buf_dma;

	hdr->cmd_tbl = cpu_to_le64(sg_dma_address(sg_req));

	/* region 2: open address frame area (MVS_OAF_SZ bytes) ********* */
	buf_oaf = buf_tmp;
	hdr->open_frame = cpu_to_le64(buf_tmp_dma);

	buf_tmp += MVS_OAF_SZ;
	buf_tmp_dma += MVS_OAF_SZ;

	/* region 3: PRD table *********************************** */
	buf_prd = buf_tmp;
	if (tei->n_elem)
		hdr->prd_tbl = cpu_to_le64(buf_tmp_dma);
	else
		hdr->prd_tbl = 0;

	i = MVS_CHIP_DISP->prd_size() * tei->n_elem;
	buf_tmp += i;
	buf_tmp_dma += i;

	/* region 4: status buffer (larger the PRD, smaller this buf) ****** */
	slot->response = buf_tmp;
	hdr->status_buf = cpu_to_le64(buf_tmp_dma);
	if (mvi->flags & MVF_FLAG_SOC)
		hdr->reserved[0] = 0;

	/*
	 * Fill in TX ring and command slot header
	 */
	slot->tx = mvi->tx_prod;
	mvi->tx[mvi->tx_prod] = cpu_to_le32((TXQ_CMD_SMP << TXQ_CMD_SHIFT) |
					TXQ_MODE_I | tag |
					(MVS_PHY_ID << TXQ_PHY_SHIFT));

	hdr->flags |= flags;
	hdr->lens = cpu_to_le32(((resp_len / 4) << 16) | ((req_len - 4) / 4));
	hdr->tags = cpu_to_le32(tag);
	hdr->data_len = 0;

	/* generate open address frame hdr (first 12 bytes) */
	/* initiator, SMP, ftype 1h */
	buf_oaf[0] = (1 << 7) | (PROTOCOL_SMP << 4) | 0x01;
	buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
	*(u16 *)(buf_oaf + 2) = 0xFFFF;		/* SAS SPEC */
	memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);

	/* fill in PRD (scatter/gather) table, if any */
	MVS_CHIP_DISP->make_prd(task->scatter, tei->n_elem, buf_prd);

	return 0;

err_out_2:
	dma_unmap_sg(mvi->dev, &tei->task->smp_task.smp_resp, 1,
		     PCI_DMA_FROMDEVICE);
err_out:
	dma_unmap_sg(mvi->dev, &tei->task->smp_task.smp_req, 1,
		     PCI_DMA_TODEVICE);
	return rc;
}

static u32 mvs_get_ncq_tag(struct sas_task *task, u32 *tag)
{
	struct ata_queued_cmd *qc = task->uldd_task;

	if (qc) {
		if (qc->tf.command == ATA_CMD_FPDMA_WRITE ||
			qc->tf.command == ATA_CMD_FPDMA_READ) {
			*tag = qc->tag;
			return 1;
		}
	}

	return 0;
}

static int mvs_task_prep_ata(struct mvs_info *mvi,
			     struct mvs_task_exec_info *tei)
{
	struct sas_task *task = tei->task;
	struct domain_device *dev = task->dev;
	struct mvs_device *mvi_dev = dev->lldd_dev;
	struct mvs_cmd_hdr *hdr = tei->hdr;
	struct asd_sas_port *sas_port = dev->port;
	struct mvs_slot_info *slot;
	void *buf_prd;
	u32 tag = tei->tag, hdr_tag;
	u32 flags, del_q;
	void *buf_tmp;
	u8 *buf_cmd, *buf_oaf;
	dma_addr_t buf_tmp_dma;
	u32 i, req_len, resp_len;
	const u32 max_resp_len = SB_RFB_MAX;

	if (mvs_assign_reg_set(mvi, mvi_dev) == MVS_ID_NOT_MAPPED) {
		mv_dprintk("Have not enough regiset for dev %d.\n",
			mvi_dev->device_id);
		return -EBUSY;
	}
	slot = &mvi->slot_info[tag];
	slot->tx = mvi->tx_prod;
	del_q = TXQ_MODE_I | tag |
		(TXQ_CMD_STP << TXQ_CMD_SHIFT) |
		((sas_port->phy_mask & TXQ_PHY_MASK) << TXQ_PHY_SHIFT) |
		(mvi_dev->taskfileset << TXQ_SRS_SHIFT);
	mvi->tx[mvi->tx_prod] = cpu_to_le32(del_q);

	if (task->data_dir == DMA_FROM_DEVICE)
		flags = (MVS_CHIP_DISP->prd_count() << MCH_PRD_LEN_SHIFT);
	else
		flags = (tei->n_elem << MCH_PRD_LEN_SHIFT);

	if (task->ata_task.use_ncq)
		flags |= MCH_FPDMA;
	if (dev->sata_dev.command_set == ATAPI_COMMAND_SET) {
		if (task->ata_task.fis.command != ATA_CMD_ID_ATAPI)
			flags |= MCH_ATAPI;
	}

	hdr->flags = cpu_to_le32(flags);

	if (task->ata_task.use_ncq && mvs_get_ncq_tag(task, &hdr_tag))
		task->ata_task.fis.sector_count |= (u8) (hdr_tag << 3);
	else
		hdr_tag = tag;

	hdr->tags = cpu_to_le32(hdr_tag);

	hdr->data_len = cpu_to_le32(task->total_xfer_len);

	/*
	 * arrange MVS_SLOT_BUF_SZ-sized DMA buffer according to our needs
	 */

	/* region 1: command table area (MVS_ATA_CMD_SZ bytes) ************** */
	buf_cmd = buf_tmp = slot->buf;
	buf_tmp_dma = slot->buf_dma;

	hdr->cmd_tbl = cpu_to_le64(buf_tmp_dma);

	buf_tmp += MVS_ATA_CMD_SZ;
	buf_tmp_dma += MVS_ATA_CMD_SZ;

	/* region 2: open address frame area (MVS_OAF_SZ bytes) ********* */
	/* used for STP.  unused for SATA? */
	buf_oaf = buf_tmp;
	hdr->open_frame = cpu_to_le64(buf_tmp_dma);

	buf_tmp += MVS_OAF_SZ;
	buf_tmp_dma += MVS_OAF_SZ;

	/* region 3: PRD table ********************************************* */
	buf_prd = buf_tmp;

	if (tei->n_elem)
		hdr->prd_tbl = cpu_to_le64(buf_tmp_dma);
	else
		hdr->prd_tbl = 0;
	i = MVS_CHIP_DISP->prd_size() * MVS_CHIP_DISP->prd_count();

	buf_tmp += i;
	buf_tmp_dma += i;

	/* region 4: status buffer (larger the PRD, smaller this buf) ****** */
	slot->response = buf_tmp;
	hdr->status_buf = cpu_to_le64(buf_tmp_dma);
	if (mvi->flags & MVF_FLAG_SOC)
		hdr->reserved[0] = 0;

	req_len = sizeof(struct host_to_dev_fis);
	resp_len = MVS_SLOT_BUF_SZ - MVS_ATA_CMD_SZ -
	    sizeof(struct mvs_err_info) - i;

	/* request, response lengths */
	resp_len = min(resp_len, max_resp_len);
	hdr->lens = cpu_to_le32(((resp_len / 4) << 16) | (req_len / 4));

	if (likely(!task->ata_task.device_control_reg_update))
		task->ata_task.fis.flags |= 0x80; /* C=1: update ATA cmd reg */
	/* fill in command FIS and ATAPI CDB */
	memcpy(buf_cmd, &task->ata_task.fis, sizeof(struct host_to_dev_fis));
	if (dev->sata_dev.command_set == ATAPI_COMMAND_SET)
		memcpy(buf_cmd + STP_ATAPI_CMD,
			task->ata_task.atapi_packet, 16);

	/* generate open address frame hdr (first 12 bytes) */
	/* initiator, STP, ftype 1h */
	buf_oaf[0] = (1 << 7) | (PROTOCOL_STP << 4) | 0x1;
	buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
	*(u16 *)(buf_oaf + 2) = cpu_to_be16(mvi_dev->device_id + 1);
	memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);

	/* fill in PRD (scatter/gather) table, if any */
	MVS_CHIP_DISP->make_prd(task->scatter, tei->n_elem, buf_prd);

	if (task->data_dir == DMA_FROM_DEVICE)
		MVS_CHIP_DISP->dma_fix(mvi, sas_port->phy_mask,
				TRASH_BUCKET_SIZE, tei->n_elem, buf_prd);

	return 0;
}

static int mvs_task_prep_ssp(struct mvs_info *mvi,
			     struct mvs_task_exec_info *tei, int is_tmf,
			     struct mvs_tmf_task *tmf)
{
	struct sas_task *task = tei->task;
	struct mvs_cmd_hdr *hdr = tei->hdr;
	struct mvs_port *port = tei->port;
	struct domain_device *dev = task->dev;
	struct mvs_device *mvi_dev = dev->lldd_dev;
	struct asd_sas_port *sas_port = dev->port;
	struct mvs_slot_info *slot;
	void *buf_prd;
	struct ssp_frame_hdr *ssp_hdr;
	void *buf_tmp;
	u8 *buf_cmd, *buf_oaf, fburst = 0;
	dma_addr_t buf_tmp_dma;
	u32 flags;
	u32 resp_len, req_len, i, tag = tei->tag;
	const u32 max_resp_len = SB_RFB_MAX;
	u32 phy_mask;

	slot = &mvi->slot_info[tag];

	phy_mask = ((port->wide_port_phymap) ? port->wide_port_phymap :
		sas_port->phy_mask) & TXQ_PHY_MASK;

	slot->tx = mvi->tx_prod;
	mvi->tx[mvi->tx_prod] = cpu_to_le32(TXQ_MODE_I | tag |
				(TXQ_CMD_SSP << TXQ_CMD_SHIFT) |
				(phy_mask << TXQ_PHY_SHIFT));

	flags = MCH_RETRY;
	if (task->ssp_task.enable_first_burst) {
		flags |= MCH_FBURST;
		fburst = (1 << 7);
	}
	if (is_tmf)
		flags |= (MCH_SSP_FR_TASK << MCH_SSP_FR_TYPE_SHIFT);
	else
		flags |= (MCH_SSP_FR_CMD << MCH_SSP_FR_TYPE_SHIFT);

	hdr->flags = cpu_to_le32(flags | (tei->n_elem << MCH_PRD_LEN_SHIFT));
	hdr->tags = cpu_to_le32(tag);
	hdr->data_len = cpu_to_le32(task->total_xfer_len);

	/*
	 * arrange MVS_SLOT_BUF_SZ-sized DMA buffer according to our needs
	 */

	/* region 1: command table area (MVS_SSP_CMD_SZ bytes) ************** */
	buf_cmd = buf_tmp = slot->buf;
	buf_tmp_dma = slot->buf_dma;

	hdr->cmd_tbl = cpu_to_le64(buf_tmp_dma);

	buf_tmp += MVS_SSP_CMD_SZ;
	buf_tmp_dma += MVS_SSP_CMD_SZ;

	/* region 2: open address frame area (MVS_OAF_SZ bytes) ********* */
	buf_oaf = buf_tmp;
	hdr->open_frame = cpu_to_le64(buf_tmp_dma);

	buf_tmp += MVS_OAF_SZ;
	buf_tmp_dma += MVS_OAF_SZ;

	/* region 3: PRD table ********************************************* */
	buf_prd = buf_tmp;
	if (tei->n_elem)
		hdr->prd_tbl = cpu_to_le64(buf_tmp_dma);
	else
		hdr->prd_tbl = 0;

	i = MVS_CHIP_DISP->prd_size() * tei->n_elem;
	buf_tmp += i;
	buf_tmp_dma += i;

	/* region 4: status buffer (larger the PRD, smaller this buf) ****** */
	slot->response = buf_tmp;
	hdr->status_buf = cpu_to_le64(buf_tmp_dma);
	if (mvi->flags & MVF_FLAG_SOC)
		hdr->reserved[0] = 0;

	resp_len = MVS_SLOT_BUF_SZ - MVS_SSP_CMD_SZ - MVS_OAF_SZ -
	    sizeof(struct mvs_err_info) - i;
	resp_len = min(resp_len, max_resp_len);

	req_len = sizeof(struct ssp_frame_hdr) + 28;

	/* request, response lengths */
	hdr->lens = cpu_to_le32(((resp_len / 4) << 16) | (req_len / 4));

	/* generate open address frame hdr (first 12 bytes) */
	/* initiator, SSP, ftype 1h */
	buf_oaf[0] = (1 << 7) | (PROTOCOL_SSP << 4) | 0x1;
	buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
	*(u16 *)(buf_oaf + 2) = cpu_to_be16(mvi_dev->device_id + 1);
	memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);

	/* fill in SSP frame header (Command Table.SSP frame header) */
	ssp_hdr = (struct ssp_frame_hdr *)buf_cmd;

	if (is_tmf)
		ssp_hdr->frame_type = SSP_TASK;
	else
		ssp_hdr->frame_type = SSP_COMMAND;

	memcpy(ssp_hdr->hashed_dest_addr, dev->hashed_sas_addr,
	       HASHED_SAS_ADDR_SIZE);
	memcpy(ssp_hdr->hashed_src_addr,
	       dev->hashed_sas_addr, HASHED_SAS_ADDR_SIZE);
	ssp_hdr->tag = cpu_to_be16(tag);

	/* fill in IU for TASK and Command Frame */
	buf_cmd += sizeof(*ssp_hdr);
	memcpy(buf_cmd, &task->ssp_task.LUN, 8);

	if (ssp_hdr->frame_type != SSP_TASK) {
		buf_cmd[9] = fburst | task->ssp_task.task_attr |
				(task->ssp_task.task_prio << 3);
		memcpy(buf_cmd + 12, &task->ssp_task.cdb, 16);
	} else{
		buf_cmd[10] = tmf->tmf;
		switch (tmf->tmf) {
		case TMF_ABORT_TASK:
		case TMF_QUERY_TASK:
			buf_cmd[12] =
				(tmf->tag_of_task_to_be_managed >> 8) & 0xff;
			buf_cmd[13] =
				tmf->tag_of_task_to_be_managed & 0xff;
			break;
		default:
			break;
		}
	}
	/* fill in PRD (scatter/gather) table, if any */
	MVS_CHIP_DISP->make_prd(task->scatter, tei->n_elem, buf_prd);
	return 0;
}

#define	DEV_IS_GONE(mvi_dev)	((!mvi_dev || (mvi_dev->dev_type == SAS_PHY_UNUSED)))
static int mvs_task_prep(struct sas_task *task, struct mvs_info *mvi, int is_tmf,
				struct mvs_tmf_task *tmf, int *pass)
{
	struct domain_device *dev = task->dev;
	struct mvs_device *mvi_dev = dev->lldd_dev;
	struct mvs_task_exec_info tei;
	struct mvs_slot_info *slot;
	u32 tag = 0xdeadbeef, n_elem = 0;
	int rc = 0;

	if (!dev->port) {
		struct task_status_struct *tsm = &task->task_status;

		tsm->resp = SAS_TASK_UNDELIVERED;
		tsm->stat = SAS_PHY_DOWN;
		/*
		 * libsas will use dev->port, should
		 * not call task_done for sata
		 */
		if (dev->dev_type != SAS_SATA_DEV)
			task->task_done(task);
		return rc;
	}

	if (DEV_IS_GONE(mvi_dev)) {
		if (mvi_dev)
			mv_dprintk("device %d not ready.\n",
				mvi_dev->device_id);
		else
			mv_dprintk("device %016llx not ready.\n",
				SAS_ADDR(dev->sas_addr));

			rc = SAS_PHY_DOWN;
			return rc;
	}
	tei.port = dev->port->lldd_port;
	if (tei.port && !tei.port->port_attached && !tmf) {
		if (sas_protocol_ata(task->task_proto)) {
			struct task_status_struct *ts = &task->task_status;
			mv_dprintk("SATA/STP port %d does not attach"
					"device.\n", dev->port->id);
			ts->resp = SAS_TASK_COMPLETE;
			ts->stat = SAS_PHY_DOWN;

			task->task_done(task);

		} else {
			struct task_status_struct *ts = &task->task_status;
			mv_dprintk("SAS port %d does not attach"
				"device.\n", dev->port->id);
			ts->resp = SAS_TASK_UNDELIVERED;
			ts->stat = SAS_PHY_DOWN;
			task->task_done(task);
		}
		return rc;
	}

	if (!sas_protocol_ata(task->task_proto)) {
		if (task->num_scatter) {
			n_elem = dma_map_sg(mvi->dev,
					    task->scatter,
					    task->num_scatter,
					    task->data_dir);
			if (!n_elem) {
				rc = -ENOMEM;
				goto prep_out;
			}
		}
	} else {
		n_elem = task->num_scatter;
	}

	rc = mvs_tag_alloc(mvi, &tag);
	if (rc)
		goto err_out;

	slot = &mvi->slot_info[tag];

	task->lldd_task = NULL;
	slot->n_elem = n_elem;
	slot->slot_tag = tag;

	slot->buf = pci_pool_alloc(mvi->dma_pool, GFP_ATOMIC, &slot->buf_dma);
	if (!slot->buf)
		goto err_out_tag;
	memset(slot->buf, 0, MVS_SLOT_BUF_SZ);

	tei.task = task;
	tei.hdr = &mvi->slot[tag];
	tei.tag = tag;
	tei.n_elem = n_elem;
	switch (task->task_proto) {
	case SAS_PROTOCOL_SMP:
		rc = mvs_task_prep_smp(mvi, &tei);
		break;
	case SAS_PROTOCOL_SSP:
		rc = mvs_task_prep_ssp(mvi, &tei, is_tmf, tmf);
		break;
	case SAS_PROTOCOL_SATA:
	case SAS_PROTOCOL_STP:
	case SAS_PROTOCOL_SATA | SAS_PROTOCOL_STP:
		rc = mvs_task_prep_ata(mvi, &tei);
		break;
	default:
		dev_printk(KERN_ERR, mvi->dev,
			"unknown sas_task proto: 0x%x\n",
			task->task_proto);
		rc = -EINVAL;
		break;
	}

	if (rc) {
		mv_dprintk("rc is %x\n", rc);
		goto err_out_slot_buf;
	}
	slot->task = task;
	slot->port = tei.port;
	task->lldd_task = slot;
	list_add_tail(&slot->entry, &tei.port->list);
	spin_lock(&task->task_state_lock);
	task->task_state_flags |= SAS_TASK_AT_INITIATOR;
	spin_unlock(&task->task_state_lock);

	mvi_dev->running_req++;
	++(*pass);
	mvi->tx_prod = (mvi->tx_prod + 1) & (MVS_CHIP_SLOT_SZ - 1);

	return rc;

err_out_slot_buf:
	pci_pool_free(mvi->dma_pool, slot->buf, slot->buf_dma);
err_out_tag:
	mvs_tag_free(mvi, tag);
err_out:

	dev_printk(KERN_ERR, mvi->dev, "mvsas prep failed[%d]!\n", rc);
	if (!sas_protocol_ata(task->task_proto))
		if (n_elem)
			dma_unmap_sg(mvi->dev, task->scatter, n_elem,
				     task->data_dir);
prep_out:
	return rc;
}

static struct mvs_task_list *mvs_task_alloc_list(int *num, gfp_t gfp_flags)
{
	struct mvs_task_list *first = NULL;

	for (; *num > 0; --*num) {
		struct mvs_task_list *mvs_list = kmem_cache_zalloc(mvs_task_list_cache, gfp_flags);

		if (!mvs_list)
			break;

		INIT_LIST_HEAD(&mvs_list->list);
		if (!first)
			first = mvs_list;
		else
			list_add_tail(&mvs_list->list, &first->list);

	}

	return first;
}

static inline void mvs_task_free_list(struct mvs_task_list *mvs_list)
{
	LIST_HEAD(list);
	struct list_head *pos, *a;
	struct mvs_task_list *mlist = NULL;

	__list_add(&list, mvs_list->list.prev, &mvs_list->list);

	list_for_each_safe(pos, a, &list) {
		list_del_init(pos);
		mlist = list_entry(pos, struct mvs_task_list, list);
		kmem_cache_free(mvs_task_list_cache, mlist);
	}
}

static int mvs_task_exec(struct sas_task *task, const int num, gfp_t gfp_flags,
				struct completion *completion, int is_tmf,
				struct mvs_tmf_task *tmf)
{
	struct mvs_info *mvi = NULL;
	u32 rc = 0;
	u32 pass = 0;
	unsigned long flags = 0;

	mvi = ((struct mvs_device *)task->dev->lldd_dev)->mvi_info;

	spin_lock_irqsave(&mvi->lock, flags);
	rc = mvs_task_prep(task, mvi, is_tmf, tmf, &pass);
	if (rc)
		dev_printk(KERN_ERR, mvi->dev, "mvsas exec failed[%d]!\n", rc);

	if (likely(pass))
			MVS_CHIP_DISP->start_delivery(mvi, (mvi->tx_prod - 1) &
				(MVS_CHIP_SLOT_SZ - 1));
	spin_unlock_irqrestore(&mvi->lock, flags);

	return rc;
}

static int mvs_collector_task_exec(struct sas_task *task, const int num, gfp_t gfp_flags,
				struct completion *completion, int is_tmf,
				struct mvs_tmf_task *tmf)
{
	struct domain_device *dev = task->dev;
	struct mvs_prv_info *mpi = dev->port->ha->lldd_ha;
	struct mvs_info *mvi = NULL;
	struct sas_task *t = task;
	struct mvs_task_list *mvs_list = NULL, *a;
	LIST_HEAD(q);
	int pass[2] = {0};
	u32 rc = 0;
	u32 n = num;
	unsigned long flags = 0;

	mvs_list = mvs_task_alloc_list(&n, gfp_flags);
	if (n) {
		printk(KERN_ERR "%s: mvs alloc list failed.\n", __func__);
		rc = -ENOMEM;
		goto free_list;
	}

	__list_add(&q, mvs_list->list.prev, &mvs_list->list);

	list_for_each_entry(a, &q, list) {
		a->task = t;
		t = list_entry(t->list.next, struct sas_task, list);
	}

	list_for_each_entry(a, &q , list) {

		t = a->task;
		mvi = ((struct mvs_device *)t->dev->lldd_dev)->mvi_info;

		spin_lock_irqsave(&mvi->lock, flags);
		rc = mvs_task_prep(t, mvi, is_tmf, tmf, &pass[mvi->id]);
		if (rc)
			dev_printk(KERN_ERR, mvi->dev, "mvsas exec failed[%d]!\n", rc);
		spin_unlock_irqrestore(&mvi->lock, flags);
	}

	if (likely(pass[0]))
			MVS_CHIP_DISP->start_delivery(mpi->mvi[0],
				(mpi->mvi[0]->tx_prod - 1) & (MVS_CHIP_SLOT_SZ - 1));

	if (likely(pass[1]))
			MVS_CHIP_DISP->start_delivery(mpi->mvi[1],
				(mpi->mvi[1]->tx_prod - 1) & (MVS_CHIP_SLOT_SZ - 1));

	list_del_init(&q);

free_list:
	if (mvs_list)
		mvs_task_free_list(mvs_list);

	return rc;
}

int mvs_queue_command(struct sas_task *task, const int num,
			gfp_t gfp_flags)
{
	struct mvs_device *mvi_dev = task->dev->lldd_dev;
	struct sas_ha_struct *sas = mvi_dev->mvi_info->sas;

	if (sas->lldd_max_execute_num < 2)
		return mvs_task_exec(task, num, gfp_flags, NULL, 0, NULL);
	else
		return mvs_collector_task_exec(task, num, gfp_flags, NULL, 0, NULL);
}

static void mvs_slot_free(struct mvs_info *mvi, u32 rx_desc)
{
	u32 slot_idx = rx_desc & RXQ_SLOT_MASK;
	mvs_tag_clear(mvi, slot_idx);
}

static void mvs_slot_task_free(struct mvs_info *mvi, struct sas_task *task,
			  struct mvs_slot_info *slot, u32 slot_idx)
{
	if (!slot)
		return;
	if (!slot->task)
		return;
	if (!sas_protocol_ata(task->task_proto))
		if (slot->n_elem)
			dma_unmap_sg(mvi->dev, task->scatter,
				     slot->n_elem, task->data_dir);

	switch (task->task_proto) {
	case SAS_PROTOCOL_SMP:
		dma_unmap_sg(mvi->dev, &task->smp_task.smp_resp, 1,
			     PCI_DMA_FROMDEVICE);
		dma_unmap_sg(mvi->dev, &task->smp_task.smp_req, 1,
			     PCI_DMA_TODEVICE);
		break;

	case SAS_PROTOCOL_SATA:
	case SAS_PROTOCOL_STP:
	case SAS_PROTOCOL_SSP:
	default:
		/* do nothing */
		break;
	}

	if (slot->buf) {
		pci_pool_free(mvi->dma_pool, slot->buf, slot->buf_dma);
		slot->buf = NULL;
	}
	list_del_init(&slot->entry);
	task->lldd_task = NULL;
	slot->task = NULL;
	slot->port = NULL;
	slot->slot_tag = 0xFFFFFFFF;
	mvs_slot_free(mvi, slot_idx);
}

static void mvs_update_wideport(struct mvs_info *mvi, int phy_no)
{
	struct mvs_phy *phy = &mvi->phy[phy_no];
	struct mvs_port *port = phy->port;
	int j, no;

	for_each_phy(port->wide_port_phymap, j, no) {
		if (j & 1) {
			MVS_CHIP_DISP->write_port_cfg_addr(mvi, no,
						PHYR_WIDE_PORT);
			MVS_CHIP_DISP->write_port_cfg_data(mvi, no,
						port->wide_port_phymap);
		} else {
			MVS_CHIP_DISP->write_port_cfg_addr(mvi, no,
						PHYR_WIDE_PORT);
			MVS_CHIP_DISP->write_port_cfg_data(mvi, no,
						0);
		}
	}
}

static u32 mvs_is_phy_ready(struct mvs_info *mvi, int i)
{
	u32 tmp;
	struct mvs_phy *phy = &mvi->phy[i];
	struct mvs_port *port = phy->port;

	tmp = MVS_CHIP_DISP->read_phy_ctl(mvi, i);
	if ((tmp & PHY_READY_MASK) && !(phy->irq_status & PHYEV_POOF)) {
		if (!port)
			phy->phy_attached = 1;
		return tmp;
	}

	if (port) {
		if (phy->phy_type & PORT_TYPE_SAS) {
			port->wide_port_phymap &= ~(1U << i);
			if (!port->wide_port_phymap)
				port->port_attached = 0;
			mvs_update_wideport(mvi, i);
		} else if (phy->phy_type & PORT_TYPE_SATA)
			port->port_attached = 0;
		phy->port = NULL;
		phy->phy_attached = 0;
		phy->phy_type &= ~(PORT_TYPE_SAS | PORT_TYPE_SATA);
	}
	return 0;
}

static void *mvs_get_d2h_reg(struct mvs_info *mvi, int i, void *buf)
{
	u32 *s = (u32 *) buf;

	if (!s)
		return NULL;

	MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_SATA_SIG3);
	s[3] = cpu_to_le32(MVS_CHIP_DISP->read_port_cfg_data(mvi, i));

	MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_SATA_SIG2);
	s[2] = cpu_to_le32(MVS_CHIP_DISP->read_port_cfg_data(mvi, i));

	MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_SATA_SIG1);
	s[1] = cpu_to_le32(MVS_CHIP_DISP->read_port_cfg_data(mvi, i));

	MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_SATA_SIG0);
	s[0] = cpu_to_le32(MVS_CHIP_DISP->read_port_cfg_data(mvi, i));

	if (((s[1] & 0x00FFFFFF) == 0x00EB1401) && (*(u8 *)&s[3] == 0x01))
		s[1] = 0x00EB1401 | (*((u8 *)&s[1] + 3) & 0x10);

	return s;
}

static u32 mvs_is_sig_fis_received(u32 irq_status)
{
	return irq_status & PHYEV_SIG_FIS;
}

static void mvs_sig_remove_timer(struct mvs_phy *phy)
{
	if (phy->timer.function)
		del_timer(&phy->timer);
	phy->timer.function = NULL;
}

void mvs_update_phyinfo(struct mvs_info *mvi, int i, int get_st)
{
	struct mvs_phy *phy = &mvi->phy[i];
	struct sas_identify_frame *id;

	id = (struct sas_identify_frame *)phy->frame_rcvd;

	if (get_st) {
		phy->irq_status = MVS_CHIP_DISP->read_port_irq_stat(mvi, i);
		phy->phy_status = mvs_is_phy_ready(mvi, i);
	}

	if (phy->phy_status) {
		int oob_done = 0;
		struct asd_sas_phy *sas_phy = &mvi->phy[i].sas_phy;

		oob_done = MVS_CHIP_DISP->oob_done(mvi, i);

		MVS_CHIP_DISP->fix_phy_info(mvi, i, id);
		if (phy->phy_type & PORT_TYPE_SATA) {
			phy->identify.target_port_protocols = SAS_PROTOCOL_STP;
			if (mvs_is_sig_fis_received(phy->irq_status)) {
				mvs_sig_remove_timer(phy);
				phy->phy_attached = 1;
				phy->att_dev_sas_addr =
					i + mvi->id * mvi->chip->n_phy;
				if (oob_done)
					sas_phy->oob_mode = SATA_OOB_MODE;
				phy->frame_rcvd_size =
				    sizeof(struct dev_to_host_fis);
				mvs_get_d2h_reg(mvi, i, id);
			} else {
				u32 tmp;
				dev_printk(KERN_DEBUG, mvi->dev,
					"Phy%d : No sig fis\n", i);
				tmp = MVS_CHIP_DISP->read_port_irq_mask(mvi, i);
				MVS_CHIP_DISP->write_port_irq_mask(mvi, i,
						tmp | PHYEV_SIG_FIS);
				phy->phy_attached = 0;
				phy->phy_type &= ~PORT_TYPE_SATA;
				goto out_done;
			}
		}	else if (phy->phy_type & PORT_TYPE_SAS
			|| phy->att_dev_info & PORT_SSP_INIT_MASK) {
			phy->phy_attached = 1;
			phy->identify.device_type =
				phy->att_dev_info & PORT_DEV_TYPE_MASK;

			if (phy->identify.device_type == SAS_END_DEVICE)
				phy->identify.target_port_protocols =
							SAS_PROTOCOL_SSP;
			else if (phy->identify.device_type != SAS_PHY_UNUSED)
				phy->identify.target_port_protocols =
							SAS_PROTOCOL_SMP;
			if (oob_done)
				sas_phy->oob_mode = SAS_OOB_MODE;
			phy->frame_rcvd_size =
			    sizeof(struct sas_identify_frame);
		}
		memcpy(sas_phy->attached_sas_addr,
			&phy->att_dev_sas_addr, SAS_ADDR_SIZE);

		if (MVS_CHIP_DISP->phy_work_around)
			MVS_CHIP_DISP->phy_work_around(mvi, i);
	}
	mv_dprintk("phy %d attach dev info is %x\n",
		i + mvi->id * mvi->chip->n_phy, phy->att_dev_info);
	mv_dprintk("phy %d attach sas addr is %llx\n",
		i + mvi->id * mvi->chip->n_phy, phy->att_dev_sas_addr);
out_done:
	if (get_st)
		MVS_CHIP_DISP->write_port_irq_stat(mvi, i, phy->irq_status);
}

static void mvs_port_notify_formed(struct asd_sas_phy *sas_phy, int lock)
{
	struct sas_ha_struct *sas_ha = sas_phy->ha;
	struct mvs_info *mvi = NULL; int i = 0, hi;
	struct mvs_phy *phy = sas_phy->lldd_phy;
	struct asd_sas_port *sas_port = sas_phy->port;
	struct mvs_port *port;
	unsigned long flags = 0;
	if (!sas_port)
		return;

	while (sas_ha->sas_phy[i]) {
		if (sas_ha->sas_phy[i] == sas_phy)
			break;
		i++;
	}
	hi = i/((struct mvs_prv_info *)sas_ha->lldd_ha)->n_phy;
	mvi = ((struct mvs_prv_info *)sas_ha->lldd_ha)->mvi[hi];
	if (i >= mvi->chip->n_phy)
		port = &mvi->port[i - mvi->chip->n_phy];
	else
		port = &mvi->port[i];
	if (lock)
		spin_lock_irqsave(&mvi->lock, flags);
	port->port_attached = 1;
	phy->port = port;
	sas_port->lldd_port = port;
	if (phy->phy_type & PORT_TYPE_SAS) {
		port->wide_port_phymap = sas_port->phy_mask;
		mv_printk("set wide port phy map %x\n", sas_port->phy_mask);
		mvs_update_wideport(mvi, sas_phy->id);

		/* direct attached SAS device */
		if (phy->att_dev_info & PORT_SSP_TRGT_MASK) {
			MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_PHY_STAT);
			MVS_CHIP_DISP->write_port_cfg_data(mvi, i, 0x04);
		}
	}
	if (lock)
		spin_unlock_irqrestore(&mvi->lock, flags);
}

static void mvs_port_notify_deformed(struct asd_sas_phy *sas_phy, int lock)
{
	struct domain_device *dev;
	struct mvs_phy *phy = sas_phy->lldd_phy;
	struct mvs_info *mvi = phy->mvi;
	struct asd_sas_port *port = sas_phy->port;
	int phy_no = 0;

	while (phy != &mvi->phy[phy_no]) {
		phy_no++;
		if (phy_no >= MVS_MAX_PHYS)
			return;
	}
	list_for_each_entry(dev, &port->dev_list, dev_list_node)
		mvs_do_release_task(phy->mvi, phy_no, dev);

}


void mvs_port_formed(struct asd_sas_phy *sas_phy)
{
	mvs_port_notify_formed(sas_phy, 1);
}

void mvs_port_deformed(struct asd_sas_phy *sas_phy)
{
	mvs_port_notify_deformed(sas_phy, 1);
}

struct mvs_device *mvs_alloc_dev(struct mvs_info *mvi)
{
	u32 dev;
	for (dev = 0; dev < MVS_MAX_DEVICES; dev++) {
		if (mvi->devices[dev].dev_type == SAS_PHY_UNUSED) {
			mvi->devices[dev].device_id = dev;
			return &mvi->devices[dev];
		}
	}

	if (dev == MVS_MAX_DEVICES)
		mv_printk("max support %d devices, ignore ..\n",
			MVS_MAX_DEVICES);

	return NULL;
}

void mvs_free_dev(struct mvs_device *mvi_dev)
{
	u32 id = mvi_dev->device_id;
	memset(mvi_dev, 0, sizeof(*mvi_dev));
	mvi_dev->device_id = id;
	mvi_dev->dev_type = SAS_PHY_UNUSED;
	mvi_dev->dev_status = MVS_DEV_NORMAL;
	mvi_dev->taskfileset = MVS_ID_NOT_MAPPED;
}

int mvs_dev_found_notify(struct domain_device *dev, int lock)
{
	unsigned long flags = 0;
	int res = 0;
	struct mvs_info *mvi = NULL;
	struct domain_device *parent_dev = dev->parent;
	struct mvs_device *mvi_device;

	mvi = mvs_find_dev_mvi(dev);

	if (lock)
		spin_lock_irqsave(&mvi->lock, flags);

	mvi_device = mvs_alloc_dev(mvi);
	if (!mvi_device) {
		res = -1;
		goto found_out;
	}
	dev->lldd_dev = mvi_device;
	mvi_device->dev_status = MVS_DEV_NORMAL;
	mvi_device->dev_type = dev->dev_type;
	mvi_device->mvi_info = mvi;
	mvi_device->sas_device = dev;
	if (parent_dev && DEV_IS_EXPANDER(parent_dev->dev_type)) {
		int phy_id;
		u8 phy_num = parent_dev->ex_dev.num_phys;
		struct ex_phy *phy;
		for (phy_id = 0; phy_id < phy_num; phy_id++) {
			phy = &parent_dev->ex_dev.ex_phy[phy_id];
			if (SAS_ADDR(phy->attached_sas_addr) ==
				SAS_ADDR(dev->sas_addr)) {
				mvi_device->attached_phy = phy_id;
				break;
			}
		}

		if (phy_id == phy_num) {
			mv_printk("Error: no attached dev:%016llx"
				"at ex:%016llx.\n",
				SAS_ADDR(dev->sas_addr),
				SAS_ADDR(parent_dev->sas_addr));
			res = -1;
		}
	}

found_out:
	if (lock)
		spin_unlock_irqrestore(&mvi->lock, flags);
	return res;
}

int mvs_dev_found(struct domain_device *dev)
{
	return mvs_dev_found_notify(dev, 1);
}

void mvs_dev_gone_notify(struct domain_device *dev)
{
	unsigned long flags = 0;
	struct mvs_device *mvi_dev = dev->lldd_dev;
	struct mvs_info *mvi = mvi_dev->mvi_info;

	spin_lock_irqsave(&mvi->lock, flags);

	if (mvi_dev) {
		mv_dprintk("found dev[%d:%x] is gone.\n",
			mvi_dev->device_id, mvi_dev->dev_type);
		mvs_release_task(mvi, dev);
		mvs_free_reg_set(mvi, mvi_dev);
		mvs_free_dev(mvi_dev);
	} else {
		mv_dprintk("found dev has gone.\n");
	}
	dev->lldd_dev = NULL;
	mvi_dev->sas_device = NULL;

	spin_unlock_irqrestore(&mvi->lock, flags);
}


void mvs_dev_gone(struct domain_device *dev)
{
	mvs_dev_gone_notify(dev);
}

static void mvs_task_done(struct sas_task *task)
{
	if (!del_timer(&task->slow_task->timer))
		return;
	complete(&task->slow_task->completion);
}

static void mvs_tmf_timedout(unsigned long data)
{
	struct sas_task *task = (struct sas_task *)data;

	task->task_state_flags |= SAS_TASK_STATE_ABORTED;
	complete(&task->slow_task->completion);
}

#define MVS_TASK_TIMEOUT 20
static int mvs_exec_internal_tmf_task(struct domain_device *dev,
			void *parameter, u32 para_len, struct mvs_tmf_task *tmf)
{
	int res, retry;
	struct sas_task *task = NULL;

	for (retry = 0; retry < 3; retry++) {
		task = sas_alloc_slow_task(GFP_KERNEL);
		if (!task)
			return -ENOMEM;

		task->dev = dev;
		task->task_proto = dev->tproto;

		memcpy(&task->ssp_task, parameter, para_len);
		task->task_done = mvs_task_done;

		task->slow_task->timer.data = (unsigned long) task;
		task->slow_task->timer.function = mvs_tmf_timedout;
		task->slow_task->timer.expires = jiffies + MVS_TASK_TIMEOUT*HZ;
		add_timer(&task->slow_task->timer);

		res = mvs_task_exec(task, 1, GFP_KERNEL, NULL, 1, tmf);

		if (res) {
			del_timer(&task->slow_task->timer);
			mv_printk("executing internel task failed:%d\n", res);
			goto ex_err;
		}

		wait_for_completion(&task->slow_task->completion);
		res = TMF_RESP_FUNC_FAILED;
		/* Even TMF timed out, return direct. */
		if ((task->task_state_flags & SAS_TASK_STATE_ABORTED)) {
			if (!(task->task_state_flags & SAS_TASK_STATE_DONE)) {
				mv_printk("TMF task[%x] timeout.\n", tmf->tmf);
				goto ex_err;
			}
		}

		if (task->task_status.resp == SAS_TASK_COMPLETE &&
		    task->task_status.stat == SAM_STAT_GOOD) {
			res = TMF_RESP_FUNC_COMPLETE;
			break;
		}

		if (task->task_status.resp == SAS_TASK_COMPLETE &&
		      task->task_status.stat == SAS_DATA_UNDERRUN) {
			/* no error, but return the number of bytes of
			 * underrun */
			res = task->task_status.residual;
			break;
		}

		if (task->task_status.resp == SAS_TASK_COMPLETE &&
		      task->task_status.stat == SAS_DATA_OVERRUN) {
			mv_dprintk("blocked task error.\n");
			res = -EMSGSIZE;
			break;
		} else {
			mv_dprintk(" task to dev %016llx response: 0x%x "
				    "status 0x%x\n",
				    SAS_ADDR(dev->sas_addr),
				    task->task_status.resp,
				    task->task_status.stat);
			sas_free_task(task);
			task = NULL;

		}
	}
ex_err:
	BUG_ON(retry == 3 && task != NULL);
	sas_free_task(task);
	return res;
}

static int mvs_debug_issue_ssp_tmf(struct domain_device *dev,
				u8 *lun, struct mvs_tmf_task *tmf)
{
	struct sas_ssp_task ssp_task;
	if (!(dev->tproto & SAS_PROTOCOL_SSP))
		return TMF_RESP_FUNC_ESUPP;

	memcpy(ssp_task.LUN, lun, 8);

	return mvs_exec_internal_tmf_task(dev, &ssp_task,
				sizeof(ssp_task), tmf);
}


/*  Standard mandates link reset for ATA  (type 0)
    and hard reset for SSP (type 1) , only for RECOVERY */
static int mvs_debug_I_T_nexus_reset(struct domain_device *dev)
{
	int rc;
	struct sas_phy *phy = sas_get_local_phy(dev);
	int reset_type = (dev->dev_type == SAS_SATA_DEV ||
			(dev->tproto & SAS_PROTOCOL_STP)) ? 0 : 1;
	rc = sas_phy_reset(phy, reset_type);
	sas_put_local_phy(phy);
	msleep(2000);
	return rc;
}

/* mandatory SAM-3 */
int mvs_lu_reset(struct domain_device *dev, u8 *lun)
{
	unsigned long flags;
	int rc = TMF_RESP_FUNC_FAILED;
	struct mvs_tmf_task tmf_task;
	struct mvs_device * mvi_dev = dev->lldd_dev;
	struct mvs_info *mvi = mvi_dev->mvi_info;

	tmf_task.tmf = TMF_LU_RESET;
	mvi_dev->dev_status = MVS_DEV_EH;
	rc = mvs_debug_issue_ssp_tmf(dev, lun, &tmf_task);
	if (rc == TMF_RESP_FUNC_COMPLETE) {
		spin_lock_irqsave(&mvi->lock, flags);
		mvs_release_task(mvi, dev);
		spin_unlock_irqrestore(&mvi->lock, flags);
	}
	/* If failed, fall-through I_T_Nexus reset */
	mv_printk("%s for device[%x]:rc= %d\n", __func__,
			mvi_dev->device_id, rc);
	return rc;
}

int mvs_I_T_nexus_reset(struct domain_device *dev)
{
	unsigned long flags;
	int rc = TMF_RESP_FUNC_FAILED;
    struct mvs_device * mvi_dev = (struct mvs_device *)dev->lldd_dev;
	struct mvs_info *mvi = mvi_dev->mvi_info;

	if (mvi_dev->dev_status != MVS_DEV_EH)
		return TMF_RESP_FUNC_COMPLETE;
	else
		mvi_dev->dev_status = MVS_DEV_NORMAL;
	rc = mvs_debug_I_T_nexus_reset(dev);
	mv_printk("%s for device[%x]:rc= %d\n",
		__func__, mvi_dev->device_id, rc);

	spin_lock_irqsave(&mvi->lock, flags);
	mvs_release_task(mvi, dev);
	spin_unlock_irqrestore(&mvi->lock, flags);

	return rc;
}
/* optional SAM-3 */
int mvs_query_task(struct sas_task *task)
{
	u32 tag;
	struct scsi_lun lun;
	struct mvs_tmf_task tmf_task;
	int rc = TMF_RESP_FUNC_FAILED;

	if (task->lldd_task && task->task_proto & SAS_PROTOCOL_SSP) {
		struct scsi_cmnd * cmnd = (struct scsi_cmnd *)task->uldd_task;
		struct domain_device *dev = task->dev;
		struct mvs_device *mvi_dev = (struct mvs_device *)dev->lldd_dev;
		struct mvs_info *mvi = mvi_dev->mvi_info;

		int_to_scsilun(cmnd->device->lun, &lun);
		rc = mvs_find_tag(mvi, task, &tag);
		if (rc == 0) {
			rc = TMF_RESP_FUNC_FAILED;
			return rc;
		}

		tmf_task.tmf = TMF_QUERY_TASK;
		tmf_task.tag_of_task_to_be_managed = cpu_to_le16(tag);

		rc = mvs_debug_issue_ssp_tmf(dev, lun.scsi_lun, &tmf_task);
		switch (rc) {
		/* The task is still in Lun, release it then */
		case TMF_RESP_FUNC_SUCC:
		/* The task is not in Lun or failed, reset the phy */
		case TMF_RESP_FUNC_FAILED:
		case TMF_RESP_FUNC_COMPLETE:
			break;
		}
	}
	mv_printk("%s:rc= %d\n", __func__, rc);
	return rc;
}

/*  mandatory SAM-3, still need free task/slot info */
int mvs_abort_task(struct sas_task *task)
{
	struct scsi_lun lun;
	struct mvs_tmf_task tmf_task;
	struct domain_device *dev = task->dev;
	struct mvs_device *mvi_dev = (struct mvs_device *)dev->lldd_dev;
	struct mvs_info *mvi;
	int rc = TMF_RESP_FUNC_FAILED;
	unsigned long flags;
	u32 tag;

	if (!mvi_dev) {
		mv_printk("Device has removed\n");
		return TMF_RESP_FUNC_FAILED;
	}

	mvi = mvi_dev->mvi_info;

	spin_lock_irqsave(&task->task_state_lock, flags);
	if (task->task_state_flags & SAS_TASK_STATE_DONE) {
		spin_unlock_irqrestore(&task->task_state_lock, flags);
		rc = TMF_RESP_FUNC_COMPLETE;
		goto out;
	}
	spin_unlock_irqrestore(&task->task_state_lock, flags);
	mvi_dev->dev_status = MVS_DEV_EH;
	if (task->lldd_task && task->task_proto & SAS_PROTOCOL_SSP) {
		struct scsi_cmnd * cmnd = (struct scsi_cmnd *)task->uldd_task;

		int_to_scsilun(cmnd->device->lun, &lun);
		rc = mvs_find_tag(mvi, task, &tag);
		if (rc == 0) {
			mv_printk("No such tag in %s\n", __func__);
			rc = TMF_RESP_FUNC_FAILED;
			return rc;
		}

		tmf_task.tmf = TMF_ABORT_TASK;
		tmf_task.tag_of_task_to_be_managed = cpu_to_le16(tag);

		rc = mvs_debug_issue_ssp_tmf(dev, lun.scsi_lun, &tmf_task);

		/* if successful, clear the task and callback forwards.*/
		if (rc == TMF_RESP_FUNC_COMPLETE) {
			u32 slot_no;
			struct mvs_slot_info *slot;

			if (task->lldd_task) {
				slot = task->lldd_task;
				slot_no = (u32) (slot - mvi->slot_info);
				spin_lock_irqsave(&mvi->lock, flags);
				mvs_slot_complete(mvi, slot_no, 1);
				spin_unlock_irqrestore(&mvi->lock, flags);
			}
		}

	} else if (task->task_proto & SAS_PROTOCOL_SATA ||
		task->task_proto & SAS_PROTOCOL_STP) {
		if (SAS_SATA_DEV == dev->dev_type) {
			struct mvs_slot_info *slot = task->lldd_task;
			u32 slot_idx = (u32)(slot - mvi->slot_info);
			mv_dprintk("mvs_abort_task() mvi=%p task=%p "
				   "slot=%p slot_idx=x%x\n",
				   mvi, task, slot, slot_idx);
			task->task_state_flags |= SAS_TASK_STATE_ABORTED;
			mvs_slot_task_free(mvi, task, slot, slot_idx);
			rc = TMF_RESP_FUNC_COMPLETE;
			goto out;
		}

	}
out:
	if (rc != TMF_RESP_FUNC_COMPLETE)
		mv_printk("%s:rc= %d\n", __func__, rc);
	return rc;
}

int mvs_abort_task_set(struct domain_device *dev, u8 *lun)
{
	int rc = TMF_RESP_FUNC_FAILED;
	struct mvs_tmf_task tmf_task;

	tmf_task.tmf = TMF_ABORT_TASK_SET;
	rc = mvs_debug_issue_ssp_tmf(dev, lun, &tmf_task);

	return rc;
}

int mvs_clear_aca(struct domain_device *dev, u8 *lun)
{
	int rc = TMF_RESP_FUNC_FAILED;
	struct mvs_tmf_task tmf_task;

	tmf_task.tmf = TMF_CLEAR_ACA;
	rc = mvs_debug_issue_ssp_tmf(dev, lun, &tmf_task);

	return rc;
}

int mvs_clear_task_set(struct domain_device *dev, u8 *lun)
{
	int rc = TMF_RESP_FUNC_FAILED;
	struct mvs_tmf_task tmf_task;

	tmf_task.tmf = TMF_CLEAR_TASK_SET;
	rc = mvs_debug_issue_ssp_tmf(dev, lun, &tmf_task);

	return rc;
}

static int mvs_sata_done(struct mvs_info *mvi, struct sas_task *task,
			u32 slot_idx, int err)
{
	struct mvs_device *mvi_dev = task->dev->lldd_dev;
	struct task_status_struct *tstat = &task->task_status;
	struct ata_task_resp *resp = (struct ata_task_resp *)tstat->buf;
	int stat = SAM_STAT_GOOD;


	resp->frame_len = sizeof(struct dev_to_host_fis);
	memcpy(&resp->ending_fis[0],
	       SATA_RECEIVED_D2H_FIS(mvi_dev->taskfileset),
	       sizeof(struct dev_to_host_fis));
	tstat->buf_valid_size = sizeof(*resp);
	if (unlikely(err)) {
		if (unlikely(err & CMD_ISS_STPD))
			stat = SAS_OPEN_REJECT;
		else
			stat = SAS_PROTO_RESPONSE;
       }

	return stat;
}

void mvs_set_sense(u8 *buffer, int len, int d_sense,
		int key, int asc, int ascq)
{
	memset(buffer, 0, len);

	if (d_sense) {
		/* Descriptor format */
		if (len < 4) {
			mv_printk("Length %d of sense buffer too small to "
				"fit sense %x:%x:%x", len, key, asc, ascq);
		}

		buffer[0] = 0x72;		/* Response Code	*/
		if (len > 1)
			buffer[1] = key;	/* Sense Key */
		if (len > 2)
			buffer[2] = asc;	/* ASC	*/
		if (len > 3)
			buffer[3] = ascq;	/* ASCQ	*/
	} else {
		if (len < 14) {
			mv_printk("Length %d of sense buffer too small to "
				"fit sense %x:%x:%x", len, key, asc, ascq);
		}

		buffer[0] = 0x70;		/* Response Code	*/
		if (len > 2)
			buffer[2] = key;	/* Sense Key */
		if (len > 7)
			buffer[7] = 0x0a;	/* Additional Sense Length */
		if (len > 12)
			buffer[12] = asc;	/* ASC */
		if (len > 13)
			buffer[13] = ascq; /* ASCQ */
	}

	return;
}

void mvs_fill_ssp_resp_iu(struct ssp_response_iu *iu,
				u8 key, u8 asc, u8 asc_q)
{
	iu->datapres = 2;
	iu->response_data_len = 0;
	iu->sense_data_len = 17;
	iu->status = 02;
	mvs_set_sense(iu->sense_data, 17, 0,
			key, asc, asc_q);
}

static int mvs_slot_err(struct mvs_info *mvi, struct sas_task *task,
			 u32 slot_idx)
{
	struct mvs_slot_info *slot = &mvi->slot_info[slot_idx];
	int stat;
	u32 err_dw0 = le32_to_cpu(*(u32 *)slot->response);
	u32 err_dw1 = le32_to_cpu(*((u32 *)slot->response + 1));
	u32 tfs = 0;
	enum mvs_port_type type = PORT_TYPE_SAS;

	if (err_dw0 & CMD_ISS_STPD)
		MVS_CHIP_DISP->issue_stop(mvi, type, tfs);

	MVS_CHIP_DISP->command_active(mvi, slot_idx);

	stat = SAM_STAT_CHECK_CONDITION;
	switch (task->task_proto) {
	case SAS_PROTOCOL_SSP:
	{
		stat = SAS_ABORTED_TASK;
		if ((err_dw0 & NO_DEST) || err_dw1 & bit(31)) {
			struct ssp_response_iu *iu = slot->response +
				sizeof(struct mvs_err_info);
			mvs_fill_ssp_resp_iu(iu, NOT_READY, 0x04, 01);
			sas_ssp_task_response(mvi->dev, task, iu);
			stat = SAM_STAT_CHECK_CONDITION;
		}
		if (err_dw1 & bit(31))
			mv_printk("reuse same slot, retry command.\n");
		break;
	}
	case SAS_PROTOCOL_SMP:
		stat = SAM_STAT_CHECK_CONDITION;
		break;

	case SAS_PROTOCOL_SATA:
	case SAS_PROTOCOL_STP:
	case SAS_PROTOCOL_SATA | SAS_PROTOCOL_STP:
	{
		task->ata_task.use_ncq = 0;
		stat = SAS_PROTO_RESPONSE;
		mvs_sata_done(mvi, task, slot_idx, err_dw0);
	}
		break;
	default:
		break;
	}

	return stat;
}

int mvs_slot_complete(struct mvs_info *mvi, u32 rx_desc, u32 flags)
{
	u32 slot_idx = rx_desc & RXQ_SLOT_MASK;
	struct mvs_slot_info *slot = &mvi->slot_info[slot_idx];
	struct sas_task *task = slot->task;
	struct mvs_device *mvi_dev = NULL;
	struct task_status_struct *tstat;
	struct domain_device *dev;
	u32 aborted;

	void *to;
	enum exec_status sts;

	if (unlikely(!task || !task->lldd_task || !task->dev))
		return -1;

	tstat = &task->task_status;
	dev = task->dev;
	mvi_dev = dev->lldd_dev;

	spin_lock(&task->task_state_lock);
	task->task_state_flags &=
		~(SAS_TASK_STATE_PENDING | SAS_TASK_AT_INITIATOR);
	task->task_state_flags |= SAS_TASK_STATE_DONE;
	/* race condition*/
	aborted = task->task_state_flags & SAS_TASK_STATE_ABORTED;
	spin_unlock(&task->task_state_lock);

	memset(tstat, 0, sizeof(*tstat));
	tstat->resp = SAS_TASK_COMPLETE;

	if (unlikely(aborted)) {
		tstat->stat = SAS_ABORTED_TASK;
		if (mvi_dev && mvi_dev->running_req)
			mvi_dev->running_req--;
		if (sas_protocol_ata(task->task_proto))
			mvs_free_reg_set(mvi, mvi_dev);

		mvs_slot_task_free(mvi, task, slot, slot_idx);
		return -1;
	}

	/* when no device attaching, go ahead and complete by error handling*/
	if (unlikely(!mvi_dev || flags)) {
		if (!mvi_dev)
			mv_dprintk("port has not device.\n");
		tstat->stat = SAS_PHY_DOWN;
		goto out;
	}

	/* error info record present */
	if (unlikely((rx_desc & RXQ_ERR) && (*(u64 *) slot->response))) {
		mv_dprintk("port %d slot %d rx_desc %X has error info"
			"%016llX.\n", slot->port->sas_port.id, slot_idx,
			 rx_desc, (u64)(*(u64 *)slot->response));
		tstat->stat = mvs_slot_err(mvi, task, slot_idx);
		tstat->resp = SAS_TASK_COMPLETE;
		goto out;
	}

	switch (task->task_proto) {
	case SAS_PROTOCOL_SSP:
		/* hw says status == 0, datapres == 0 */
		if (rx_desc & RXQ_GOOD) {
			tstat->stat = SAM_STAT_GOOD;
			tstat->resp = SAS_TASK_COMPLETE;
		}
		/* response frame present */
		else if (rx_desc & RXQ_RSP) {
			struct ssp_response_iu *iu = slot->response +
						sizeof(struct mvs_err_info);
			sas_ssp_task_response(mvi->dev, task, iu);
		} else
			tstat->stat = SAM_STAT_CHECK_CONDITION;
		break;

	case SAS_PROTOCOL_SMP: {
			struct scatterlist *sg_resp = &task->smp_task.smp_resp;
			tstat->stat = SAM_STAT_GOOD;
			to = kmap_atomic(sg_page(sg_resp));
			memcpy(to + sg_resp->offset,
				slot->response + sizeof(struct mvs_err_info),
				sg_dma_len(sg_resp));
			kunmap_atomic(to);
			break;
		}

	case SAS_PROTOCOL_SATA:
	case SAS_PROTOCOL_STP:
	case SAS_PROTOCOL_SATA | SAS_PROTOCOL_STP: {
			tstat->stat = mvs_sata_done(mvi, task, slot_idx, 0);
			break;
		}

	default:
		tstat->stat = SAM_STAT_CHECK_CONDITION;
		break;
	}
	if (!slot->port->port_attached) {
		mv_dprintk("port %d has removed.\n", slot->port->sas_port.id);
		tstat->stat = SAS_PHY_DOWN;
	}


out:
	if (mvi_dev && mvi_dev->running_req) {
		mvi_dev->running_req--;
		if (sas_protocol_ata(task->task_proto) && !mvi_dev->running_req)
			mvs_free_reg_set(mvi, mvi_dev);
	}
	mvs_slot_task_free(mvi, task, slot, slot_idx);
	sts = tstat->stat;

	spin_unlock(&mvi->lock);
	if (task->task_done)
		task->task_done(task);

	spin_lock(&mvi->lock);

	return sts;
}

void mvs_do_release_task(struct mvs_info *mvi,
		int phy_no, struct domain_device *dev)
{
	u32 slot_idx;
	struct mvs_phy *phy;
	struct mvs_port *port;
	struct mvs_slot_info *slot, *slot2;

	phy = &mvi->phy[phy_no];
	port = phy->port;
	if (!port)
		return;
	/* clean cmpl queue in case request is already finished */
	mvs_int_rx(mvi, false);



	list_for_each_entry_safe(slot, slot2, &port->list, entry) {
		struct sas_task *task;
		slot_idx = (u32) (slot - mvi->slot_info);
		task = slot->task;

		if (dev && task->dev != dev)
			continue;

		mv_printk("Release slot [%x] tag[%x], task [%p]:\n",
			slot_idx, slot->slot_tag, task);
		MVS_CHIP_DISP->command_active(mvi, slot_idx);

		mvs_slot_complete(mvi, slot_idx, 1);
	}
}

void mvs_release_task(struct mvs_info *mvi,
		      struct domain_device *dev)
{
	int i, phyno[WIDE_PORT_MAX_PHY], num;
	num = mvs_find_dev_phyno(dev, phyno);
	for (i = 0; i < num; i++)
		mvs_do_release_task(mvi, phyno[i], dev);
}

static void mvs_phy_disconnected(struct mvs_phy *phy)
{
	phy->phy_attached = 0;
	phy->att_dev_info = 0;
	phy->att_dev_sas_addr = 0;
}

static void mvs_work_queue(struct work_struct *work)
{
	struct delayed_work *dw = container_of(work, struct delayed_work, work);
	struct mvs_wq *mwq = container_of(dw, struct mvs_wq, work_q);
	struct mvs_info *mvi = mwq->mvi;
	unsigned long flags;
	u32 phy_no = (unsigned long) mwq->data;
	struct sas_ha_struct *sas_ha = mvi->sas;
	struct mvs_phy *phy = &mvi->phy[phy_no];
	struct asd_sas_phy *sas_phy = &phy->sas_phy;

	spin_lock_irqsave(&mvi->lock, flags);
	if (mwq->handler & PHY_PLUG_EVENT) {

		if (phy->phy_event & PHY_PLUG_OUT) {
			u32 tmp;
			struct sas_identify_frame *id;
			id = (struct sas_identify_frame *)phy->frame_rcvd;
			tmp = MVS_CHIP_DISP->read_phy_ctl(mvi, phy_no);
			phy->phy_event &= ~PHY_PLUG_OUT;
			if (!(tmp & PHY_READY_MASK)) {
				sas_phy_disconnected(sas_phy);
				mvs_phy_disconnected(phy);
				sas_ha->notify_phy_event(sas_phy,
					PHYE_LOSS_OF_SIGNAL);
				mv_dprintk("phy%d Removed Device\n", phy_no);
			} else {
				MVS_CHIP_DISP->detect_porttype(mvi, phy_no);
				mvs_update_phyinfo(mvi, phy_no, 1);
				mvs_bytes_dmaed(mvi, phy_no);
				mvs_port_notify_formed(sas_phy, 0);
				mv_dprintk("phy%d Attached Device\n", phy_no);
			}
		}
	} else if (mwq->handler & EXP_BRCT_CHG) {
		phy->phy_event &= ~EXP_BRCT_CHG;
		sas_ha->notify_port_event(sas_phy,
				PORTE_BROADCAST_RCVD);
		mv_dprintk("phy%d Got Broadcast Change\n", phy_no);
	}
	list_del(&mwq->entry);
	spin_unlock_irqrestore(&mvi->lock, flags);
	kfree(mwq);
}

static int mvs_handle_event(struct mvs_info *mvi, void *data, int handler)
{
	struct mvs_wq *mwq;
	int ret = 0;

	mwq = kmalloc(sizeof(struct mvs_wq), GFP_ATOMIC);
	if (mwq) {
		mwq->mvi = mvi;
		mwq->data = data;
		mwq->handler = handler;
		MV_INIT_DELAYED_WORK(&mwq->work_q, mvs_work_queue, mwq);
		list_add_tail(&mwq->entry, &mvi->wq_list);
		schedule_delayed_work(&mwq->work_q, HZ * 2);
	} else
		ret = -ENOMEM;

	return ret;
}

static void mvs_sig_time_out(unsigned long tphy)
{
	struct mvs_phy *phy = (struct mvs_phy *)tphy;
	struct mvs_info *mvi = phy->mvi;
	u8 phy_no;

	for (phy_no = 0; phy_no < mvi->chip->n_phy; phy_no++) {
		if (&mvi->phy[phy_no] == phy) {
			mv_dprintk("Get signature time out, reset phy %d\n",
				phy_no+mvi->id*mvi->chip->n_phy);
			MVS_CHIP_DISP->phy_reset(mvi, phy_no, MVS_HARD_RESET);
		}
	}
}

void mvs_int_port(struct mvs_info *mvi, int phy_no, u32 events)
{
	u32 tmp;
	struct mvs_phy *phy = &mvi->phy[phy_no];

	phy->irq_status = MVS_CHIP_DISP->read_port_irq_stat(mvi, phy_no);
	MVS_CHIP_DISP->write_port_irq_stat(mvi, phy_no, phy->irq_status);
	mv_dprintk("phy %d ctrl sts=0x%08X.\n", phy_no+mvi->id*mvi->chip->n_phy,
		MVS_CHIP_DISP->read_phy_ctl(mvi, phy_no));
	mv_dprintk("phy %d irq sts = 0x%08X\n", phy_no+mvi->id*mvi->chip->n_phy,
		phy->irq_status);

	/*
	* events is port event now ,
	* we need check the interrupt status which belongs to per port.
	*/

	if (phy->irq_status & PHYEV_DCDR_ERR) {
		mv_dprintk("phy %d STP decoding error.\n",
		phy_no + mvi->id*mvi->chip->n_phy);
	}

	if (phy->irq_status & PHYEV_POOF) {
		mdelay(500);
		if (!(phy->phy_event & PHY_PLUG_OUT)) {
			int dev_sata = phy->phy_type & PORT_TYPE_SATA;
			int ready;
			mvs_do_release_task(mvi, phy_no, NULL);
			phy->phy_event |= PHY_PLUG_OUT;
			MVS_CHIP_DISP->clear_srs_irq(mvi, 0, 1);
			mvs_handle_event(mvi,
				(void *)(unsigned long)phy_no,
				PHY_PLUG_EVENT);
			ready = mvs_is_phy_ready(mvi, phy_no);
			if (ready || dev_sata) {
				if (MVS_CHIP_DISP->stp_reset)
					MVS_CHIP_DISP->stp_reset(mvi,
							phy_no);
				else
					MVS_CHIP_DISP->phy_reset(mvi,
							phy_no, MVS_SOFT_RESET);
				return;
			}
		}
	}

	if (phy->irq_status & PHYEV_COMWAKE) {
		tmp = MVS_CHIP_DISP->read_port_irq_mask(mvi, phy_no);
		MVS_CHIP_DISP->write_port_irq_mask(mvi, phy_no,
					tmp | PHYEV_SIG_FIS);
		if (phy->timer.function == NULL) {
			phy->timer.data = (unsigned long)phy;
			phy->timer.function = mvs_sig_time_out;
			phy->timer.expires = jiffies + 5*HZ;
			add_timer(&phy->timer);
		}
	}
	if (phy->irq_status & (PHYEV_SIG_FIS | PHYEV_ID_DONE)) {
		phy->phy_status = mvs_is_phy_ready(mvi, phy_no);
		mv_dprintk("notify plug in on phy[%d]\n", phy_no);
		if (phy->phy_status) {
			mdelay(10);
			MVS_CHIP_DISP->detect_porttype(mvi, phy_no);
			if (phy->phy_type & PORT_TYPE_SATA) {
				tmp = MVS_CHIP_DISP->read_port_irq_mask(
						mvi, phy_no);
				tmp &= ~PHYEV_SIG_FIS;
				MVS_CHIP_DISP->write_port_irq_mask(mvi,
							phy_no, tmp);
			}
			mvs_update_phyinfo(mvi, phy_no, 0);
			if (phy->phy_type & PORT_TYPE_SAS) {
				MVS_CHIP_DISP->phy_reset(mvi, phy_no, MVS_PHY_TUNE);
				mdelay(10);
			}

			mvs_bytes_dmaed(mvi, phy_no);
			/* whether driver is going to handle hot plug */
			if (phy->phy_event & PHY_PLUG_OUT) {
				mvs_port_notify_formed(&phy->sas_phy, 0);
				phy->phy_event &= ~PHY_PLUG_OUT;
			}
		} else {
			mv_dprintk("plugin interrupt but phy%d is gone\n",
				phy_no + mvi->id*mvi->chip->n_phy);
		}
	} else if (phy->irq_status & PHYEV_BROAD_CH) {
		mv_dprintk("phy %d broadcast change.\n",
			phy_no + mvi->id*mvi->chip->n_phy);
		mvs_handle_event(mvi, (void *)(unsigned long)phy_no,
				EXP_BRCT_CHG);
	}
}

int mvs_int_rx(struct mvs_info *mvi, bool self_clear)
{
	u32 rx_prod_idx, rx_desc;
	bool attn = false;

	/* the first dword in the RX ring is special: it contains
	 * a mirror of the hardware's RX producer index, so that
	 * we don't have to stall the CPU reading that register.
	 * The actual RX ring is offset by one dword, due to this.
	 */
	rx_prod_idx = mvi->rx_cons;
	mvi->rx_cons = le32_to_cpu(mvi->rx[0]);
	if (mvi->rx_cons == 0xfff)	/* h/w hasn't touched RX ring yet */
		return 0;

	/* The CMPL_Q may come late, read from register and try again
	* note: if coalescing is enabled,
	* it will need to read from register every time for sure
	*/
	if (unlikely(mvi->rx_cons == rx_prod_idx))
		mvi->rx_cons = MVS_CHIP_DISP->rx_update(mvi) & RX_RING_SZ_MASK;

	if (mvi->rx_cons == rx_prod_idx)
		return 0;

	while (mvi->rx_cons != rx_prod_idx) {
		/* increment our internal RX consumer pointer */
		rx_prod_idx = (rx_prod_idx + 1) & (MVS_RX_RING_SZ - 1);
		rx_desc = le32_to_cpu(mvi->rx[rx_prod_idx + 1]);

		if (likely(rx_desc & RXQ_DONE))
			mvs_slot_complete(mvi, rx_desc, 0);
		if (rx_desc & RXQ_ATTN) {
			attn = true;
		} else if (rx_desc & RXQ_ERR) {
			if (!(rx_desc & RXQ_DONE))
				mvs_slot_complete(mvi, rx_desc, 0);
		} else if (rx_desc & RXQ_SLOT_RESET) {
			mvs_slot_free(mvi, rx_desc);
		}
	}

	if (attn && self_clear)
		MVS_CHIP_DISP->int_full(mvi);
	return 0;
}

