Lines Matching +full:host +full:- +full:port
1 // SPDX-License-Identifier: GPL-2.0-only
5 * Maintained at www.Open-FCoE.org
9 * PORT LOCKING NOTES
11 * These comments only apply to the 'port code' which consists of the lport,
27 * be held while attempting to acquire a greater lock. Here is the hierarchy-
42 * single-threaded workqueue. An rport would never be free'd while in a
92 /* Fabric IDs to use for point-to-point mode, chosen on whims. */
134 * struct fc_bsg_info - FC Passthrough managemet structure
136 * @lport: The local port to pass through a command
138 * @sg: job->reply_payload.sg_list
139 * @nents: job->reply_payload.sg_cnt
152 * fc_frame_drop() - Dummy frame handler
153 * @lport: The local port the frame was received on
163 * fc_lport_rport_callback() - Event handler for rport events
165 * @rdata: private remote port data
175 FC_LPORT_DBG(lport, "Received a %d event for port (%6.6x)\n", event, in fc_lport_rport_callback()
176 rdata->ids.port_id); in fc_lport_rport_callback()
178 mutex_lock(&lport->lp_mutex); in fc_lport_rport_callback()
181 if (lport->state == LPORT_ST_DNS) { in fc_lport_rport_callback()
182 lport->dns_rdata = rdata; in fc_lport_rport_callback()
184 } else if (lport->state == LPORT_ST_FDMI) { in fc_lport_rport_callback()
185 lport->ms_rdata = rdata; in fc_lport_rport_callback()
189 "on port (%6.6x) for the directory " in fc_lport_rport_callback()
192 "%d state", rdata->ids.port_id, in fc_lport_rport_callback()
193 lport->state); in fc_lport_rport_callback()
200 if (rdata->ids.port_id == FC_FID_DIR_SERV) in fc_lport_rport_callback()
201 lport->dns_rdata = NULL; in fc_lport_rport_callback()
202 else if (rdata->ids.port_id == FC_FID_MGMT_SERV) in fc_lport_rport_callback()
203 lport->ms_rdata = NULL; in fc_lport_rport_callback()
208 mutex_unlock(&lport->lp_mutex); in fc_lport_rport_callback()
212 * fc_lport_state() - Return a string which represents the lport's state
219 cp = fc_lport_state_names[lport->state]; in fc_lport_state()
226 * fc_lport_ptp_setup() - Create an rport for point-to-point mode
236 lockdep_assert_held(&lport->lp_mutex); in fc_lport_ptp_setup()
238 if (lport->ptp_rdata) { in fc_lport_ptp_setup()
239 fc_rport_logoff(lport->ptp_rdata); in fc_lport_ptp_setup()
240 kref_put(&lport->ptp_rdata->kref, fc_rport_destroy); in fc_lport_ptp_setup()
242 mutex_lock(&lport->disc.disc_mutex); in fc_lport_ptp_setup()
243 lport->ptp_rdata = fc_rport_create(lport, remote_fid); in fc_lport_ptp_setup()
244 if (!lport->ptp_rdata) { in fc_lport_ptp_setup()
246 lport->port_id); in fc_lport_ptp_setup()
247 mutex_unlock(&lport->disc.disc_mutex); in fc_lport_ptp_setup()
250 kref_get(&lport->ptp_rdata->kref); in fc_lport_ptp_setup()
251 lport->ptp_rdata->ids.port_name = remote_wwpn; in fc_lport_ptp_setup()
252 lport->ptp_rdata->ids.node_name = remote_wwnn; in fc_lport_ptp_setup()
253 mutex_unlock(&lport->disc.disc_mutex); in fc_lport_ptp_setup()
255 fc_rport_login(lport->ptp_rdata); in fc_lport_ptp_setup()
261 * fc_get_host_port_state() - Return the port state of the given Scsi_Host
262 * @shost: The SCSI host whose port state is to be determined
268 mutex_lock(&lport->lp_mutex); in fc_get_host_port_state()
269 if (!lport->link_up) in fc_get_host_port_state()
272 switch (lport->state) { in fc_get_host_port_state()
279 mutex_unlock(&lport->lp_mutex); in fc_get_host_port_state()
284 * fc_get_host_speed() - Return the speed of the given Scsi_Host
285 * @shost: The SCSI host whose port speed is to be determined
291 fc_host_speed(shost) = lport->link_speed; in fc_get_host_speed()
296 * fc_get_host_stats() - Return the Scsi_Host's statistics
297 * @shost: The SCSI host whose statistics are to be returned
307 fc_stats = &lport->host_stats; in fc_get_host_stats()
310 fc_stats->seconds_since_last_reset = (jiffies - lport->boot_time) / HZ; in fc_get_host_stats()
315 stats = per_cpu_ptr(lport->stats, cpu); in fc_get_host_stats()
317 fc_stats->tx_frames += READ_ONCE(stats->TxFrames); in fc_get_host_stats()
318 fc_stats->tx_words += READ_ONCE(stats->TxWords); in fc_get_host_stats()
319 fc_stats->rx_frames += READ_ONCE(stats->RxFrames); in fc_get_host_stats()
320 fc_stats->rx_words += READ_ONCE(stats->RxWords); in fc_get_host_stats()
321 fc_stats->error_frames += READ_ONCE(stats->ErrorFrames); in fc_get_host_stats()
322 fc_stats->invalid_crc_count += READ_ONCE(stats->InvalidCRCCount); in fc_get_host_stats()
323 fc_stats->fcp_input_requests += READ_ONCE(stats->InputRequests); in fc_get_host_stats()
324 fc_stats->fcp_output_requests += READ_ONCE(stats->OutputRequests); in fc_get_host_stats()
325 fc_stats->fcp_control_requests += READ_ONCE(stats->ControlRequests); in fc_get_host_stats()
326 fcp_in_bytes += READ_ONCE(stats->InputBytes); in fc_get_host_stats()
327 fcp_out_bytes += READ_ONCE(stats->OutputBytes); in fc_get_host_stats()
328 fc_stats->fcp_packet_alloc_failures += READ_ONCE(stats->FcpPktAllocFails); in fc_get_host_stats()
329 fc_stats->fcp_packet_aborts += READ_ONCE(stats->FcpPktAborts); in fc_get_host_stats()
330 fc_stats->fcp_frame_alloc_failures += READ_ONCE(stats->FcpFrameAllocFails); in fc_get_host_stats()
331 fc_stats->link_failure_count += READ_ONCE(stats->LinkFailureCount); in fc_get_host_stats()
333 fc_stats->fcp_input_megabytes = div_u64(fcp_in_bytes, 1000000); in fc_get_host_stats()
334 fc_stats->fcp_output_megabytes = div_u64(fcp_out_bytes, 1000000); in fc_get_host_stats()
335 fc_stats->lip_count = -1; in fc_get_host_stats()
336 fc_stats->nos_count = -1; in fc_get_host_stats()
337 fc_stats->loss_of_sync_count = -1; in fc_get_host_stats()
338 fc_stats->loss_of_signal_count = -1; in fc_get_host_stats()
339 fc_stats->prim_seq_protocol_err_count = -1; in fc_get_host_stats()
340 fc_stats->dumped_frames = -1; in fc_get_host_stats()
350 * fc_lport_flogi_fill() - Fill in FLOGI command for request
351 * @lport: The local port the FLOGI is for
363 flogi->fl_cmd = (u8) op; in fc_lport_flogi_fill()
364 put_unaligned_be64(lport->wwpn, &flogi->fl_wwpn); in fc_lport_flogi_fill()
365 put_unaligned_be64(lport->wwnn, &flogi->fl_wwnn); in fc_lport_flogi_fill()
366 sp = &flogi->fl_csp; in fc_lport_flogi_fill()
367 sp->sp_hi_ver = 0x20; in fc_lport_flogi_fill()
368 sp->sp_lo_ver = 0x20; in fc_lport_flogi_fill()
369 sp->sp_bb_cred = htons(10); /* this gets set by gateway */ in fc_lport_flogi_fill()
370 sp->sp_bb_data = htons((u16) lport->mfs); in fc_lport_flogi_fill()
371 cp = &flogi->fl_cssp[3 - 1]; /* class 3 parameters */ in fc_lport_flogi_fill()
372 cp->cp_class = htons(FC_CPC_VALID | FC_CPC_SEQ); in fc_lport_flogi_fill()
374 sp->sp_features = htons(FC_SP_FT_CIRO); in fc_lport_flogi_fill()
375 sp->sp_tot_seq = htons(255); /* seq. we accept */ in fc_lport_flogi_fill()
376 sp->sp_rel_off = htons(0x1f); in fc_lport_flogi_fill()
377 sp->sp_e_d_tov = htonl(lport->e_d_tov); in fc_lport_flogi_fill()
379 cp->cp_rdfs = htons((u16) lport->mfs); in fc_lport_flogi_fill()
380 cp->cp_con_seq = htons(255); in fc_lport_flogi_fill()
381 cp->cp_open_seq = 1; in fc_lport_flogi_fill()
386 * fc_lport_add_fc4_type() - Add a supported FC-4 type to a local port
387 * @lport: The local port to add a new FC-4 type to
388 * @type: The new FC-4 type
394 mp = &lport->fcts.ff_type_map[type / FC_NS_BPW]; in fc_lport_add_fc4_type()
399 * fc_lport_recv_rlir_req() - Handle received Registered Link Incident Report.
400 * @lport: Fibre Channel local port receiving the RLIR
405 lockdep_assert_held(&lport->lp_mutex); in fc_lport_recv_rlir_req()
415 * fc_lport_recv_echo_req() - Handle received ECHO request
416 * @lport: The local port receiving the ECHO
427 lockdep_assert_held(&lport->lp_mutex); in fc_lport_recv_echo_req()
432 len = fr_len(in_fp) - sizeof(struct fc_frame_header); in fc_lport_recv_echo_req()
444 lport->tt.frame_send(lport, fp); in fc_lport_recv_echo_req()
450 * fc_lport_recv_rnid_req() - Handle received Request Node ID data request
451 * @lport: The local port receiving the RNID
468 lockdep_assert_held(&lport->lp_mutex); in fc_lport_recv_rnid_req()
479 fmt = req->rnid_fmt; in fc_lport_recv_rnid_req()
482 ntohl(lport->rnid_gen.rnid_atype) == 0) { in fc_lport_recv_rnid_req()
484 len -= sizeof(rp->gen); in fc_lport_recv_rnid_req()
490 rp->rnid.rnid_cmd = ELS_LS_ACC; in fc_lport_recv_rnid_req()
491 rp->rnid.rnid_fmt = fmt; in fc_lport_recv_rnid_req()
492 rp->rnid.rnid_cid_len = sizeof(rp->cid); in fc_lport_recv_rnid_req()
493 rp->cid.rnid_wwpn = htonll(lport->wwpn); in fc_lport_recv_rnid_req()
494 rp->cid.rnid_wwnn = htonll(lport->wwnn); in fc_lport_recv_rnid_req()
496 rp->rnid.rnid_sid_len = sizeof(rp->gen); in fc_lport_recv_rnid_req()
497 memcpy(&rp->gen, &lport->rnid_gen, in fc_lport_recv_rnid_req()
498 sizeof(rp->gen)); in fc_lport_recv_rnid_req()
501 lport->tt.frame_send(lport, fp); in fc_lport_recv_rnid_req()
508 * fc_lport_recv_logo_req() - Handle received fabric LOGO request
509 * @lport: The local port receiving the LOGO
514 lockdep_assert_held(&lport->lp_mutex); in fc_lport_recv_logo_req()
522 * fc_fabric_login() - Start the lport state machine
523 * @lport: The local port that should log into the fabric
530 int rc = -1; in fc_fabric_login()
532 mutex_lock(&lport->lp_mutex); in fc_fabric_login()
533 if (lport->state == LPORT_ST_DISABLED || in fc_fabric_login()
534 lport->state == LPORT_ST_LOGO) { in fc_fabric_login()
539 mutex_unlock(&lport->lp_mutex); in fc_fabric_login()
546 * __fc_linkup() - Handler for transport linkup events
551 lockdep_assert_held(&lport->lp_mutex); in __fc_linkup()
553 if (!lport->link_up) { in __fc_linkup()
554 lport->link_up = 1; in __fc_linkup()
556 if (lport->state == LPORT_ST_RESET) in __fc_linkup()
562 * fc_linkup() - Handler for transport linkup events
563 * @lport: The local port whose link is up
567 printk(KERN_INFO "host%d: libfc: Link up on port (%6.6x)\n", in fc_linkup()
568 lport->host->host_no, lport->port_id); in fc_linkup()
570 mutex_lock(&lport->lp_mutex); in fc_linkup()
572 mutex_unlock(&lport->lp_mutex); in fc_linkup()
577 * __fc_linkdown() - Handler for transport linkdown events
582 lockdep_assert_held(&lport->lp_mutex); in __fc_linkdown()
584 if (lport->link_up) { in __fc_linkdown()
585 lport->link_up = 0; in __fc_linkdown()
587 lport->tt.fcp_cleanup(lport); in __fc_linkdown()
592 * fc_linkdown() - Handler for transport linkdown events
593 * @lport: The local port whose link is down
597 printk(KERN_INFO "host%d: libfc: Link down on port (%6.6x)\n", in fc_linkdown()
598 lport->host->host_no, lport->port_id); in fc_linkdown()
600 mutex_lock(&lport->lp_mutex); in fc_linkdown()
602 mutex_unlock(&lport->lp_mutex); in fc_linkdown()
607 * fc_fabric_logoff() - Logout of the fabric
608 * @lport: The local port to logoff the fabric
611 * 0 for success, -1 for failure
615 lport->tt.disc_stop_final(lport); in fc_fabric_logoff()
616 mutex_lock(&lport->lp_mutex); in fc_fabric_logoff()
617 if (lport->dns_rdata) in fc_fabric_logoff()
618 fc_rport_logoff(lport->dns_rdata); in fc_fabric_logoff()
619 mutex_unlock(&lport->lp_mutex); in fc_fabric_logoff()
621 mutex_lock(&lport->lp_mutex); in fc_fabric_logoff()
623 mutex_unlock(&lport->lp_mutex); in fc_fabric_logoff()
624 cancel_delayed_work_sync(&lport->retry_work); in fc_fabric_logoff()
630 * fc_lport_destroy() - Unregister a fc_lport
631 * @lport: The local port to unregister
635 * clean-up all the allocated memory
641 mutex_lock(&lport->lp_mutex); in fc_lport_destroy()
642 lport->state = LPORT_ST_DISABLED; in fc_lport_destroy()
643 lport->link_up = 0; in fc_lport_destroy()
644 lport->tt.frame_send = fc_frame_drop; in fc_lport_destroy()
645 mutex_unlock(&lport->lp_mutex); in fc_lport_destroy()
647 lport->tt.fcp_abort_io(lport); in fc_lport_destroy()
648 lport->tt.disc_stop_final(lport); in fc_lport_destroy()
649 lport->tt.exch_mgr_reset(lport, 0, 0); in fc_lport_destroy()
650 cancel_delayed_work_sync(&lport->retry_work); in fc_lport_destroy()
657 * fc_set_mfs() - Set the maximum frame size for a local port
658 * @lport: The local port to set the MFS for
664 int rc = -EINVAL; in fc_set_mfs()
666 mutex_lock(&lport->lp_mutex); in fc_set_mfs()
668 old_mfs = lport->mfs; in fc_set_mfs()
674 mfs -= sizeof(struct fc_frame_header); in fc_set_mfs()
675 lport->mfs = mfs; in fc_set_mfs()
682 mutex_unlock(&lport->lp_mutex); in fc_set_mfs()
689 * fc_lport_disc_callback() - Callback for discovery events
690 * @lport: The local port receiving the event
701 printk(KERN_ERR "host%d: libfc: " in fc_lport_disc_callback()
702 "Discovery failed for port (%6.6x)\n", in fc_lport_disc_callback()
703 lport->host->host_no, lport->port_id); in fc_lport_disc_callback()
704 mutex_lock(&lport->lp_mutex); in fc_lport_disc_callback()
706 mutex_unlock(&lport->lp_mutex); in fc_lport_disc_callback()
715 * fc_lport_enter_ready() - Enter the ready state and start discovery
716 * @lport: The local port that is ready
720 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_ready()
726 if (lport->vport) in fc_lport_enter_ready()
727 fc_vport_set_state(lport->vport, FC_VPORT_ACTIVE); in fc_lport_enter_ready()
730 if (!lport->ptp_rdata) in fc_lport_enter_ready()
731 lport->tt.disc_start(fc_lport_disc_callback, lport); in fc_lport_enter_ready()
735 * fc_lport_set_port_id() - set the local port Port ID
736 * @lport: The local port which will have its Port ID set.
737 * @port_id: The new port ID.
743 lockdep_assert_held(&lport->lp_mutex); in fc_lport_set_port_id()
746 printk(KERN_INFO "host%d: Assigned Port ID %6.6x\n", in fc_lport_set_port_id()
747 lport->host->host_no, port_id); in fc_lport_set_port_id()
749 lport->port_id = port_id; in fc_lport_set_port_id()
752 fc_host_port_id(lport->host) = port_id; in fc_lport_set_port_id()
754 if (lport->tt.lport_set_port_id) in fc_lport_set_port_id()
755 lport->tt.lport_set_port_id(lport, port_id, fp); in fc_lport_set_port_id()
759 * fc_lport_set_local_id() - set the local port Port ID for point-to-multipoint
760 * @lport: The local port which will have its Port ID set.
761 * @port_id: The new port ID.
763 * Called by the lower-level driver when transport sets the local port_id.
769 mutex_lock(&lport->lp_mutex); in fc_lport_set_local_id()
773 switch (lport->state) { in fc_lport_set_local_id()
782 mutex_unlock(&lport->lp_mutex); in fc_lport_set_local_id()
787 * fc_lport_recv_flogi_req() - Receive a FLOGI request
788 * @lport: The local port that received the request
791 * A received FLOGI request indicates a point-to-point connection.
792 * Accept it with the common service parameters indicating our N port.
793 * Set up to do a PLOGI if we have the higher-number WWPN.
806 lockdep_assert_held(&lport->lp_mutex); in fc_lport_recv_flogi_req()
815 remote_wwpn = get_unaligned_be64(&flp->fl_wwpn); in fc_lport_recv_flogi_req()
816 if (remote_wwpn == lport->wwpn) { in fc_lport_recv_flogi_req()
817 printk(KERN_WARNING "host%d: libfc: Received FLOGI from port " in fc_lport_recv_flogi_req()
819 lport->host->host_no, remote_wwpn); in fc_lport_recv_flogi_req()
822 FC_LPORT_DBG(lport, "FLOGI from port WWPN %16.16llx\n", remote_wwpn); in fc_lport_recv_flogi_req()
830 if (remote_wwpn < lport->wwpn) { in fc_lport_recv_flogi_req()
844 new_flp->fl_cmd = (u8) ELS_LS_ACC; in fc_lport_recv_flogi_req()
852 hton24(fh->fh_s_id, local_fid); in fc_lport_recv_flogi_req()
853 hton24(fh->fh_d_id, remote_fid); in fc_lport_recv_flogi_req()
854 lport->tt.frame_send(lport, fp); in fc_lport_recv_flogi_req()
860 get_unaligned_be64(&flp->fl_wwnn)); in fc_lport_recv_flogi_req()
866 * fc_lport_recv_els_req() - The generic lport ELS request handler
867 * @lport: The local port that received the request
879 mutex_lock(&lport->lp_mutex); in fc_lport_recv_els_req()
886 if (!lport->link_up) in fc_lport_recv_els_req()
894 if (!lport->point_to_multipoint) in fc_lport_recv_els_req()
906 lport->tt.disc_recv_req(lport, fp); in fc_lport_recv_els_req()
922 mutex_unlock(&lport->lp_mutex); in fc_lport_recv_els_req()
938 * fc_lport_recv() - The generic lport request handler
960 if (fh->fh_type >= FC_FC4_PROV_SIZE) in fc_lport_recv()
962 prov = rcu_dereference(fc_passive_prov[fh->fh_type]); in fc_lport_recv()
963 if (!prov || !try_module_get(prov->module)) in fc_lport_recv()
966 prov->recv(lport, fp); in fc_lport_recv()
967 module_put(prov->module); in fc_lport_recv()
971 FC_LPORT_DBG(lport, "dropping unexpected frame type %x\n", fh->fh_type); in fc_lport_recv()
979 * fc_lport_reset() - Reset a local port
980 * @lport: The local port which should be reset
987 cancel_delayed_work_sync(&lport->retry_work); in fc_lport_reset()
988 mutex_lock(&lport->lp_mutex); in fc_lport_reset()
990 mutex_unlock(&lport->lp_mutex); in fc_lport_reset()
996 * fc_lport_reset_locked() - Reset the local port w/ the lport lock held
997 * @lport: The local port to be reset
1001 lockdep_assert_held(&lport->lp_mutex); in fc_lport_reset_locked()
1003 if (lport->dns_rdata) { in fc_lport_reset_locked()
1004 fc_rport_logoff(lport->dns_rdata); in fc_lport_reset_locked()
1005 lport->dns_rdata = NULL; in fc_lport_reset_locked()
1008 if (lport->ptp_rdata) { in fc_lport_reset_locked()
1009 fc_rport_logoff(lport->ptp_rdata); in fc_lport_reset_locked()
1010 kref_put(&lport->ptp_rdata->kref, fc_rport_destroy); in fc_lport_reset_locked()
1011 lport->ptp_rdata = NULL; in fc_lport_reset_locked()
1014 lport->tt.disc_stop(lport); in fc_lport_reset_locked()
1016 lport->tt.exch_mgr_reset(lport, 0, 0); in fc_lport_reset_locked()
1017 fc_host_fabric_name(lport->host) = 0; in fc_lport_reset_locked()
1019 if (lport->port_id && (!lport->point_to_multipoint || !lport->link_up)) in fc_lport_reset_locked()
1024 * fc_lport_enter_reset() - Reset the local port
1025 * @lport: The local port to be reset
1029 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_reset()
1034 if (lport->state == LPORT_ST_DISABLED || lport->state == LPORT_ST_LOGO) in fc_lport_enter_reset()
1037 if (lport->vport) { in fc_lport_enter_reset()
1038 if (lport->link_up) in fc_lport_enter_reset()
1039 fc_vport_set_state(lport->vport, FC_VPORT_INITIALIZING); in fc_lport_enter_reset()
1041 fc_vport_set_state(lport->vport, FC_VPORT_LINKDOWN); in fc_lport_enter_reset()
1044 fc_host_post_event(lport->host, fc_get_event_number(), in fc_lport_enter_reset()
1048 if (lport->link_up) in fc_lport_enter_reset()
1053 * fc_lport_enter_disabled() - Disable the local port
1054 * @lport: The local port to be reset
1058 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_disabled()
1069 * fc_lport_error() - Handler for any errors
1070 * @lport: The local port that the error was on
1081 IS_ERR(fp) ? -PTR_ERR(fp) : 0, fc_lport_state(lport), in fc_lport_error()
1082 lport->retry_count); in fc_lport_error()
1084 if (PTR_ERR(fp) == -FC_EX_CLOSED) in fc_lport_error()
1092 if (lport->retry_count < lport->max_retry_count) { in fc_lport_error()
1093 lport->retry_count++; in fc_lport_error()
1097 delay = msecs_to_jiffies(lport->e_d_tov); in fc_lport_error()
1099 schedule_delayed_work(&lport->retry_work, delay); in fc_lport_error()
1105 * fc_lport_ns_resp() - Handle response to a name server
1109 * @lp_arg: Fibre Channel host port instance
1124 if (fp == ERR_PTR(-FC_EX_CLOSED)) in fc_lport_ns_resp()
1127 mutex_lock(&lport->lp_mutex); in fc_lport_ns_resp()
1129 if (lport->state < LPORT_ST_RNN_ID || lport->state > LPORT_ST_RFF_ID) { in fc_lport_ns_resp()
1145 if (fh && ct && fh->fh_type == FC_TYPE_CT && in fc_lport_ns_resp()
1146 ct->ct_fs_type == FC_FST_DIR && in fc_lport_ns_resp()
1147 ct->ct_fs_subtype == FC_NS_SUBTYPE && in fc_lport_ns_resp()
1148 ntohs(ct->ct_cmd) == FC_FS_ACC) in fc_lport_ns_resp()
1149 switch (lport->state) { in fc_lport_ns_resp()
1163 if (lport->fdmi_enabled) in fc_lport_ns_resp()
1177 mutex_unlock(&lport->lp_mutex); in fc_lport_ns_resp()
1181 * fc_lport_ms_resp() - Handle response to a management server
1185 * @lp_arg: Fibre Channel host port instance
1197 struct fc_host_attrs *fc_host = shost_to_fc_host(lport->host); in fc_lport_ms_resp()
1200 if (fp == ERR_PTR(-FC_EX_CLOSED)) in fc_lport_ms_resp()
1203 mutex_lock(&lport->lp_mutex); in fc_lport_ms_resp()
1205 if (lport->state < LPORT_ST_RHBA || lport->state > LPORT_ST_DPRT) { in fc_lport_ms_resp()
1221 if (fh && ct && fh->fh_type == FC_TYPE_CT && in fc_lport_ms_resp()
1222 ct->ct_fs_type == FC_FST_MGMT && in fc_lport_ms_resp()
1223 ct->ct_fs_subtype == FC_FDMI_SUBTYPE) { in fc_lport_ms_resp()
1226 ct->ct_reason, in fc_lport_ms_resp()
1227 ct->ct_explan); in fc_lport_ms_resp()
1229 switch (lport->state) { in fc_lport_ms_resp()
1231 if ((ntohs(ct->ct_cmd) == FC_FS_RJT) && fc_host->fdmi_version == FDMI_V2) { in fc_lport_ms_resp()
1232 FC_LPORT_DBG(lport, "Error for FDMI-V2, fall back to FDMI-V1\n"); in fc_lport_ms_resp()
1233 fc_host->fdmi_version = FDMI_V1; in fc_lport_ms_resp()
1237 } else if (ntohs(ct->ct_cmd) == FC_FS_ACC) in fc_lport_ms_resp()
1262 mutex_unlock(&lport->lp_mutex); in fc_lport_ms_resp()
1266 * fc_lport_scr_resp() - Handle response to State Change Register (SCR) request
1269 * @lp_arg: Fibre Channel lport port instance that sent the registration request
1283 if (fp == ERR_PTR(-FC_EX_CLOSED)) in fc_lport_scr_resp()
1286 mutex_lock(&lport->lp_mutex); in fc_lport_scr_resp()
1288 if (lport->state != LPORT_ST_SCR) { in fc_lport_scr_resp()
1310 mutex_unlock(&lport->lp_mutex); in fc_lport_scr_resp()
1314 * fc_lport_enter_scr() - Send a SCR (State Change Register) request
1315 * @lport: The local port to register for state changes
1321 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_scr()
1334 if (!lport->tt.elsct_send(lport, FC_FID_FCTRL, fp, ELS_SCR, in fc_lport_enter_scr()
1336 2 * lport->r_a_tov)) in fc_lport_enter_scr()
1341 * fc_lport_enter_ns() - register some object with the name server
1342 * @lport: Fibre Channel local port to register
1343 * @state: Local port state
1352 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_ns()
1366 len = strnlen(fc_host_symbolic_name(lport->host), 255); in fc_lport_enter_ns()
1374 len = strnlen(fc_host_symbolic_name(lport->host), 255); in fc_lport_enter_ns()
1400 if (!lport->tt.elsct_send(lport, FC_FID_DIR_SERV, fp, cmd, in fc_lport_enter_ns()
1402 lport, 3 * lport->r_a_tov)) in fc_lport_enter_ns()
1411 * fc_lport_enter_dns() - Create a fc_rport for the name server
1412 * @lport: The local port requesting a remote port for the name server
1418 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_dns()
1425 mutex_lock(&lport->disc.disc_mutex); in fc_lport_enter_dns()
1427 mutex_unlock(&lport->disc.disc_mutex); in fc_lport_enter_dns()
1431 rdata->ops = &fc_lport_rport_ops; in fc_lport_enter_dns()
1440 * fc_lport_enter_ms() - management server commands
1441 * @lport: Fibre Channel local port to register
1442 * @state: Local port state
1451 struct fc_host_attrs *fc_host = shost_to_fc_host(lport->host); in fc_lport_enter_ms()
1452 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_ms()
1466 len -= sizeof(struct fc_fdmi_attr_entry); in fc_lport_enter_ms()
1481 if (fc_host->fdmi_version == FDMI_V2) { in fc_lport_enter_ms()
1498 /* Number of Port Attributes */ in fc_lport_enter_ms()
1501 len -= sizeof(struct fc_fdmi_attr_entry); in fc_lport_enter_ms()
1509 if (fc_host->fdmi_version == FDMI_V2) { in fc_lport_enter_ms()
1550 if (!lport->tt.elsct_send(lport, FC_FID_MGMT_SERV, fp, cmd, in fc_lport_enter_ms()
1552 lport, 3 * lport->r_a_tov)) in fc_lport_enter_ms()
1557 * fc_lport_enter_fdmi() - Create a fc_rport for the management server
1558 * @lport: The local port requesting a remote port for the management server
1564 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_fdmi()
1571 mutex_lock(&lport->disc.disc_mutex); in fc_lport_enter_fdmi()
1573 mutex_unlock(&lport->disc.disc_mutex); in fc_lport_enter_fdmi()
1577 rdata->ops = &fc_lport_rport_ops; in fc_lport_enter_fdmi()
1586 * fc_lport_timeout() - Handler for the retry_work timer
1587 * @work: The work struct of the local port
1594 struct fc_host_attrs *fc_host = shost_to_fc_host(lport->host); in fc_lport_timeout()
1596 mutex_lock(&lport->lp_mutex); in fc_lport_timeout()
1598 switch (lport->state) { in fc_lport_timeout()
1616 fc_lport_enter_ns(lport, lport->state); in fc_lport_timeout()
1622 if (fc_host->fdmi_version == FDMI_V2) { in fc_lport_timeout()
1623 FC_LPORT_DBG(lport, "timeout for FDMI-V2 RHBA,fall back to FDMI-V1\n"); in fc_lport_timeout()
1624 fc_host->fdmi_version = FDMI_V1; in fc_lport_timeout()
1643 mutex_unlock(&lport->lp_mutex); in fc_lport_timeout()
1647 * fc_lport_logo_resp() - Handle response to LOGO request
1650 * @lp_arg: The lport port that received the LOGO request
1664 if (fp == ERR_PTR(-FC_EX_CLOSED)) in fc_lport_logo_resp()
1667 mutex_lock(&lport->lp_mutex); in fc_lport_logo_resp()
1669 if (lport->state != LPORT_ST_LOGO) { in fc_lport_logo_resp()
1691 mutex_unlock(&lport->lp_mutex); in fc_lport_logo_resp()
1696 * fc_lport_enter_logo() - Logout of the fabric
1697 * @lport: The local port to be logged out
1704 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_logo()
1718 if (!lport->tt.elsct_send(lport, FC_FID_FLOGI, fp, ELS_LOGO, in fc_lport_enter_logo()
1720 2 * lport->r_a_tov)) in fc_lport_enter_logo()
1725 * fc_lport_flogi_resp() - Handle response to FLOGI request
1728 * @lp_arg: The lport port that received the FLOGI response
1748 if (fp == ERR_PTR(-FC_EX_CLOSED)) in fc_lport_flogi_resp()
1751 mutex_lock(&lport->lp_mutex); in fc_lport_flogi_resp()
1753 if (lport->state != LPORT_ST_FLOGI) { in fc_lport_flogi_resp()
1768 if (fh->fh_r_ctl != FC_RCTL_ELS_REP || did == 0 || in fc_lport_flogi_resp()
1782 mfs = ntohs(flp->fl_csp.sp_bb_data) & in fc_lport_flogi_resp()
1787 "lport->mfs:%u\n", mfs, lport->mfs); in fc_lport_flogi_resp()
1792 if (mfs <= lport->mfs) { in fc_lport_flogi_resp()
1793 lport->mfs = mfs; in fc_lport_flogi_resp()
1794 fc_host_maxframe_size(lport->host) = mfs; in fc_lport_flogi_resp()
1797 csp_flags = ntohs(flp->fl_csp.sp_features); in fc_lport_flogi_resp()
1798 r_a_tov = ntohl(flp->fl_csp.sp_r_a_tov); in fc_lport_flogi_resp()
1799 e_d_tov = ntohl(flp->fl_csp.sp_e_d_tov); in fc_lport_flogi_resp()
1803 lport->npiv_enabled = !!(csp_flags & FC_SP_FT_NPIV_ACC); in fc_lport_flogi_resp()
1806 if (e_d_tov > lport->e_d_tov) in fc_lport_flogi_resp()
1807 lport->e_d_tov = e_d_tov; in fc_lport_flogi_resp()
1808 lport->r_a_tov = 2 * lport->e_d_tov; in fc_lport_flogi_resp()
1810 printk(KERN_INFO "host%d: libfc: " in fc_lport_flogi_resp()
1811 "Port (%6.6x) entered " in fc_lport_flogi_resp()
1812 "point-to-point mode\n", in fc_lport_flogi_resp()
1813 lport->host->host_no, did); in fc_lport_flogi_resp()
1816 &flp->fl_wwpn), in fc_lport_flogi_resp()
1818 &flp->fl_wwnn)); in fc_lport_flogi_resp()
1820 if (e_d_tov > lport->e_d_tov) in fc_lport_flogi_resp()
1821 lport->e_d_tov = e_d_tov; in fc_lport_flogi_resp()
1822 if (r_a_tov > lport->r_a_tov) in fc_lport_flogi_resp()
1823 lport->r_a_tov = r_a_tov; in fc_lport_flogi_resp()
1824 fc_host_fabric_name(lport->host) = in fc_lport_flogi_resp()
1825 get_unaligned_be64(&flp->fl_wwnn); in fc_lport_flogi_resp()
1833 mutex_unlock(&lport->lp_mutex); in fc_lport_flogi_resp()
1838 * fc_lport_enter_flogi() - Send a FLOGI request to the fabric manager
1839 * @lport: Fibre Channel local port to be logged in to the fabric
1845 lockdep_assert_held(&lport->lp_mutex); in fc_lport_enter_flogi()
1852 if (lport->point_to_multipoint) { in fc_lport_enter_flogi()
1853 if (lport->port_id) in fc_lport_enter_flogi()
1862 if (!lport->tt.elsct_send(lport, FC_FID_FLOGI, fp, in fc_lport_enter_flogi()
1863 lport->vport ? ELS_FDISC : ELS_FLOGI, in fc_lport_enter_flogi()
1865 lport->vport ? 2 * lport->r_a_tov : in fc_lport_enter_flogi()
1866 lport->e_d_tov)) in fc_lport_enter_flogi()
1871 * fc_lport_config() - Configure a fc_lport
1872 * @lport: The local port to be configured
1876 INIT_DELAYED_WORK(&lport->retry_work, fc_lport_timeout); in fc_lport_config()
1877 mutex_init(&lport->lp_mutex); in fc_lport_config()
1890 * fc_lport_init() - Initialize the lport layer for a local port
1891 * @lport: The local port to initialize the exchange layer for
1897 fc_host = shost_to_fc_host(lport->host); in fc_lport_init()
1899 /* Set FDMI version to FDMI-2 specification*/ in fc_lport_init()
1900 fc_host->fdmi_version = FDMI_V2; in fc_lport_init()
1902 fc_host_port_type(lport->host) = FC_PORTTYPE_NPORT; in fc_lport_init()
1903 fc_host_node_name(lport->host) = lport->wwnn; in fc_lport_init()
1904 fc_host_port_name(lport->host) = lport->wwpn; in fc_lport_init()
1905 fc_host_supported_classes(lport->host) = FC_COS_CLASS3; in fc_lport_init()
1906 memset(fc_host_supported_fc4s(lport->host), 0, in fc_lport_init()
1907 sizeof(fc_host_supported_fc4s(lport->host))); in fc_lport_init()
1908 fc_host_supported_fc4s(lport->host)[2] = 1; in fc_lport_init()
1909 fc_host_supported_fc4s(lport->host)[7] = 1; in fc_lport_init()
1910 fc_host_num_discovered_ports(lport->host) = 4; in fc_lport_init()
1913 memset(fc_host_active_fc4s(lport->host), 0, in fc_lport_init()
1914 sizeof(fc_host_active_fc4s(lport->host))); in fc_lport_init()
1915 fc_host_active_fc4s(lport->host)[2] = 1; in fc_lport_init()
1916 fc_host_active_fc4s(lport->host)[7] = 1; in fc_lport_init()
1917 fc_host_maxframe_size(lport->host) = lport->mfs; in fc_lport_init()
1918 fc_host_supported_speeds(lport->host) = 0; in fc_lport_init()
1919 if (lport->link_supported_speeds & FC_PORTSPEED_1GBIT) in fc_lport_init()
1920 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_1GBIT; in fc_lport_init()
1921 if (lport->link_supported_speeds & FC_PORTSPEED_10GBIT) in fc_lport_init()
1922 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_10GBIT; in fc_lport_init()
1923 if (lport->link_supported_speeds & FC_PORTSPEED_40GBIT) in fc_lport_init()
1924 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_40GBIT; in fc_lport_init()
1925 if (lport->link_supported_speeds & FC_PORTSPEED_100GBIT) in fc_lport_init()
1926 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_100GBIT; in fc_lport_init()
1927 if (lport->link_supported_speeds & FC_PORTSPEED_25GBIT) in fc_lport_init()
1928 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_25GBIT; in fc_lport_init()
1929 if (lport->link_supported_speeds & FC_PORTSPEED_50GBIT) in fc_lport_init()
1930 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_50GBIT; in fc_lport_init()
1931 if (lport->link_supported_speeds & FC_PORTSPEED_100GBIT) in fc_lport_init()
1932 fc_host_supported_speeds(lport->host) |= FC_PORTSPEED_100GBIT; in fc_lport_init()
1936 fc_host_num_discovered_ports(lport->host) = DISCOVERED_PORTS; in fc_lport_init()
1937 fc_host_port_state(lport->host) = FC_PORTSTATE_ONLINE; in fc_lport_init()
1938 fc_host_max_ct_payload(lport->host) = MAX_CT_PAYLOAD; in fc_lport_init()
1939 fc_host_num_ports(lport->host) = NUMBER_OF_PORTS; in fc_lport_init()
1940 fc_host_bootbios_state(lport->host) = 0X00000000; in fc_lport_init()
1941 snprintf(fc_host_bootbios_version(lport->host), in fc_lport_init()
1949 * fc_lport_bsg_resp() - The common response handler for FC Passthrough requests
1958 struct bsg_job *job = info->job; in fc_lport_bsg_resp()
1959 struct fc_bsg_reply *bsg_reply = job->reply; in fc_lport_bsg_resp()
1960 struct fc_lport *lport = info->lport; in fc_lport_bsg_resp()
1966 bsg_reply->result = (PTR_ERR(fp) == -FC_EX_CLOSED) ? in fc_lport_bsg_resp()
1967 -ECONNABORTED : -ETIMEDOUT; in fc_lport_bsg_resp()
1968 job->reply_len = sizeof(uint32_t); in fc_lport_bsg_resp()
1969 bsg_job_done(job, bsg_reply->result, in fc_lport_bsg_resp()
1970 bsg_reply->reply_payload_rcv_len); in fc_lport_bsg_resp()
1975 mutex_lock(&lport->lp_mutex); in fc_lport_bsg_resp()
1977 len = fr_len(fp) - sizeof(*fh); in fc_lport_bsg_resp()
1980 if (fr_sof(fp) == FC_SOF_I3 && !ntohs(fh->fh_seq_cnt)) { in fc_lport_bsg_resp()
1982 unsigned short cmd = (info->rsp_code == FC_FS_ACC) ? in fc_lport_bsg_resp()
1983 ntohs(((struct fc_ct_hdr *)buf)->ct_cmd) : in fc_lport_bsg_resp()
1987 bsg_reply->reply_data.ctels_reply.status = in fc_lport_bsg_resp()
1988 (cmd == info->rsp_code) ? in fc_lport_bsg_resp()
1992 bsg_reply->reply_payload_rcv_len += in fc_lport_bsg_resp()
1993 fc_copy_buffer_to_sglist(buf, len, info->sg, &info->nents, in fc_lport_bsg_resp()
1994 &info->offset, NULL); in fc_lport_bsg_resp()
1997 (ntoh24(fh->fh_f_ctl) & (FC_FC_LAST_SEQ | FC_FC_END_SEQ)) == in fc_lport_bsg_resp()
1999 if (bsg_reply->reply_payload_rcv_len > in fc_lport_bsg_resp()
2000 job->reply_payload.payload_len) in fc_lport_bsg_resp()
2001 bsg_reply->reply_payload_rcv_len = in fc_lport_bsg_resp()
2002 job->reply_payload.payload_len; in fc_lport_bsg_resp()
2003 bsg_reply->result = 0; in fc_lport_bsg_resp()
2004 bsg_job_done(job, bsg_reply->result, in fc_lport_bsg_resp()
2005 bsg_reply->reply_payload_rcv_len); in fc_lport_bsg_resp()
2009 mutex_unlock(&lport->lp_mutex); in fc_lport_bsg_resp()
2013 * fc_lport_els_request() - Send ELS passthrough request
2015 * @lport: The local port sending the request
2016 * @did: The destination port id
2029 lockdep_assert_held(&lport->lp_mutex); in fc_lport_els_request()
2031 fp = fc_frame_alloc(lport, job->request_payload.payload_len); in fc_lport_els_request()
2033 return -ENOMEM; in fc_lport_els_request()
2035 len = job->request_payload.payload_len; in fc_lport_els_request()
2038 sg_copy_to_buffer(job->request_payload.sg_list, in fc_lport_els_request()
2039 job->request_payload.sg_cnt, in fc_lport_els_request()
2043 fh->fh_r_ctl = FC_RCTL_ELS_REQ; in fc_lport_els_request()
2044 hton24(fh->fh_d_id, did); in fc_lport_els_request()
2045 hton24(fh->fh_s_id, lport->port_id); in fc_lport_els_request()
2046 fh->fh_type = FC_TYPE_ELS; in fc_lport_els_request()
2047 hton24(fh->fh_f_ctl, FC_FCTL_REQ); in fc_lport_els_request()
2048 fh->fh_cs_ctl = 0; in fc_lport_els_request()
2049 fh->fh_df_ctl = 0; in fc_lport_els_request()
2050 fh->fh_parm_offset = 0; in fc_lport_els_request()
2055 return -ENOMEM; in fc_lport_els_request()
2058 info->job = job; in fc_lport_els_request()
2059 info->lport = lport; in fc_lport_els_request()
2060 info->rsp_code = ELS_LS_ACC; in fc_lport_els_request()
2061 info->nents = job->reply_payload.sg_cnt; in fc_lport_els_request()
2062 info->sg = job->reply_payload.sg_list; in fc_lport_els_request()
2067 return -ECOMM; in fc_lport_els_request()
2073 * fc_lport_ct_request() - Send CT Passthrough request
2075 * @lport: The local port sending the request
2076 * @did: The destination FC-ID
2088 lockdep_assert_held(&lport->lp_mutex); in fc_lport_ct_request()
2091 job->request_payload.payload_len); in fc_lport_ct_request()
2093 return -ENOMEM; in fc_lport_ct_request()
2095 len = job->request_payload.payload_len; in fc_lport_ct_request()
2098 sg_copy_to_buffer(job->request_payload.sg_list, in fc_lport_ct_request()
2099 job->request_payload.sg_cnt, in fc_lport_ct_request()
2103 fh->fh_r_ctl = FC_RCTL_DD_UNSOL_CTL; in fc_lport_ct_request()
2104 hton24(fh->fh_d_id, did); in fc_lport_ct_request()
2105 hton24(fh->fh_s_id, lport->port_id); in fc_lport_ct_request()
2106 fh->fh_type = FC_TYPE_CT; in fc_lport_ct_request()
2107 hton24(fh->fh_f_ctl, FC_FCTL_REQ); in fc_lport_ct_request()
2108 fh->fh_cs_ctl = 0; in fc_lport_ct_request()
2109 fh->fh_df_ctl = 0; in fc_lport_ct_request()
2110 fh->fh_parm_offset = 0; in fc_lport_ct_request()
2115 return -ENOMEM; in fc_lport_ct_request()
2118 info->job = job; in fc_lport_ct_request()
2119 info->lport = lport; in fc_lport_ct_request()
2120 info->rsp_code = FC_FS_ACC; in fc_lport_ct_request()
2121 info->nents = job->reply_payload.sg_cnt; in fc_lport_ct_request()
2122 info->sg = job->reply_payload.sg_list; in fc_lport_ct_request()
2127 return -ECOMM; in fc_lport_ct_request()
2133 * fc_lport_bsg_request() - The common entry point for sending
2139 struct fc_bsg_request *bsg_request = job->request; in fc_lport_bsg_request()
2140 struct fc_bsg_reply *bsg_reply = job->reply; in fc_lport_bsg_request()
2145 int rc = -EINVAL; in fc_lport_bsg_request()
2148 bsg_reply->reply_payload_rcv_len = 0; in fc_lport_bsg_request()
2150 mutex_lock(&lport->lp_mutex); in fc_lport_bsg_request()
2152 switch (bsg_request->msgcode) { in fc_lport_bsg_request()
2158 rdata = rport->dd_data; in fc_lport_bsg_request()
2159 rc = fc_lport_els_request(job, lport, rport->port_id, in fc_lport_bsg_request()
2160 rdata->e_d_tov); in fc_lport_bsg_request()
2168 rdata = rport->dd_data; in fc_lport_bsg_request()
2169 rc = fc_lport_ct_request(job, lport, rport->port_id, in fc_lport_bsg_request()
2170 rdata->e_d_tov); in fc_lport_bsg_request()
2174 did = ntoh24(bsg_request->rqst_data.h_ct.port_id); in fc_lport_bsg_request()
2176 rdata = lport->dns_rdata; in fc_lport_bsg_request()
2179 tov = rdata->e_d_tov; in fc_lport_bsg_request()
2184 tov = rdata->e_d_tov; in fc_lport_bsg_request()
2185 kref_put(&rdata->kref, fc_rport_destroy); in fc_lport_bsg_request()
2192 did = ntoh24(bsg_request->rqst_data.h_els.port_id); in fc_lport_bsg_request()
2193 rc = fc_lport_els_request(job, lport, did, lport->e_d_tov); in fc_lport_bsg_request()
2197 mutex_unlock(&lport->lp_mutex); in fc_lport_bsg_request()