Skip to content

Commit e3ba04c

Browse files
jsmart-ghmartinkpetersen
authored andcommitted
scsi: lpfc: Fix Fabric hostname registration if system hostname changes
There are reports of multiple ports on the same system displaying different hostnames in fabric FDMI displays. Currently, the driver registers the hostname at initialization and obtains the hostname via init_utsname()->nodename queried at the time the FC link comes up. Unfortunately, if the machine hostname is updated after initialization, such as via DHCP or admin command, the value registered initially will be incorrect. Fix by having the driver save the hostname that was registered with FDMI. The driver then runs a heartbeat action that will check the hostname. If the name changes, reregister the FMDI data. The hostname is used in RSNN_NN, FDMI RPA and FDMI RHBA. Link: https://lore.kernel.org/r/20191218235808.31922-5-jsmart2021@gmail.com Signed-off-by: Dick Kennedy <dick.kennedy@broadcom.com> Signed-off-by: James Smart <jsmart2021@gmail.com> Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
1 parent f3d0a8a commit e3ba04c

File tree

5 files changed

+46
-13
lines changed

5 files changed

+46
-13
lines changed

drivers/scsi/lpfc/lpfc.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1223,6 +1223,8 @@ struct lpfc_hba {
12231223
#define LPFC_POLL_HB 1 /* slowpath heartbeat */
12241224
#define LPFC_POLL_FASTPATH 0 /* called from fastpath */
12251225
#define LPFC_POLL_SLOWPATH 1 /* called from slowpath */
1226+
1227+
char os_host_name[MAXHOSTNAMELEN];
12261228
};
12271229

12281230
static inline struct Scsi_Host *

drivers/scsi/lpfc/lpfc_crtn.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,7 +180,7 @@ int lpfc_issue_gidft(struct lpfc_vport *vport);
180180
int lpfc_get_gidft_type(struct lpfc_vport *vport, struct lpfc_iocbq *iocbq);
181181
int lpfc_ns_cmd(struct lpfc_vport *, int, uint8_t, uint32_t);
182182
int lpfc_fdmi_cmd(struct lpfc_vport *, struct lpfc_nodelist *, int, uint32_t);
183-
void lpfc_fdmi_num_disc_check(struct lpfc_vport *);
183+
void lpfc_fdmi_change_check(struct lpfc_vport *vport);
184184
void lpfc_delayed_disc_tmo(struct timer_list *);
185185
void lpfc_delayed_disc_timeout_handler(struct lpfc_vport *);
186186

drivers/scsi/lpfc/lpfc_ct.c

Lines changed: 37 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1511,7 +1511,7 @@ lpfc_vport_symbolic_node_name(struct lpfc_vport *vport, char *symbol,
15111511
if (strlcat(symbol, tmp, size) >= size)
15121512
goto buffer_done;
15131513

1514-
scnprintf(tmp, sizeof(tmp), " HN:%s", init_utsname()->nodename);
1514+
scnprintf(tmp, sizeof(tmp), " HN:%s", vport->phba->os_host_name);
15151515
if (strlcat(symbol, tmp, size) >= size)
15161516
goto buffer_done;
15171517

@@ -2000,14 +2000,16 @@ lpfc_cmpl_ct_disc_fdmi(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
20002000

20012001

20022002
/**
2003-
* lpfc_fdmi_num_disc_check - Check how many mapped NPorts we are connected to
2003+
* lpfc_fdmi_change_check - Check for changed FDMI parameters
20042004
* @vport: pointer to a host virtual N_Port data structure.
20052005
*
2006-
* Called from hbeat timeout routine to check if the number of discovered
2007-
* ports has changed. If so, re-register thar port Attribute.
2006+
* Check how many mapped NPorts we are connected to
2007+
* Check if our hostname changed
2008+
* Called from hbeat timeout routine to check if any FDMI parameters
2009+
* changed. If so, re-register those Attributes.
20082010
*/
20092011
void
2010-
lpfc_fdmi_num_disc_check(struct lpfc_vport *vport)
2012+
lpfc_fdmi_change_check(struct lpfc_vport *vport)
20112013
{
20122014
struct lpfc_hba *phba = vport->phba;
20132015
struct lpfc_nodelist *ndlp;
@@ -2020,17 +2022,41 @@ lpfc_fdmi_num_disc_check(struct lpfc_vport *vport)
20202022
if (!(vport->fc_flag & FC_FABRIC))
20212023
return;
20222024

2025+
ndlp = lpfc_findnode_did(vport, FDMI_DID);
2026+
if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
2027+
return;
2028+
2029+
/* Check if system hostname changed */
2030+
if (strcmp(phba->os_host_name, init_utsname()->nodename)) {
2031+
memset(phba->os_host_name, 0, sizeof(phba->os_host_name));
2032+
scnprintf(phba->os_host_name, sizeof(phba->os_host_name), "%s",
2033+
init_utsname()->nodename);
2034+
lpfc_ns_cmd(vport, SLI_CTNS_RSNN_NN, 0, 0);
2035+
2036+
/* Since this effects multiple HBA and PORT attributes, we need
2037+
* de-register and go thru the whole FDMI registration cycle.
2038+
* DHBA -> DPRT -> RHBA -> RPA (physical port)
2039+
* DPRT -> RPRT (vports)
2040+
*/
2041+
if (vport->port_type == LPFC_PHYSICAL_PORT)
2042+
lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_DHBA, 0);
2043+
else
2044+
lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_DPRT, 0);
2045+
2046+
/* Since this code path registers all the port attributes
2047+
* we can just return without further checking.
2048+
*/
2049+
return;
2050+
}
2051+
20232052
if (!(vport->fdmi_port_mask & LPFC_FDMI_PORT_ATTR_num_disc))
20242053
return;
20252054

2055+
/* Check if the number of mapped NPorts changed */
20262056
cnt = lpfc_find_map_node(vport);
20272057
if (cnt == vport->fdmi_num_disc)
20282058
return;
20292059

2030-
ndlp = lpfc_findnode_did(vport, FDMI_DID);
2031-
if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
2032-
return;
2033-
20342060
if (vport->port_type == LPFC_PHYSICAL_PORT) {
20352061
lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_RPA,
20362062
LPFC_FDMI_PORT_ATTR_num_disc);
@@ -2618,8 +2644,8 @@ lpfc_fdmi_port_attr_host_name(struct lpfc_vport *vport,
26182644
ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
26192645
memset(ae, 0, 256);
26202646

2621-
snprintf(ae->un.AttrString, sizeof(ae->un.AttrString), "%s",
2622-
init_utsname()->nodename);
2647+
scnprintf(ae->un.AttrString, sizeof(ae->un.AttrString), "%s",
2648+
vport->phba->os_host_name);
26232649

26242650
len = strnlen(ae->un.AttrString, sizeof(ae->un.AttrString));
26252651
len += (len & 3) ? (4 - (len & 3)) : 4;

drivers/scsi/lpfc/lpfc_hbadisc.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
#include <linux/kthread.h>
2929
#include <linux/interrupt.h>
3030
#include <linux/lockdep.h>
31+
#include <linux/utsname.h>
3132

3233
#include <scsi/scsi.h>
3334
#include <scsi/scsi_device.h>
@@ -3315,6 +3316,10 @@ lpfc_mbx_process_link_up(struct lpfc_hba *phba, struct lpfc_mbx_read_top *la)
33153316
lpfc_sli4_clear_fcf_rr_bmask(phba);
33163317
}
33173318

3319+
/* Prepare for LINK up registrations */
3320+
memset(phba->os_host_name, 0, sizeof(phba->os_host_name));
3321+
scnprintf(phba->os_host_name, sizeof(phba->os_host_name), "%s",
3322+
init_utsname()->nodename);
33183323
return;
33193324
out:
33203325
lpfc_vport_set_state(vport, FC_VPORT_FAILED);

drivers/scsi/lpfc/lpfc_init.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1362,7 +1362,7 @@ lpfc_hb_timeout_handler(struct lpfc_hba *phba)
13621362
if (vports != NULL)
13631363
for (i = 0; i <= phba->max_vports && vports[i] != NULL; i++) {
13641364
lpfc_rcv_seq_check_edtov(vports[i]);
1365-
lpfc_fdmi_num_disc_check(vports[i]);
1365+
lpfc_fdmi_change_check(vports[i]);
13661366
}
13671367
lpfc_destroy_vport_work_array(phba, vports);
13681368

0 commit comments

Comments
 (0)