@@ -58,7 +58,13 @@ struct smc_llc_msg_add_link { /* type 0x02 */
5858 u8 sender_gid [SMC_GID_SIZE ];
5959 u8 sender_qp_num [3 ];
6060 u8 link_num ;
61- u8 flags2 ; /* QP mtu */
61+ #if defined(__BIG_ENDIAN_BITFIELD )
62+ u8 reserved3 : 4 ,
63+ qp_mtu : 4 ;
64+ #elif defined(__LITTLE_ENDIAN_BITFIELD )
65+ u8 qp_mtu : 4 ,
66+ reserved3 : 4 ;
67+ #endif
6268 u8 initial_psn [3 ];
6369 u8 reserved [8 ];
6470};
@@ -427,26 +433,9 @@ static int smc_llc_send_delete_rkey(struct smc_link *link,
427433 return rc ;
428434}
429435
430- /* prepare an add link message */
431- static void smc_llc_prep_add_link (struct smc_llc_msg_add_link * addllc ,
432- struct smc_link * link , u8 mac [], u8 gid [],
433- enum smc_llc_reqresp reqresp )
434- {
435- memset (addllc , 0 , sizeof (* addllc ));
436- addllc -> hd .common .type = SMC_LLC_ADD_LINK ;
437- addllc -> hd .length = sizeof (struct smc_llc_msg_add_link );
438- if (reqresp == SMC_LLC_RESP ) {
439- addllc -> hd .flags |= SMC_LLC_FLAG_RESP ;
440- /* always reject more links for now */
441- addllc -> hd .flags |= SMC_LLC_FLAG_ADD_LNK_REJ ;
442- addllc -> hd .add_link_rej_rsn = SMC_LLC_REJ_RSN_NO_ALT_PATH ;
443- }
444- memcpy (addllc -> sender_mac , mac , ETH_ALEN );
445- memcpy (addllc -> sender_gid , gid , SMC_GID_SIZE );
446- }
447-
448436/* send ADD LINK request or response */
449437int smc_llc_send_add_link (struct smc_link * link , u8 mac [], u8 gid [],
438+ struct smc_link * link_new ,
450439 enum smc_llc_reqresp reqresp )
451440{
452441 struct smc_llc_msg_add_link * addllc ;
@@ -458,32 +447,33 @@ int smc_llc_send_add_link(struct smc_link *link, u8 mac[], u8 gid[],
458447 if (rc )
459448 return rc ;
460449 addllc = (struct smc_llc_msg_add_link * )wr_buf ;
461- smc_llc_prep_add_link (addllc , link , mac , gid , reqresp );
450+
451+ memset (addllc , 0 , sizeof (* addllc ));
452+ addllc -> hd .common .type = SMC_LLC_ADD_LINK ;
453+ addllc -> hd .length = sizeof (struct smc_llc_msg_add_link );
454+ if (reqresp == SMC_LLC_RESP )
455+ addllc -> hd .flags |= SMC_LLC_FLAG_RESP ;
456+ memcpy (addllc -> sender_mac , mac , ETH_ALEN );
457+ memcpy (addllc -> sender_gid , gid , SMC_GID_SIZE );
458+ if (link_new ) {
459+ addllc -> link_num = link_new -> link_id ;
460+ hton24 (addllc -> sender_qp_num , link_new -> roce_qp -> qp_num );
461+ hton24 (addllc -> initial_psn , link_new -> psn_initial );
462+ if (reqresp == SMC_LLC_REQ )
463+ addllc -> qp_mtu = link_new -> path_mtu ;
464+ else
465+ addllc -> qp_mtu = min (link_new -> path_mtu ,
466+ link_new -> peer_mtu );
467+ }
462468 /* send llc message */
463469 rc = smc_wr_tx_send (link , pend );
464470 return rc ;
465471}
466472
467- /* prepare a delete link message */
468- static void smc_llc_prep_delete_link (struct smc_llc_msg_del_link * delllc ,
469- struct smc_link * link ,
470- enum smc_llc_reqresp reqresp , bool orderly )
471- {
472- memset (delllc , 0 , sizeof (* delllc ));
473- delllc -> hd .common .type = SMC_LLC_DELETE_LINK ;
474- delllc -> hd .length = sizeof (struct smc_llc_msg_add_link );
475- if (reqresp == SMC_LLC_RESP )
476- delllc -> hd .flags |= SMC_LLC_FLAG_RESP ;
477- /* DEL_LINK_ALL because only 1 link supported */
478- delllc -> hd .flags |= SMC_LLC_FLAG_DEL_LINK_ALL ;
479- if (orderly )
480- delllc -> hd .flags |= SMC_LLC_FLAG_DEL_LINK_ORDERLY ;
481- delllc -> link_num = link -> link_id ;
482- }
483-
484473/* send DELETE LINK request or response */
485- int smc_llc_send_delete_link (struct smc_link * link ,
486- enum smc_llc_reqresp reqresp , bool orderly )
474+ int smc_llc_send_delete_link (struct smc_link * link , u8 link_del_id ,
475+ enum smc_llc_reqresp reqresp , bool orderly ,
476+ u32 reason )
487477{
488478 struct smc_llc_msg_del_link * delllc ;
489479 struct smc_wr_tx_pend_priv * pend ;
@@ -494,7 +484,19 @@ int smc_llc_send_delete_link(struct smc_link *link,
494484 if (rc )
495485 return rc ;
496486 delllc = (struct smc_llc_msg_del_link * )wr_buf ;
497- smc_llc_prep_delete_link (delllc , link , reqresp , orderly );
487+
488+ memset (delllc , 0 , sizeof (* delllc ));
489+ delllc -> hd .common .type = SMC_LLC_DELETE_LINK ;
490+ delllc -> hd .length = sizeof (struct smc_llc_msg_del_link );
491+ if (reqresp == SMC_LLC_RESP )
492+ delllc -> hd .flags |= SMC_LLC_FLAG_RESP ;
493+ if (orderly )
494+ delllc -> hd .flags |= SMC_LLC_FLAG_DEL_LINK_ORDERLY ;
495+ if (link_del_id )
496+ delllc -> link_num = link_del_id ;
497+ else
498+ delllc -> hd .flags |= SMC_LLC_FLAG_DEL_LINK_ALL ;
499+ delllc -> reason = htonl (reason );
498500 /* send llc message */
499501 rc = smc_wr_tx_send (link , pend );
500502 return rc ;
@@ -547,12 +549,13 @@ static void smc_llc_rx_delete_link(struct smc_link *link,
547549 smc_lgr_forget (lgr );
548550 if (lgr -> role == SMC_SERV ) {
549551 /* client asks to delete this link, send request */
550- smc_llc_prep_delete_link (llc , link , SMC_LLC_REQ , true);
552+ smc_llc_send_delete_link (link , 0 , SMC_LLC_REQ , true,
553+ SMC_LLC_DEL_PROG_INIT_TERM );
551554 } else {
552555 /* server requests to delete this link, send response */
553- smc_llc_prep_delete_link (llc , link , SMC_LLC_RESP , true);
556+ smc_llc_send_delete_link (link , 0 , SMC_LLC_RESP , true,
557+ SMC_LLC_DEL_PROG_INIT_TERM );
554558 }
555- smc_llc_send_message (link , llc );
556559 smc_lgr_terminate_sched (lgr );
557560}
558561
0 commit comments