brintos

brintos / linux-shallow public Read only

0
0
Text · 35.0 KiB · 52303e8 Raw
1349 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*3 * Copyright (c) 2005-2014 Brocade Communications Systems, Inc.4 * Copyright (c) 2014- QLogic Corporation.5 * All rights reserved6 * www.qlogic.com7 *8 * Linux driver for QLogic BR-series Fibre Channel Host Bus Adapter.9 */10/*11 * fcbuild.c - FC link service frame building and parsing routines12 */13 14#include "bfad_drv.h"15#include "bfa_fcbuild.h"16 17/*18 * static build functions19 */20static void     fc_els_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id,21				 __be16 ox_id);22static void     fc_bls_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id,23				 __be16 ox_id);24static struct fchs_s fc_els_req_tmpl;25static struct fchs_s fc_els_rsp_tmpl;26static struct fchs_s fc_bls_req_tmpl;27static struct fchs_s fc_bls_rsp_tmpl;28static struct fc_ba_acc_s ba_acc_tmpl;29static struct fc_logi_s plogi_tmpl;30static struct fc_prli_s prli_tmpl;31static struct fc_rrq_s rrq_tmpl;32static struct fchs_s fcp_fchs_tmpl;33 34void35fcbuild_init(void)36{37	/*38	 * fc_els_req_tmpl39	 */40	fc_els_req_tmpl.routing = FC_RTG_EXT_LINK;41	fc_els_req_tmpl.cat_info = FC_CAT_LD_REQUEST;42	fc_els_req_tmpl.type = FC_TYPE_ELS;43	fc_els_req_tmpl.f_ctl =44		bfa_hton3b(FCTL_SEQ_INI | FCTL_FS_EXCH | FCTL_END_SEQ |45			      FCTL_SI_XFER);46	fc_els_req_tmpl.rx_id = FC_RXID_ANY;47 48	/*49	 * fc_els_rsp_tmpl50	 */51	fc_els_rsp_tmpl.routing = FC_RTG_EXT_LINK;52	fc_els_rsp_tmpl.cat_info = FC_CAT_LD_REPLY;53	fc_els_rsp_tmpl.type = FC_TYPE_ELS;54	fc_els_rsp_tmpl.f_ctl =55		bfa_hton3b(FCTL_EC_RESP | FCTL_SEQ_INI | FCTL_LS_EXCH |56			      FCTL_END_SEQ | FCTL_SI_XFER);57	fc_els_rsp_tmpl.rx_id = FC_RXID_ANY;58 59	/*60	 * fc_bls_req_tmpl61	 */62	fc_bls_req_tmpl.routing = FC_RTG_BASIC_LINK;63	fc_bls_req_tmpl.type = FC_TYPE_BLS;64	fc_bls_req_tmpl.f_ctl = bfa_hton3b(FCTL_END_SEQ | FCTL_SI_XFER);65	fc_bls_req_tmpl.rx_id = FC_RXID_ANY;66 67	/*68	 * fc_bls_rsp_tmpl69	 */70	fc_bls_rsp_tmpl.routing = FC_RTG_BASIC_LINK;71	fc_bls_rsp_tmpl.cat_info = FC_CAT_BA_ACC;72	fc_bls_rsp_tmpl.type = FC_TYPE_BLS;73	fc_bls_rsp_tmpl.f_ctl =74		bfa_hton3b(FCTL_EC_RESP | FCTL_SEQ_INI | FCTL_LS_EXCH |75			      FCTL_END_SEQ | FCTL_SI_XFER);76	fc_bls_rsp_tmpl.rx_id = FC_RXID_ANY;77 78	/*79	 * ba_acc_tmpl80	 */81	ba_acc_tmpl.seq_id_valid = 0;82	ba_acc_tmpl.low_seq_cnt = 0;83	ba_acc_tmpl.high_seq_cnt = 0xFFFF;84 85	/*86	 * plogi_tmpl87	 */88	plogi_tmpl.csp.verhi = FC_PH_VER_PH_3;89	plogi_tmpl.csp.verlo = FC_PH_VER_4_3;90	plogi_tmpl.csp.ciro = 0x1;91	plogi_tmpl.csp.cisc = 0x0;92	plogi_tmpl.csp.altbbcred = 0x0;93	plogi_tmpl.csp.conseq = cpu_to_be16(0x00FF);94	plogi_tmpl.csp.ro_bitmap = cpu_to_be16(0x0002);95	plogi_tmpl.csp.e_d_tov = cpu_to_be32(2000);96 97	plogi_tmpl.class3.class_valid = 1;98	plogi_tmpl.class3.sequential = 1;99	plogi_tmpl.class3.conseq = 0xFF;100	plogi_tmpl.class3.ospx = 1;101 102	/*103	 * prli_tmpl104	 */105	prli_tmpl.command = FC_ELS_PRLI;106	prli_tmpl.pglen = 0x10;107	prli_tmpl.pagebytes = cpu_to_be16(0x0014);108	prli_tmpl.parampage.type = FC_TYPE_FCP;109	prli_tmpl.parampage.imagepair = 1;110	prli_tmpl.parampage.servparams.rxrdisab = 1;111 112	/*113	 * rrq_tmpl114	 */115	rrq_tmpl.els_cmd.els_code = FC_ELS_RRQ;116 117	/*118	 * fcp_struct fchs_s mpl119	 */120	fcp_fchs_tmpl.routing = FC_RTG_FC4_DEV_DATA;121	fcp_fchs_tmpl.cat_info = FC_CAT_UNSOLICIT_CMD;122	fcp_fchs_tmpl.type = FC_TYPE_FCP;123	fcp_fchs_tmpl.f_ctl =124		bfa_hton3b(FCTL_FS_EXCH | FCTL_END_SEQ | FCTL_SI_XFER);125	fcp_fchs_tmpl.seq_id = 1;126	fcp_fchs_tmpl.rx_id = FC_RXID_ANY;127}128 129static void130fc_gs_fchdr_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u32 ox_id)131{132	memset(fchs, 0, sizeof(struct fchs_s));133 134	fchs->routing = FC_RTG_FC4_DEV_DATA;135	fchs->cat_info = FC_CAT_UNSOLICIT_CTRL;136	fchs->type = FC_TYPE_SERVICES;137	fchs->f_ctl =138		bfa_hton3b(FCTL_SEQ_INI | FCTL_FS_EXCH | FCTL_END_SEQ |139			      FCTL_SI_XFER);140	fchs->rx_id = FC_RXID_ANY;141	fchs->d_id = (d_id);142	fchs->s_id = (s_id);143	fchs->ox_id = cpu_to_be16(ox_id);144 145	/*146	 * @todo no need to set ox_id for request147	 *       no need to set rx_id for response148	 */149}150 151static void152fc_gsresp_fchdr_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id)153{154	memset(fchs, 0, sizeof(struct fchs_s));155 156	fchs->routing = FC_RTG_FC4_DEV_DATA;157	fchs->cat_info = FC_CAT_SOLICIT_CTRL;158	fchs->type = FC_TYPE_SERVICES;159	fchs->f_ctl =160		bfa_hton3b(FCTL_EC_RESP | FCTL_SEQ_INI | FCTL_LS_EXCH |161			   FCTL_END_SEQ | FCTL_SI_XFER);162	fchs->d_id = d_id;163	fchs->s_id = s_id;164	fchs->ox_id = ox_id;165}166 167void168fc_els_req_build(struct fchs_s *fchs, u32 d_id, u32 s_id, __be16 ox_id)169{170	memcpy(fchs, &fc_els_req_tmpl, sizeof(struct fchs_s));171	fchs->d_id = (d_id);172	fchs->s_id = (s_id);173	fchs->ox_id = cpu_to_be16(ox_id);174}175 176static void177fc_els_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, __be16 ox_id)178{179	memcpy(fchs, &fc_els_rsp_tmpl, sizeof(struct fchs_s));180	fchs->d_id = d_id;181	fchs->s_id = s_id;182	fchs->ox_id = ox_id;183}184 185static void186fc_bls_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, __be16 ox_id)187{188	memcpy(fchs, &fc_bls_rsp_tmpl, sizeof(struct fchs_s));189	fchs->d_id = d_id;190	fchs->s_id = s_id;191	fchs->ox_id = ox_id;192}193 194static          u16195fc_plogi_x_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,196		 __be16 ox_id, wwn_t port_name, wwn_t node_name,197		 u16 pdu_size, u16 bb_cr, u8 els_code)198{199	struct fc_logi_s *plogi = (struct fc_logi_s *) (pld);200 201	memcpy(plogi, &plogi_tmpl, sizeof(struct fc_logi_s));202 203	/* For FC AL bb_cr is 0 and altbbcred is 1 */204	if (!bb_cr)205		plogi->csp.altbbcred = 1;206 207	plogi->els_cmd.els_code = els_code;208	if (els_code == FC_ELS_PLOGI)209		fc_els_req_build(fchs, d_id, s_id, ox_id);210	else211		fc_els_rsp_build(fchs, d_id, s_id, ox_id);212 213	plogi->csp.rxsz = plogi->class3.rxsz = cpu_to_be16(pdu_size);214	plogi->csp.bbcred  = cpu_to_be16(bb_cr);215 216	memcpy(&plogi->port_name, &port_name, sizeof(wwn_t));217	memcpy(&plogi->node_name, &node_name, sizeof(wwn_t));218 219	return sizeof(struct fc_logi_s);220}221 222u16223fc_flogi_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id,224		u16 ox_id, wwn_t port_name, wwn_t node_name, u16 pdu_size,225	       u8 set_npiv, u8 set_auth, u16 local_bb_credits)226{227	u32        d_id = bfa_hton3b(FC_FABRIC_PORT);228	__be32	*vvl_info;229 230	memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s));231 232	flogi->els_cmd.els_code = FC_ELS_FLOGI;233	fc_els_req_build(fchs, d_id, s_id, ox_id);234 235	flogi->csp.rxsz = flogi->class3.rxsz = cpu_to_be16(pdu_size);236	flogi->port_name = port_name;237	flogi->node_name = node_name;238 239	/*240	 * Set the NPIV Capability Bit ( word 1, bit 31) of Common241	 * Service Parameters.242	 */243	flogi->csp.ciro = set_npiv;244 245	/* set AUTH capability */246	flogi->csp.security = set_auth;247 248	flogi->csp.bbcred = cpu_to_be16(local_bb_credits);249 250	/* Set brcd token in VVL */251	vvl_info = (u32 *)&flogi->vvl[0];252 253	/* set the flag to indicate the presence of VVL */254	flogi->csp.npiv_supp    = 1; /* @todo. field name is not correct */255	vvl_info[0]	= cpu_to_be32(FLOGI_VVL_BRCD);256 257	return sizeof(struct fc_logi_s);258}259 260u16261fc_flogi_acc_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id,262		   __be16 ox_id, wwn_t port_name, wwn_t node_name,263		   u16 pdu_size, u16 local_bb_credits, u8 bb_scn)264{265	u32        d_id = 0;266	u16	   bbscn_rxsz = (bb_scn << 12) | pdu_size;267 268	memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s));269	fc_els_rsp_build(fchs, d_id, s_id, ox_id);270 271	flogi->els_cmd.els_code = FC_ELS_ACC;272	flogi->class3.rxsz = cpu_to_be16(pdu_size);273	flogi->csp.rxsz  = cpu_to_be16(bbscn_rxsz);	/* bb_scn/rxsz */274	flogi->port_name = port_name;275	flogi->node_name = node_name;276 277	flogi->csp.bbcred = cpu_to_be16(local_bb_credits);278 279	return sizeof(struct fc_logi_s);280}281 282u16283fc_fdisc_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id,284		u16 ox_id, wwn_t port_name, wwn_t node_name, u16 pdu_size)285{286	u32        d_id = bfa_hton3b(FC_FABRIC_PORT);287 288	memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s));289 290	flogi->els_cmd.els_code = FC_ELS_FDISC;291	fc_els_req_build(fchs, d_id, s_id, ox_id);292 293	flogi->csp.rxsz = flogi->class3.rxsz = cpu_to_be16(pdu_size);294	flogi->port_name = port_name;295	flogi->node_name = node_name;296 297	return sizeof(struct fc_logi_s);298}299 300u16301fc_plogi_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,302	       u16 ox_id, wwn_t port_name, wwn_t node_name,303	       u16 pdu_size, u16 bb_cr)304{305	return fc_plogi_x_build(fchs, pld, d_id, s_id, ox_id, port_name,306				node_name, pdu_size, bb_cr, FC_ELS_PLOGI);307}308 309u16310fc_plogi_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,311		   u16 ox_id, wwn_t port_name, wwn_t node_name,312		   u16 pdu_size, u16 bb_cr)313{314	return fc_plogi_x_build(fchs, pld, d_id, s_id, ox_id, port_name,315				node_name, pdu_size, bb_cr, FC_ELS_ACC);316}317 318enum fc_parse_status319fc_plogi_rsp_parse(struct fchs_s *fchs, int len, wwn_t port_name)320{321	struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1);322	struct fc_logi_s *plogi;323	struct fc_ls_rjt_s *ls_rjt;324 325	switch (els_cmd->els_code) {326	case FC_ELS_LS_RJT:327		ls_rjt = (struct fc_ls_rjt_s *) (fchs + 1);328		if (ls_rjt->reason_code == FC_LS_RJT_RSN_LOGICAL_BUSY)329			return FC_PARSE_BUSY;330		else331			return FC_PARSE_FAILURE;332	case FC_ELS_ACC:333		plogi = (struct fc_logi_s *) (fchs + 1);334		if (len < sizeof(struct fc_logi_s))335			return FC_PARSE_FAILURE;336 337		if (!wwn_is_equal(plogi->port_name, port_name))338			return FC_PARSE_FAILURE;339 340		if (!plogi->class3.class_valid)341			return FC_PARSE_FAILURE;342 343		if (be16_to_cpu(plogi->class3.rxsz) < (FC_MIN_PDUSZ))344			return FC_PARSE_FAILURE;345 346		return FC_PARSE_OK;347	default:348		return FC_PARSE_FAILURE;349	}350}351 352enum fc_parse_status353fc_plogi_parse(struct fchs_s *fchs)354{355	struct fc_logi_s *plogi = (struct fc_logi_s *) (fchs + 1);356 357	if (plogi->class3.class_valid != 1)358		return FC_PARSE_FAILURE;359 360	if ((be16_to_cpu(plogi->class3.rxsz) < FC_MIN_PDUSZ)361	    || (be16_to_cpu(plogi->class3.rxsz) > FC_MAX_PDUSZ)362	    || (plogi->class3.rxsz == 0))363		return FC_PARSE_FAILURE;364 365	return FC_PARSE_OK;366}367 368u16369fc_prli_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,370	      u16 ox_id)371{372	struct fc_prli_s *prli = (struct fc_prli_s *) (pld);373 374	fc_els_req_build(fchs, d_id, s_id, ox_id);375	memcpy(prli, &prli_tmpl, sizeof(struct fc_prli_s));376 377	prli->command = FC_ELS_PRLI;378	prli->parampage.servparams.initiator     = 1;379	prli->parampage.servparams.retry         = 1;380	prli->parampage.servparams.rec_support   = 1;381	prli->parampage.servparams.task_retry_id = 0;382	prli->parampage.servparams.confirm       = 1;383 384	return sizeof(struct fc_prli_s);385}386 387u16388fc_prli_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,389		  __be16 ox_id, enum bfa_lport_role role)390{391	struct fc_prli_s *prli = (struct fc_prli_s *) (pld);392 393	fc_els_rsp_build(fchs, d_id, s_id, ox_id);394	memcpy(prli, &prli_tmpl, sizeof(struct fc_prli_s));395 396	prli->command = FC_ELS_ACC;397 398	prli->parampage.servparams.initiator = 1;399 400	prli->parampage.rspcode = FC_PRLI_ACC_XQTD;401 402	return sizeof(struct fc_prli_s);403}404 405enum fc_parse_status406fc_prli_rsp_parse(struct fc_prli_s *prli, int len)407{408	if (len < sizeof(struct fc_prli_s))409		return FC_PARSE_FAILURE;410 411	if (prli->command != FC_ELS_ACC)412		return FC_PARSE_FAILURE;413 414	if ((prli->parampage.rspcode != FC_PRLI_ACC_XQTD)415	    && (prli->parampage.rspcode != FC_PRLI_ACC_PREDEF_IMG))416		return FC_PARSE_FAILURE;417 418	if (prli->parampage.servparams.target != 1)419		return FC_PARSE_FAILURE;420 421	return FC_PARSE_OK;422}423 424enum fc_parse_status425fc_prli_parse(struct fc_prli_s *prli)426{427	if (prli->parampage.type != FC_TYPE_FCP)428		return FC_PARSE_FAILURE;429 430	if (!prli->parampage.imagepair)431		return FC_PARSE_FAILURE;432 433	if (!prli->parampage.servparams.initiator)434		return FC_PARSE_FAILURE;435 436	return FC_PARSE_OK;437}438 439u16440fc_logo_build(struct fchs_s *fchs, struct fc_logo_s *logo, u32 d_id, u32 s_id,441	      u16 ox_id, wwn_t port_name)442{443	fc_els_req_build(fchs, d_id, s_id, ox_id);444 445	memset(logo, '\0', sizeof(struct fc_logo_s));446	logo->els_cmd.els_code = FC_ELS_LOGO;447	logo->nport_id = (s_id);448	logo->orig_port_name = port_name;449 450	return sizeof(struct fc_logo_s);451}452 453static u16454fc_adisc_x_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id,455		 u32 s_id, __be16 ox_id, wwn_t port_name,456		 wwn_t node_name, u8 els_code)457{458	memset(adisc, '\0', sizeof(struct fc_adisc_s));459 460	adisc->els_cmd.els_code = els_code;461 462	if (els_code == FC_ELS_ADISC)463		fc_els_req_build(fchs, d_id, s_id, ox_id);464	else465		fc_els_rsp_build(fchs, d_id, s_id, ox_id);466 467	adisc->orig_HA = 0;468	adisc->orig_port_name = port_name;469	adisc->orig_node_name = node_name;470	adisc->nport_id = (s_id);471 472	return sizeof(struct fc_adisc_s);473}474 475u16476fc_adisc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id,477		u32 s_id, __be16 ox_id, wwn_t port_name, wwn_t node_name)478{479	return fc_adisc_x_build(fchs, adisc, d_id, s_id, ox_id, port_name,480				node_name, FC_ELS_ADISC);481}482 483u16484fc_adisc_acc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id,485		   u32 s_id, __be16 ox_id, wwn_t port_name,486		   wwn_t node_name)487{488	return fc_adisc_x_build(fchs, adisc, d_id, s_id, ox_id, port_name,489				node_name, FC_ELS_ACC);490}491 492enum fc_parse_status493fc_adisc_rsp_parse(struct fc_adisc_s *adisc, int len, wwn_t port_name,494				 wwn_t node_name)495{496 497	if (len < sizeof(struct fc_adisc_s))498		return FC_PARSE_FAILURE;499 500	if (adisc->els_cmd.els_code != FC_ELS_ACC)501		return FC_PARSE_FAILURE;502 503	if (!wwn_is_equal(adisc->orig_port_name, port_name))504		return FC_PARSE_FAILURE;505 506	return FC_PARSE_OK;507}508 509enum fc_parse_status510fc_adisc_parse(struct fchs_s *fchs, void *pld, u32 host_dap, wwn_t node_name,511	       wwn_t port_name)512{513	struct fc_adisc_s *adisc = (struct fc_adisc_s *) pld;514 515	if (adisc->els_cmd.els_code != FC_ELS_ACC)516		return FC_PARSE_FAILURE;517 518	if ((adisc->nport_id == (host_dap))519	    && wwn_is_equal(adisc->orig_port_name, port_name)520	    && wwn_is_equal(adisc->orig_node_name, node_name))521		return FC_PARSE_OK;522 523	return FC_PARSE_FAILURE;524}525 526enum fc_parse_status527fc_pdisc_parse(struct fchs_s *fchs, wwn_t node_name, wwn_t port_name)528{529	struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1);530 531	if (pdisc->class3.class_valid != 1)532		return FC_PARSE_FAILURE;533 534	if ((be16_to_cpu(pdisc->class3.rxsz) <535		(FC_MIN_PDUSZ - sizeof(struct fchs_s)))536	    || (pdisc->class3.rxsz == 0))537		return FC_PARSE_FAILURE;538 539	if (!wwn_is_equal(pdisc->port_name, port_name))540		return FC_PARSE_FAILURE;541 542	if (!wwn_is_equal(pdisc->node_name, node_name))543		return FC_PARSE_FAILURE;544 545	return FC_PARSE_OK;546}547 548u16549fc_abts_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id)550{551	memcpy(fchs, &fc_bls_req_tmpl, sizeof(struct fchs_s));552	fchs->cat_info = FC_CAT_ABTS;553	fchs->d_id = (d_id);554	fchs->s_id = (s_id);555	fchs->ox_id = cpu_to_be16(ox_id);556 557	return sizeof(struct fchs_s);558}559 560enum fc_parse_status561fc_abts_rsp_parse(struct fchs_s *fchs, int len)562{563	if ((fchs->cat_info == FC_CAT_BA_ACC)564	    || (fchs->cat_info == FC_CAT_BA_RJT))565		return FC_PARSE_OK;566 567	return FC_PARSE_FAILURE;568}569 570u16571fc_rrq_build(struct fchs_s *fchs, struct fc_rrq_s *rrq, u32 d_id, u32 s_id,572	     u16 ox_id, u16 rrq_oxid)573{574	fc_els_req_build(fchs, d_id, s_id, ox_id);575 576	/*577	 * build rrq payload578	 */579	memcpy(rrq, &rrq_tmpl, sizeof(struct fc_rrq_s));580	rrq->s_id = (s_id);581	rrq->ox_id = cpu_to_be16(rrq_oxid);582	rrq->rx_id = FC_RXID_ANY;583 584	return sizeof(struct fc_rrq_s);585}586 587u16588fc_logo_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id,589		  __be16 ox_id)590{591	struct fc_els_cmd_s *acc = pld;592 593	fc_els_rsp_build(fchs, d_id, s_id, ox_id);594 595	memset(acc, 0, sizeof(struct fc_els_cmd_s));596	acc->els_code = FC_ELS_ACC;597 598	return sizeof(struct fc_els_cmd_s);599}600 601u16602fc_ls_rjt_build(struct fchs_s *fchs, struct fc_ls_rjt_s *ls_rjt, u32 d_id,603		u32 s_id, __be16 ox_id, u8 reason_code,604		u8 reason_code_expl)605{606	fc_els_rsp_build(fchs, d_id, s_id, ox_id);607	memset(ls_rjt, 0, sizeof(struct fc_ls_rjt_s));608 609	ls_rjt->els_cmd.els_code = FC_ELS_LS_RJT;610	ls_rjt->reason_code = reason_code;611	ls_rjt->reason_code_expl = reason_code_expl;612	ls_rjt->vendor_unique = 0x00;613 614	return sizeof(struct fc_ls_rjt_s);615}616 617u16618fc_ba_acc_build(struct fchs_s *fchs, struct fc_ba_acc_s *ba_acc, u32 d_id,619		u32 s_id, __be16 ox_id, u16 rx_id)620{621	fc_bls_rsp_build(fchs, d_id, s_id, ox_id);622 623	memcpy(ba_acc, &ba_acc_tmpl, sizeof(struct fc_ba_acc_s));624 625	fchs->rx_id = rx_id;626 627	ba_acc->ox_id = fchs->ox_id;628	ba_acc->rx_id = fchs->rx_id;629 630	return sizeof(struct fc_ba_acc_s);631}632 633u16634fc_ls_acc_build(struct fchs_s *fchs, struct fc_els_cmd_s *els_cmd, u32 d_id,635		u32 s_id, __be16 ox_id)636{637	fc_els_rsp_build(fchs, d_id, s_id, ox_id);638	memset(els_cmd, 0, sizeof(struct fc_els_cmd_s));639	els_cmd->els_code = FC_ELS_ACC;640 641	return sizeof(struct fc_els_cmd_s);642}643 644int645fc_logout_params_pages(struct fchs_s *fc_frame, u8 els_code)646{647	int             num_pages = 0;648	struct fc_prlo_s *prlo;649	struct fc_tprlo_s *tprlo;650 651	if (els_code == FC_ELS_PRLO) {652		prlo = (struct fc_prlo_s *) (fc_frame + 1);653		num_pages = (be16_to_cpu(prlo->payload_len) - 4) / 16;654	} else {655		tprlo = (struct fc_tprlo_s *) (fc_frame + 1);656		num_pages = (be16_to_cpu(tprlo->payload_len) - 4) / 16;657	}658	return num_pages;659}660 661u16662fc_tprlo_acc_build(struct fchs_s *fchs, struct fc_tprlo_acc_s *tprlo_acc,663		u32 d_id, u32 s_id, __be16 ox_id, int num_pages)664{665	int             page;666 667	fc_els_rsp_build(fchs, d_id, s_id, ox_id);668 669	memset(tprlo_acc, 0, (num_pages * 16) + 4);670	tprlo_acc->command = FC_ELS_ACC;671 672	tprlo_acc->page_len = 0x10;673	tprlo_acc->payload_len = cpu_to_be16((num_pages * 16) + 4);674 675	for (page = 0; page < num_pages; page++) {676		tprlo_acc->tprlo_acc_params[page].opa_valid = 0;677		tprlo_acc->tprlo_acc_params[page].rpa_valid = 0;678		tprlo_acc->tprlo_acc_params[page].fc4type_csp = FC_TYPE_FCP;679		tprlo_acc->tprlo_acc_params[page].orig_process_assc = 0;680		tprlo_acc->tprlo_acc_params[page].resp_process_assc = 0;681	}682	return be16_to_cpu(tprlo_acc->payload_len);683}684 685u16686fc_prlo_acc_build(struct fchs_s *fchs, struct fc_prlo_acc_s *prlo_acc, u32 d_id,687		  u32 s_id, __be16 ox_id, int num_pages)688{689	int             page;690 691	fc_els_rsp_build(fchs, d_id, s_id, ox_id);692 693	memset(prlo_acc, 0, (num_pages * 16) + 4);694	prlo_acc->command = FC_ELS_ACC;695	prlo_acc->page_len = 0x10;696	prlo_acc->payload_len = cpu_to_be16((num_pages * 16) + 4);697 698	for (page = 0; page < num_pages; page++) {699		prlo_acc->prlo_acc_params[page].opa_valid = 0;700		prlo_acc->prlo_acc_params[page].rpa_valid = 0;701		prlo_acc->prlo_acc_params[page].fc4type_csp = FC_TYPE_FCP;702		prlo_acc->prlo_acc_params[page].orig_process_assc = 0;703		prlo_acc->prlo_acc_params[page].resp_process_assc = 0;704	}705 706	return be16_to_cpu(prlo_acc->payload_len);707}708 709u16710fc_rnid_build(struct fchs_s *fchs, struct fc_rnid_cmd_s *rnid, u32 d_id,711		u32 s_id, u16 ox_id, u32 data_format)712{713	fc_els_req_build(fchs, d_id, s_id, ox_id);714 715	memset(rnid, 0, sizeof(struct fc_rnid_cmd_s));716 717	rnid->els_cmd.els_code = FC_ELS_RNID;718	rnid->node_id_data_format = data_format;719 720	return sizeof(struct fc_rnid_cmd_s);721}722 723u16724fc_rnid_acc_build(struct fchs_s *fchs, struct fc_rnid_acc_s *rnid_acc, u32 d_id,725		  u32 s_id, __be16 ox_id, u32 data_format,726		  struct fc_rnid_common_id_data_s *common_id_data,727		  struct fc_rnid_general_topology_data_s *gen_topo_data)728{729	memset(rnid_acc, 0, sizeof(struct fc_rnid_acc_s));730 731	fc_els_rsp_build(fchs, d_id, s_id, ox_id);732 733	rnid_acc->els_cmd.els_code = FC_ELS_ACC;734	rnid_acc->node_id_data_format = data_format;735	rnid_acc->common_id_data_length =736			sizeof(struct fc_rnid_common_id_data_s);737	rnid_acc->common_id_data = *common_id_data;738 739	if (data_format == RNID_NODEID_DATA_FORMAT_DISCOVERY) {740		rnid_acc->specific_id_data_length =741			sizeof(struct fc_rnid_general_topology_data_s);742		rnid_acc->gen_topology_data = *gen_topo_data;743		return sizeof(struct fc_rnid_acc_s);744	} else {745		return sizeof(struct fc_rnid_acc_s) -746			sizeof(struct fc_rnid_general_topology_data_s);747	}748 749}750 751u16752fc_rpsc_build(struct fchs_s *fchs, struct fc_rpsc_cmd_s *rpsc, u32 d_id,753		u32 s_id, u16 ox_id)754{755	fc_els_req_build(fchs, d_id, s_id, ox_id);756 757	memset(rpsc, 0, sizeof(struct fc_rpsc_cmd_s));758 759	rpsc->els_cmd.els_code = FC_ELS_RPSC;760	return sizeof(struct fc_rpsc_cmd_s);761}762 763u16764fc_rpsc2_build(struct fchs_s *fchs, struct fc_rpsc2_cmd_s *rpsc2, u32 d_id,765		u32 s_id, u32 *pid_list, u16 npids)766{767	u32 dctlr_id = FC_DOMAIN_CTRLR(bfa_hton3b(d_id));768	int i = 0;769 770	fc_els_req_build(fchs, bfa_hton3b(dctlr_id), s_id, 0);771 772	memset(rpsc2, 0, sizeof(struct fc_rpsc2_cmd_s));773 774	rpsc2->els_cmd.els_code = FC_ELS_RPSC;775	rpsc2->token = cpu_to_be32(FC_BRCD_TOKEN);776	rpsc2->num_pids  = cpu_to_be16(npids);777	for (i = 0; i < npids; i++)778		rpsc2->pid_list[i].pid = pid_list[i];779 780	return sizeof(struct fc_rpsc2_cmd_s) + ((npids - 1) * (sizeof(u32)));781}782 783u16784fc_rpsc_acc_build(struct fchs_s *fchs, struct fc_rpsc_acc_s *rpsc_acc,785		u32 d_id, u32 s_id, __be16 ox_id,786		  struct fc_rpsc_speed_info_s *oper_speed)787{788	memset(rpsc_acc, 0, sizeof(struct fc_rpsc_acc_s));789 790	fc_els_rsp_build(fchs, d_id, s_id, ox_id);791 792	rpsc_acc->command = FC_ELS_ACC;793	rpsc_acc->num_entries = cpu_to_be16(1);794 795	rpsc_acc->speed_info[0].port_speed_cap =796		cpu_to_be16(oper_speed->port_speed_cap);797 798	rpsc_acc->speed_info[0].port_op_speed =799		cpu_to_be16(oper_speed->port_op_speed);800 801	return sizeof(struct fc_rpsc_acc_s);802}803 804u16805fc_pdisc_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id,806	       wwn_t port_name, wwn_t node_name, u16 pdu_size)807{808	struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1);809 810	memcpy(pdisc, &plogi_tmpl, sizeof(struct fc_logi_s));811 812	pdisc->els_cmd.els_code = FC_ELS_PDISC;813	fc_els_req_build(fchs, d_id, s_id, ox_id);814 815	pdisc->csp.rxsz = pdisc->class3.rxsz = cpu_to_be16(pdu_size);816	pdisc->port_name = port_name;817	pdisc->node_name = node_name;818 819	return sizeof(struct fc_logi_s);820}821 822u16823fc_pdisc_rsp_parse(struct fchs_s *fchs, int len, wwn_t port_name)824{825	struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1);826 827	if (len < sizeof(struct fc_logi_s))828		return FC_PARSE_LEN_INVAL;829 830	if (pdisc->els_cmd.els_code != FC_ELS_ACC)831		return FC_PARSE_ACC_INVAL;832 833	if (!wwn_is_equal(pdisc->port_name, port_name))834		return FC_PARSE_PWWN_NOT_EQUAL;835 836	if (!pdisc->class3.class_valid)837		return FC_PARSE_NWWN_NOT_EQUAL;838 839	if (be16_to_cpu(pdisc->class3.rxsz) < (FC_MIN_PDUSZ))840		return FC_PARSE_RXSZ_INVAL;841 842	return FC_PARSE_OK;843}844 845u16846fc_prlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id,847	      int num_pages)848{849	struct fc_prlo_s *prlo = (struct fc_prlo_s *) (fchs + 1);850	int             page;851 852	fc_els_req_build(fchs, d_id, s_id, ox_id);853	memset(prlo, 0, (num_pages * 16) + 4);854	prlo->command = FC_ELS_PRLO;855	prlo->page_len = 0x10;856	prlo->payload_len = cpu_to_be16((num_pages * 16) + 4);857 858	for (page = 0; page < num_pages; page++) {859		prlo->prlo_params[page].type = FC_TYPE_FCP;860		prlo->prlo_params[page].opa_valid = 0;861		prlo->prlo_params[page].rpa_valid = 0;862		prlo->prlo_params[page].orig_process_assc = 0;863		prlo->prlo_params[page].resp_process_assc = 0;864	}865 866	return be16_to_cpu(prlo->payload_len);867}868 869u16870fc_tprlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id,871	       int num_pages, enum fc_tprlo_type tprlo_type, u32 tpr_id)872{873	struct fc_tprlo_s *tprlo = (struct fc_tprlo_s *) (fchs + 1);874	int             page;875 876	fc_els_req_build(fchs, d_id, s_id, ox_id);877	memset(tprlo, 0, (num_pages * 16) + 4);878	tprlo->command = FC_ELS_TPRLO;879	tprlo->page_len = 0x10;880	tprlo->payload_len = cpu_to_be16((num_pages * 16) + 4);881 882	for (page = 0; page < num_pages; page++) {883		tprlo->tprlo_params[page].type = FC_TYPE_FCP;884		tprlo->tprlo_params[page].opa_valid = 0;885		tprlo->tprlo_params[page].rpa_valid = 0;886		tprlo->tprlo_params[page].orig_process_assc = 0;887		tprlo->tprlo_params[page].resp_process_assc = 0;888		if (tprlo_type == FC_GLOBAL_LOGO) {889			tprlo->tprlo_params[page].global_process_logout = 1;890		} else if (tprlo_type == FC_TPR_LOGO) {891			tprlo->tprlo_params[page].tpo_nport_valid = 1;892			tprlo->tprlo_params[page].tpo_nport_id = (tpr_id);893		}894	}895 896	return be16_to_cpu(tprlo->payload_len);897}898 899u16900fc_ba_rjt_build(struct fchs_s *fchs, u32 d_id, u32 s_id, __be16 ox_id,901		u32 reason_code, u32 reason_expl)902{903	struct fc_ba_rjt_s *ba_rjt = (struct fc_ba_rjt_s *) (fchs + 1);904 905	fc_bls_rsp_build(fchs, d_id, s_id, ox_id);906 907	fchs->cat_info = FC_CAT_BA_RJT;908	ba_rjt->reason_code = reason_code;909	ba_rjt->reason_expl = reason_expl;910	return sizeof(struct fc_ba_rjt_s);911}912 913static void914fc_gs_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code)915{916	memset(cthdr, 0, sizeof(struct ct_hdr_s));917	cthdr->rev_id = CT_GS3_REVISION;918	cthdr->gs_type = CT_GSTYPE_DIRSERVICE;919	cthdr->gs_sub_type = CT_GSSUBTYPE_NAMESERVER;920	cthdr->cmd_rsp_code = cpu_to_be16(cmd_code);921}922 923static void924fc_gs_fdmi_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code)925{926	memset(cthdr, 0, sizeof(struct ct_hdr_s));927	cthdr->rev_id = CT_GS3_REVISION;928	cthdr->gs_type = CT_GSTYPE_MGMTSERVICE;929	cthdr->gs_sub_type = CT_GSSUBTYPE_HBA_MGMTSERVER;930	cthdr->cmd_rsp_code = cpu_to_be16(cmd_code);931}932 933static void934fc_gs_ms_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code,935					 u8 sub_type)936{937	memset(cthdr, 0, sizeof(struct ct_hdr_s));938	cthdr->rev_id = CT_GS3_REVISION;939	cthdr->gs_type = CT_GSTYPE_MGMTSERVICE;940	cthdr->gs_sub_type = sub_type;941	cthdr->cmd_rsp_code = cpu_to_be16(cmd_code);942}943 944u16945fc_gidpn_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,946	       wwn_t port_name)947{948	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;949	struct fcgs_gidpn_req_s *gidpn = (struct fcgs_gidpn_req_s *)(cthdr + 1);950	u32        d_id = bfa_hton3b(FC_NAME_SERVER);951 952	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);953	fc_gs_cthdr_build(cthdr, s_id, GS_GID_PN);954 955	memset(gidpn, 0, sizeof(struct fcgs_gidpn_req_s));956	gidpn->port_name = port_name;957	return sizeof(struct fcgs_gidpn_req_s) + sizeof(struct ct_hdr_s);958}959 960u16961fc_gpnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,962	       u32 port_id)963{964	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;965	fcgs_gpnid_req_t *gpnid = (fcgs_gpnid_req_t *) (cthdr + 1);966	u32        d_id = bfa_hton3b(FC_NAME_SERVER);967 968	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);969	fc_gs_cthdr_build(cthdr, s_id, GS_GPN_ID);970 971	memset(gpnid, 0, sizeof(fcgs_gpnid_req_t));972	gpnid->dap = port_id;973	return sizeof(fcgs_gpnid_req_t) + sizeof(struct ct_hdr_s);974}975 976u16977fc_gnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,978	       u32 port_id)979{980	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;981	fcgs_gnnid_req_t *gnnid = (fcgs_gnnid_req_t *) (cthdr + 1);982	u32        d_id = bfa_hton3b(FC_NAME_SERVER);983 984	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);985	fc_gs_cthdr_build(cthdr, s_id, GS_GNN_ID);986 987	memset(gnnid, 0, sizeof(fcgs_gnnid_req_t));988	gnnid->dap = port_id;989	return sizeof(fcgs_gnnid_req_t) + sizeof(struct ct_hdr_s);990}991 992u16993fc_ct_rsp_parse(struct ct_hdr_s *cthdr)994{995	if (be16_to_cpu(cthdr->cmd_rsp_code) != CT_RSP_ACCEPT) {996		if (cthdr->reason_code == CT_RSN_LOGICAL_BUSY)997			return FC_PARSE_BUSY;998		else999			return FC_PARSE_FAILURE;1000	}1001 1002	return FC_PARSE_OK;1003}1004 1005u161006fc_gs_rjt_build(struct fchs_s *fchs,  struct ct_hdr_s *cthdr,1007		u32 d_id, u32 s_id, u16 ox_id, u8 reason_code,1008		u8 reason_code_expl)1009{1010	fc_gsresp_fchdr_build(fchs, d_id, s_id, ox_id);1011 1012	cthdr->cmd_rsp_code = cpu_to_be16(CT_RSP_REJECT);1013	cthdr->rev_id = CT_GS3_REVISION;1014 1015	cthdr->reason_code = reason_code;1016	cthdr->exp_code    = reason_code_expl;1017	return sizeof(struct ct_hdr_s);1018}1019 1020u161021fc_scr_build(struct fchs_s *fchs, struct fc_scr_s *scr,1022		u8 set_br_reg, u32 s_id, u16 ox_id)1023{1024	u32        d_id = bfa_hton3b(FC_FABRIC_CONTROLLER);1025 1026	fc_els_req_build(fchs, d_id, s_id, ox_id);1027 1028	memset(scr, 0, sizeof(struct fc_scr_s));1029	scr->command = FC_ELS_SCR;1030	scr->reg_func = FC_SCR_REG_FUNC_FULL;1031	if (set_br_reg)1032		scr->vu_reg_func = FC_VU_SCR_REG_FUNC_FABRIC_NAME_CHANGE;1033 1034	return sizeof(struct fc_scr_s);1035}1036 1037u161038fc_rscn_build(struct fchs_s *fchs, struct fc_rscn_pl_s *rscn,1039		u32 s_id, u16 ox_id)1040{1041	u32        d_id = bfa_hton3b(FC_FABRIC_CONTROLLER);1042	u16        payldlen;1043 1044	fc_els_req_build(fchs, d_id, s_id, ox_id);1045	rscn->command = FC_ELS_RSCN;1046	rscn->pagelen = sizeof(rscn->event[0]);1047 1048	payldlen = sizeof(u32) + rscn->pagelen;1049	rscn->payldlen = cpu_to_be16(payldlen);1050 1051	rscn->event[0].format = FC_RSCN_FORMAT_PORTID;1052	rscn->event[0].portid = s_id;1053 1054	return struct_size(rscn, event, 1);1055}1056 1057u161058fc_rftid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,1059	       enum bfa_lport_role roles)1060{1061	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1062	struct fcgs_rftid_req_s *rftid = (struct fcgs_rftid_req_s *)(cthdr + 1);1063	u32        type_value, d_id = bfa_hton3b(FC_NAME_SERVER);1064	u8         index;1065 1066	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);1067	fc_gs_cthdr_build(cthdr, s_id, GS_RFT_ID);1068 1069	memset(rftid, 0, sizeof(struct fcgs_rftid_req_s));1070 1071	rftid->dap = s_id;1072 1073	/* By default, FCP FC4 Type is registered */1074	index = FC_TYPE_FCP >> 5;1075	type_value = 1 << (FC_TYPE_FCP % 32);1076	rftid->fc4_type[index] = cpu_to_be32(type_value);1077 1078	return sizeof(struct fcgs_rftid_req_s) + sizeof(struct ct_hdr_s);1079}1080 1081u161082fc_rftid_build_sol(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,1083		   u8 *fc4_bitmap, u32 bitmap_size)1084{1085	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1086	struct fcgs_rftid_req_s *rftid = (struct fcgs_rftid_req_s *)(cthdr + 1);1087	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1088 1089	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);1090	fc_gs_cthdr_build(cthdr, s_id, GS_RFT_ID);1091 1092	memset(rftid, 0, sizeof(struct fcgs_rftid_req_s));1093 1094	rftid->dap = s_id;1095	memcpy((void *)rftid->fc4_type, (void *)fc4_bitmap,1096		(bitmap_size < 32 ? bitmap_size : 32));1097 1098	return sizeof(struct fcgs_rftid_req_s) + sizeof(struct ct_hdr_s);1099}1100 1101u161102fc_rffid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,1103	       u8 fc4_type, u8 fc4_ftrs)1104{1105	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1106	struct fcgs_rffid_req_s *rffid = (struct fcgs_rffid_req_s *)(cthdr + 1);1107	u32         d_id = bfa_hton3b(FC_NAME_SERVER);1108 1109	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);1110	fc_gs_cthdr_build(cthdr, s_id, GS_RFF_ID);1111 1112	memset(rffid, 0, sizeof(struct fcgs_rffid_req_s));1113 1114	rffid->dap	    = s_id;1115	rffid->fc4ftr_bits  = fc4_ftrs;1116	rffid->fc4_type	    = fc4_type;1117 1118	return sizeof(struct fcgs_rffid_req_s) + sizeof(struct ct_hdr_s);1119}1120 1121u161122fc_rspnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id,1123		u8 *name)1124{1125 1126	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1127	struct fcgs_rspnid_req_s *rspnid =1128			(struct fcgs_rspnid_req_s *)(cthdr + 1);1129	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1130 1131	fc_gs_fchdr_build(fchs, d_id, s_id, ox_id);1132	fc_gs_cthdr_build(cthdr, s_id, GS_RSPN_ID);1133 1134	memset(rspnid, 0, sizeof(struct fcgs_rspnid_req_s));1135 1136	rspnid->dap = s_id;1137	strscpy(rspnid->spn, name, sizeof(rspnid->spn));1138	rspnid->spn_len = (u8) strlen(rspnid->spn);1139 1140	return sizeof(struct fcgs_rspnid_req_s) + sizeof(struct ct_hdr_s);1141}1142 1143u161144fc_rsnn_nn_build(struct fchs_s *fchs, void *pyld, u32 s_id,1145			wwn_t node_name, u8 *name)1146{1147	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1148	struct fcgs_rsnn_nn_req_s *rsnn_nn =1149		(struct fcgs_rsnn_nn_req_s *) (cthdr + 1);1150	u32	d_id = bfa_hton3b(FC_NAME_SERVER);1151 1152	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1153	fc_gs_cthdr_build(cthdr, s_id, GS_RSNN_NN);1154 1155	memset(rsnn_nn, 0, sizeof(struct fcgs_rsnn_nn_req_s));1156 1157	rsnn_nn->node_name = node_name;1158	strscpy(rsnn_nn->snn, name, sizeof(rsnn_nn->snn));1159	rsnn_nn->snn_len = (u8) strlen(rsnn_nn->snn);1160 1161	return sizeof(struct fcgs_rsnn_nn_req_s) + sizeof(struct ct_hdr_s);1162}1163 1164u161165fc_gid_ft_build(struct fchs_s *fchs, void *pyld, u32 s_id, u8 fc4_type)1166{1167 1168	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1169	struct fcgs_gidft_req_s *gidft = (struct fcgs_gidft_req_s *)(cthdr + 1);1170	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1171 1172	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1173 1174	fc_gs_cthdr_build(cthdr, s_id, GS_GID_FT);1175 1176	memset(gidft, 0, sizeof(struct fcgs_gidft_req_s));1177	gidft->fc4_type = fc4_type;1178	gidft->domain_id = 0;1179	gidft->area_id = 0;1180 1181	return sizeof(struct fcgs_gidft_req_s) + sizeof(struct ct_hdr_s);1182}1183 1184u161185fc_rpnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id,1186	       wwn_t port_name)1187{1188	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1189	struct fcgs_rpnid_req_s *rpnid = (struct fcgs_rpnid_req_s *)(cthdr + 1);1190	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1191 1192	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1193	fc_gs_cthdr_build(cthdr, s_id, GS_RPN_ID);1194 1195	memset(rpnid, 0, sizeof(struct fcgs_rpnid_req_s));1196	rpnid->port_id = port_id;1197	rpnid->port_name = port_name;1198 1199	return sizeof(struct fcgs_rpnid_req_s) + sizeof(struct ct_hdr_s);1200}1201 1202u161203fc_rnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id,1204	       wwn_t node_name)1205{1206	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1207	struct fcgs_rnnid_req_s *rnnid = (struct fcgs_rnnid_req_s *)(cthdr + 1);1208	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1209 1210	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1211	fc_gs_cthdr_build(cthdr, s_id, GS_RNN_ID);1212 1213	memset(rnnid, 0, sizeof(struct fcgs_rnnid_req_s));1214	rnnid->port_id = port_id;1215	rnnid->node_name = node_name;1216 1217	return sizeof(struct fcgs_rnnid_req_s) + sizeof(struct ct_hdr_s);1218}1219 1220u161221fc_rcsid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id,1222	       u32 cos)1223{1224	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1225	struct fcgs_rcsid_req_s *rcsid =1226			(struct fcgs_rcsid_req_s *) (cthdr + 1);1227	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1228 1229	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1230	fc_gs_cthdr_build(cthdr, s_id, GS_RCS_ID);1231 1232	memset(rcsid, 0, sizeof(struct fcgs_rcsid_req_s));1233	rcsid->port_id = port_id;1234	rcsid->cos = cos;1235 1236	return sizeof(struct fcgs_rcsid_req_s) + sizeof(struct ct_hdr_s);1237}1238 1239u161240fc_rptid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id,1241	       u8 port_type)1242{1243	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1244	struct fcgs_rptid_req_s *rptid = (struct fcgs_rptid_req_s *)(cthdr + 1);1245	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1246 1247	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1248	fc_gs_cthdr_build(cthdr, s_id, GS_RPT_ID);1249 1250	memset(rptid, 0, sizeof(struct fcgs_rptid_req_s));1251	rptid->port_id = port_id;1252	rptid->port_type = port_type;1253 1254	return sizeof(struct fcgs_rptid_req_s) + sizeof(struct ct_hdr_s);1255}1256 1257u161258fc_ganxt_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id)1259{1260	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1261	struct fcgs_ganxt_req_s *ganxt = (struct fcgs_ganxt_req_s *)(cthdr + 1);1262	u32        d_id = bfa_hton3b(FC_NAME_SERVER);1263 1264	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1265	fc_gs_cthdr_build(cthdr, s_id, GS_GA_NXT);1266 1267	memset(ganxt, 0, sizeof(struct fcgs_ganxt_req_s));1268	ganxt->port_id = port_id;1269 1270	return sizeof(struct ct_hdr_s) + sizeof(struct fcgs_ganxt_req_s);1271}1272 1273/*1274 * Builds fc hdr and ct hdr for FDMI requests.1275 */1276u161277fc_fdmi_reqhdr_build(struct fchs_s *fchs, void *pyld, u32 s_id,1278		     u16 cmd_code)1279{1280 1281	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1282	u32        d_id = bfa_hton3b(FC_MGMT_SERVER);1283 1284	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1285	fc_gs_fdmi_cthdr_build(cthdr, s_id, cmd_code);1286 1287	return sizeof(struct ct_hdr_s);1288}1289 1290/*1291 * Given a FC4 Type, this function returns a fc4 type bitmask1292 */1293void1294fc_get_fc4type_bitmask(u8 fc4_type, u8 *bit_mask)1295{1296	u8         index;1297	__be32       *ptr = (__be32 *) bit_mask;1298	u32        type_value;1299 1300	/*1301	 * @todo : Check for bitmask size1302	 */1303 1304	index = fc4_type >> 5;1305	type_value = 1 << (fc4_type % 32);1306	ptr[index] = cpu_to_be32(type_value);1307 1308}1309 1310/*1311 *	GMAL Request1312 */1313u161314fc_gmal_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, wwn_t wwn)1315{1316	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1317	fcgs_gmal_req_t *gmal = (fcgs_gmal_req_t *) (cthdr + 1);1318	u32        d_id = bfa_hton3b(FC_MGMT_SERVER);1319 1320	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1321	fc_gs_ms_cthdr_build(cthdr, s_id, GS_FC_GMAL_CMD,1322			CT_GSSUBTYPE_CFGSERVER);1323 1324	memset(gmal, 0, sizeof(fcgs_gmal_req_t));1325	gmal->wwn = wwn;1326 1327	return sizeof(struct ct_hdr_s) + sizeof(fcgs_gmal_req_t);1328}1329 1330/*1331 * GFN (Get Fabric Name) Request1332 */1333u161334fc_gfn_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, wwn_t wwn)1335{1336	struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld;1337	fcgs_gfn_req_t *gfn = (fcgs_gfn_req_t *) (cthdr + 1);1338	u32        d_id = bfa_hton3b(FC_MGMT_SERVER);1339 1340	fc_gs_fchdr_build(fchs, d_id, s_id, 0);1341	fc_gs_ms_cthdr_build(cthdr, s_id, GS_FC_GFN_CMD,1342			CT_GSSUBTYPE_CFGSERVER);1343 1344	memset(gfn, 0, sizeof(fcgs_gfn_req_t));1345	gfn->wwn = wwn;1346 1347	return sizeof(struct ct_hdr_s) + sizeof(fcgs_gfn_req_t);1348}1349