Exemplo n.º 1
0
/* ARGSUSED */
static void
emlxs_pkt_thread(emlxs_hba_t *hba, void *arg1, void *arg2)
{
	emlxs_port_t *port;
	fc_packet_t *pkt = (fc_packet_t *)arg1;
	int32_t rval;
	emlxs_buf_t *sbp;

	sbp = PKT2PRIV(pkt);
	port = sbp->port;

	/* Send the pkt now */
	rval = emlxs_pkt_send(pkt, 1);

	if (rval != FC_SUCCESS) {
		EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_pkt_trans_msg,
		    "Deferred emlxs_pkt_send failed: status=%x pkt=%p", rval,
		    pkt);

		if (pkt->pkt_comp) {
			emlxs_set_pkt_state(sbp, IOSTAT_LOCAL_REJECT, 0, 1);

			((CHANNEL *)sbp->channel)->ulpCmplCmd++;
			(*pkt->pkt_comp) (pkt);
		} else {
			emlxs_pkt_free(pkt);
		}
	}

	return;

} /* emlxs_pkt_thread() */
Exemplo n.º 2
0
/* Default pkt callback routine */
extern void
emlxs_pkt_callback(fc_packet_t *pkt)
{
	emlxs_pkt_free(pkt);

	return;

} /* emlxs_pkt_callback() */
Exemplo n.º 3
0
/*
 * Process a create_xri command completion.
 */
extern int32_t
emlxs_handle_create_xri(emlxs_hba_t *hba, CHANNEL *cp, IOCBQ *iocbq)
{
	emlxs_port_t *port = &PPORT;
	IOCB *cmd;
	NODELIST *ndlp;
	fc_packet_t *pkt;
	emlxs_buf_t *sbp;

	cmd = &iocbq->iocb;

	sbp = (emlxs_buf_t *)iocbq->sbp;

	if (!sbp) {
		EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_stray_ip_completion_msg,
		    "create_xri: cmd=0x%x iotag=0x%x status=0x%x w4=0x%x",
		    cmd->ULPCOMMAND, cmd->ULPIOTAG, cmd->ULPSTATUS,
		    cmd->un.ulpWord[4]);

		return (EIO);
	}

	/* check for first xmit completion in sequence */
	ndlp = (NODELIST *)sbp->node;

	if (cmd->ULPSTATUS) {
		EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_bad_ip_completion_msg,
		    "create_xri: cmd=0x%x iotag=0x%x status=0x%x w4=0x%x",
		    cmd->ULPCOMMAND, cmd->ULPIOTAG, cmd->ULPSTATUS,
		    cmd->un.ulpWord[4]);

		mutex_enter(&EMLXS_TX_CHANNEL_LOCK);
		ndlp->nlp_flag[cp->channelno] &= ~NLP_RPI_XRI;
		mutex_exit(&EMLXS_TX_CHANNEL_LOCK);

		return (EIO);
	}

	mutex_enter(&EMLXS_TX_CHANNEL_LOCK);
	ndlp->nlp_Xri = cmd->ULPCONTEXT;
	ndlp->nlp_flag[cp->channelno] &= ~NLP_RPI_XRI;
	mutex_exit(&EMLXS_TX_CHANNEL_LOCK);

	EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_ip_detail_msg,
	    "create_xri completed: DID=0x%x Xri=0x%x iotag=0x%x",
	    ndlp->nlp_DID, ndlp->nlp_Xri, cmd->ULPIOTAG);

	pkt = sbp->pkt;
	emlxs_pkt_free(pkt);

	return (0);

} /* emlxs_handle_create_xri()  */
Exemplo n.º 4
0
/*
 * Issue an iocb command to create an exchange with the remote Nport
 * specified by the NODELIST entry.
 */
extern int32_t
emlxs_create_xri(emlxs_port_t *port, CHANNEL *cp, NODELIST *ndlp)
{
	emlxs_hba_t *hba = HBA;
	IOCB *icmd;
	IOCBQ *iocbq;
	fc_packet_t *pkt;
	emlxs_buf_t *sbp;
	uint16_t iotag;

	/* Check if an XRI has already been requested */
	mutex_enter(&EMLXS_TX_CHANNEL_LOCK);
	if (ndlp->nlp_Xri != 0 ||
	    (ndlp->nlp_flag[cp->channelno] & NLP_RPI_XRI)) {
		mutex_exit(&EMLXS_TX_CHANNEL_LOCK);
		return (0);
	}
	ndlp->nlp_flag[cp->channelno] |= NLP_RPI_XRI;
	mutex_exit(&EMLXS_TX_CHANNEL_LOCK);

	if (!(pkt = emlxs_pkt_alloc(port, 0, 0, 0, KM_NOSLEEP))) {
		EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_ip_detail_msg,
		    "create_xri failed: Unable to allocate pkt. did=0x%x",
		    ndlp->nlp_DID);

		goto fail;
	}

	sbp = (emlxs_buf_t *)pkt->pkt_fca_private;
	iocbq = &sbp->iocbq;

	/* Clear the PACKET_ULP_OWNED flag */
	sbp->pkt_flags &= ~PACKET_ULP_OWNED;

	/* Get the iotag by registering the packet */
	iotag = emlxs_register_pkt(cp, sbp);

	if (!iotag) {
		/*
		 * No more command slots available, retry later
		 */
		emlxs_pkt_free(pkt);

		EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_ip_detail_msg,
		    "create_xri failed: Unable to allocate IOTAG. did=0x%x",
		    ndlp->nlp_DID);

		goto fail;
	}

	icmd = &iocbq->iocb;
	icmd->ULPIOTAG = iotag;
	icmd->ULPCONTEXT = ndlp->nlp_Rpi;
	icmd->ULPLE = 1;
	icmd->ULPCOMMAND = CMD_CREATE_XRI_CR;
	icmd->ULPOWNER = OWN_CHIP;

	/* Initalize iocbq */
	iocbq->port = (void *)port;
	iocbq->node = (void *)ndlp;
	iocbq->channel = (void *)cp;

	mutex_enter(&sbp->mtx);
	sbp->node = (void *)ndlp;
	sbp->channel = cp;
	mutex_exit(&sbp->mtx);

	EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_ip_detail_msg,
	    "create_xri sent: DID=0x%x Xri=0x%x iotag=0x%x", ndlp->nlp_DID,
	    ndlp->nlp_Xri, iotag);

	EMLXS_SLI_ISSUE_IOCB_CMD(hba, cp, iocbq);

	return (0);

fail:

	/* Clear the XRI flag */
	mutex_enter(&EMLXS_TX_CHANNEL_LOCK);
	ndlp->nlp_flag[cp->channelno] &= ~NLP_RPI_XRI;
	mutex_exit(&EMLXS_TX_CHANNEL_LOCK);

	return (1);

} /* emlxs_create_xri() */