static void csio_vport_set_state(struct csio_lnode *ln) { struct fc_vport *fc_vport = ln->fc_vport; struct csio_lnode *pln = ln->pln; char state[16]; /* Set fc vport state based on phyiscal lnode */ csio_lnode_state_to_str(pln, state); if (strcmp(state, "READY")) { fc_vport_set_state(fc_vport, FC_VPORT_LINKDOWN); return; } if (!(pln->flags & CSIO_LNF_NPIVSUPP)) { fc_vport_set_state(fc_vport, FC_VPORT_NO_FABRIC_SUPP); return; } /* Set fc vport state based on virtual lnode */ csio_lnode_state_to_str(ln, state); if (strcmp(state, "READY")) { fc_vport_set_state(fc_vport, FC_VPORT_LINKDOWN); return; } fc_vport_set_state(fc_vport, FC_VPORT_ACTIVE); }
static int csio_vport_disable(struct fc_vport *fc_vport, bool disable) { struct csio_lnode *ln = *(struct csio_lnode **)fc_vport->dd_data; struct Scsi_Host *shost = csio_ln_to_shost(ln); struct csio_hw *hw = csio_lnode_to_hw(ln); /* disable vport */ if (disable) { /* Quiesce ios and send stop event to lnode */ scsi_block_requests(shost); spin_lock_irq(&hw->lock); csio_scsim_cleanup_io_lnode(csio_hw_to_scsim(hw), ln); csio_lnode_stop(ln); spin_unlock_irq(&hw->lock); scsi_unblock_requests(shost); /* Free vnp */ csio_fcoe_free_vnp(hw, ln); fc_vport_set_state(fc_vport, FC_VPORT_DISABLED); csio_ln_err(ln, "vport disabled\n"); return 0; } else { /* enable vport */ fc_vport_set_state(fc_vport, FC_VPORT_INITIALIZING); if (csio_fcoe_alloc_vnp(hw, ln)) { csio_ln_err(ln, "vport enabled failed.\n"); return -1; } csio_ln_err(ln, "vport enabled\n"); return 0; } }
static int bfad_im_vport_disable(struct fc_vport *fc_vport, bool disable) { struct bfad_vport_s *vport; struct bfad_s *bfad; struct bfa_fcs_vport_s *fcs_vport; struct Scsi_Host *vshost; wwn_t pwwn; unsigned long flags; vport = (struct bfad_vport_s *)fc_vport->dd_data; bfad = vport->drv_port.bfad; vshost = vport->drv_port.im_port->shost; pwwn = wwn_to_u64((u8 *) &fc_vport->port_name); spin_lock_irqsave(&bfad->bfad_lock, flags); fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0, pwwn); spin_unlock_irqrestore(&bfad->bfad_lock, flags); if (fcs_vport == NULL) return VPCERR_BAD_WWN; if (disable) { bfa_fcs_vport_stop(fcs_vport); fc_vport_set_state(fc_vport, FC_VPORT_DISABLED); } else { bfa_fcs_vport_start(fcs_vport); fc_vport_set_state(fc_vport, FC_VPORT_ACTIVE); } return 0; }
/** * fc_lport_enter_reset() - Reset the local port * @lport: The local port to be reset * * Locking Note: The lport lock is expected to be held before calling * this routine. */ static void fc_lport_enter_reset(struct fc_lport *lport) { FC_LPORT_DBG(lport, "Entered RESET state from %s state\n", fc_lport_state(lport)); if (lport->vport) { if (lport->link_up) fc_vport_set_state(lport->vport, FC_VPORT_INITIALIZING); else fc_vport_set_state(lport->vport, FC_VPORT_LINKDOWN); } fc_lport_state_enter(lport, LPORT_ST_RESET); fc_vports_linkchange(lport); fc_lport_reset_locked(lport); if (lport->link_up) fc_lport_enter_flogi(lport); }
/** * fc_rport_enter_ready() - Enter the ready state and start discovery * @lport: The local port that is ready * * Locking Note: The lport lock is expected to be held before calling * this routine. */ static void fc_lport_enter_ready(struct fc_lport *lport) { FC_LPORT_DBG(lport, "Entered READY from state %s\n", fc_lport_state(lport)); fc_lport_state_enter(lport, LPORT_ST_READY); if (lport->vport) fc_vport_set_state(lport->vport, FC_VPORT_ACTIVE); fc_vports_linkchange(lport); if (!lport->ptp_rdata) lport->tt.disc_start(fc_lport_disc_callback, lport); }
static void fc_lport_enter_reset(struct fc_lport *lport) { FC_LPORT_DBG(lport, "Entered RESET state from %s state\n", fc_lport_state(lport)); if (lport->state == LPORT_ST_DISABLED || lport->state == LPORT_ST_LOGO) return; if (lport->vport) { if (lport->link_up) fc_vport_set_state(lport->vport, FC_VPORT_INITIALIZING); else fc_vport_set_state(lport->vport, FC_VPORT_LINKDOWN); } fc_lport_state_enter(lport, LPORT_ST_RESET); fc_host_post_event(lport->host, fc_get_event_number(), FCH_EVT_LIPRESET, 0); fc_vports_linkchange(lport); fc_lport_reset_locked(lport); if (lport->link_up) fc_lport_enter_flogi(lport); }
static int csio_vport_create(struct fc_vport *fc_vport, bool disable) { struct Scsi_Host *shost = fc_vport->shost; struct csio_lnode *pln = shost_priv(shost); struct csio_lnode *ln = NULL; struct csio_hw *hw = csio_lnode_to_hw(pln); uint8_t wwn[8]; int ret = -1; ln = csio_shost_init(hw, &fc_vport->dev, false, pln); if (!ln) goto error; if (fc_vport->node_name != 0) { u64_to_wwn(fc_vport->node_name, wwn); if (!CSIO_VALID_WWN(wwn)) { csio_ln_err(ln, "vport create failed. Invalid wwnn\n"); goto error; } memcpy(csio_ln_wwnn(ln), wwn, 8); } if (fc_vport->port_name != 0) { u64_to_wwn(fc_vport->port_name, wwn); if (!CSIO_VALID_WWN(wwn)) { csio_ln_err(ln, "vport create failed. Invalid wwpn\n"); goto error; } if (csio_lnode_lookup_by_wwpn(hw, wwn)) { csio_ln_err(ln, "vport create failed. wwpn already exists\n"); goto error; } memcpy(csio_ln_wwpn(ln), wwn, 8); } fc_vport_set_state(fc_vport, FC_VPORT_INITIALIZING); if (csio_fcoe_alloc_vnp(hw, ln)) goto error; *(struct csio_lnode **)fc_vport->dd_data = ln; ln->fc_vport = fc_vport; if (!fc_vport->node_name) fc_vport->node_name = wwn_to_u64(csio_ln_wwnn(ln)); if (!fc_vport->port_name) fc_vport->port_name = wwn_to_u64(csio_ln_wwpn(ln)); csio_fchost_attr_init(ln); return 0; error: if (ln) csio_shost_exit(ln); return ret; }
static int bfad_im_vport_create(struct fc_vport *fc_vport, bool disable) { char *vname = fc_vport->symbolic_name; struct Scsi_Host *shost = fc_vport->shost; struct bfad_im_port_s *im_port = (struct bfad_im_port_s *) shost->hostdata[0]; struct bfad_s *bfad = im_port->bfad; struct bfa_port_cfg_s port_cfg; int status = 0, rc; unsigned long flags; memset(&port_cfg, 0, sizeof(port_cfg)); port_cfg.pwwn = wwn_to_u64((u8 *) &fc_vport->port_name); port_cfg.nwwn = wwn_to_u64((u8 *) &fc_vport->node_name); if (strlen(vname) > 0) strcpy((char *)&port_cfg.sym_name, vname); port_cfg.roles = BFA_PORT_ROLE_FCP_IM; rc = bfad_vport_create(bfad, 0, &port_cfg, &fc_vport->dev); if (rc == BFA_STATUS_OK) { struct bfad_vport_s *vport; struct bfa_fcs_vport_s *fcs_vport; struct Scsi_Host *vshost; spin_lock_irqsave(&bfad->bfad_lock, flags); fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0, port_cfg.pwwn); if (fcs_vport == NULL) { spin_unlock_irqrestore(&bfad->bfad_lock, flags); return VPCERR_BAD_WWN; } fc_vport_set_state(fc_vport, FC_VPORT_ACTIVE); if (disable) { bfa_fcs_vport_stop(fcs_vport); fc_vport_set_state(fc_vport, FC_VPORT_DISABLED); } spin_unlock_irqrestore(&bfad->bfad_lock, flags); vport = fcs_vport->vport_drv; vshost = vport->drv_port.im_port->shost; fc_host_node_name(vshost) = wwn_to_u64((u8 *) &port_cfg.nwwn); fc_host_port_name(vshost) = wwn_to_u64((u8 *) &port_cfg.pwwn); fc_vport->dd_data = vport; vport->drv_port.im_port->fc_vport = fc_vport; } else if (rc == BFA_STATUS_INVALID_WWN) return VPCERR_BAD_WWN; else if (rc == BFA_STATUS_VPORT_EXISTS) return VPCERR_BAD_WWN; else if (rc == BFA_STATUS_VPORT_MAX) return VPCERR_NO_FABRIC_SUPP; else if (rc == BFA_STATUS_VPORT_WWN_BP) return VPCERR_BAD_WWN; else return FC_VPORT_FAILED; return status; }