FW: [openib-general] [PATCH] osm_sa_mcmember_record : MCMemberGet/GetTable Trusted mode
Ofer Gigi
oferg at mellanox.co.il
Thu Mar 23 08:04:45 PST 2006
Hi Hal,
The fix below fixes the retrieve of the mcmember records according to
the
Errata MGTWG3280.
Quoting from MGTWG3280:
SA can be queried for multicast groups by sending a SubnAdmGet() or a
SubnAdmGetTable() request to it using the SA query mechanism (see
15.4.4 Administration Query Subsystem on page 923).
What SA returns in response to a query of multicast groups depends
strongly on whether the request is or is not a trusted request; the
degree of trust affects both the data returned in each attribute and
the set of attributes that are returned. See <ref to C15-0.2.2:>.
o15-0.2.5 is made obsolete.
So we need to implement the following descriptive text:
SA can be queried for multicast groups by sending a SubnAdmGet() or a
SubnAdmGetTable() request to it using the SA query mechanism (see
15.4.4 Administration Query Subsystem on page 923). SA will return one
MCMemberRecord per multicast group matching the query, except in
cases where trust is specified as indicated in 15.4.1.2 Access
Restrictions
For Other Attributes on page 922; in that case all the MCMemberRecords
associated with the multicast group are returned. The MCMemberRecord
will be returned with the PortGID, ProxyJoin, and the JoinState
components
set to 0, except where trust is specified as indicated above, in that
case the actual contents for the above components will be provided.
Thanks
Ofer G.
Signed-off-by: Ofer Gigi <oferg at mellanox.co.il>
Index: osm_sa_mcmember_record.c
===================================================================
--- osm_sa_mcmember_record.c (revision 5919)
+++ osm_sa_mcmember_record.c (working copy)
@@ -91,6 +91,7 @@ typedef struct osm_sa_mcmr_search_ctx
cl_qlist_t *p_list; /* hold results */
ib_net64_t comp_mask;
const osm_physp_t* p_req_physp;
+ boolean_t trusted_req;
} osm_sa_mcmr_search_ctxt_t;
/**********************************************************************
@@ -1918,6 +1919,9 @@ __osm_sa_mcm_by_comp_mask_cb(
/* will be used for group or port info */
uint8_t scope_state;
uint8_t scope_state_mask = 0;
+ cl_map_item_t *p_item;
+ ib_gid_t port_gid;
+ boolean_t proxy_join;
OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_mcm_by_comp_mask_cb );
@@ -1938,39 +1942,28 @@ __osm_sa_mcm_by_comp_mask_cb(
/* first try to eliminate the group by MGID, MLID, or P_Key */
if ((IB_MCR_COMPMASK_MGID & comp_mask) &&
- cl_memcmp(&p_rcvd_rec->mgid, &p_mgrp->mcmember_rec.mgid,
sizeof(ib_gid_t))) {
+ cl_memcmp(&p_rcvd_rec->mgid,
+ &p_mgrp->mcmember_rec.mgid,
+ sizeof(ib_gid_t)))
+ {
goto Exit;
}
if ((IB_MCR_COMPMASK_MLID & comp_mask) &&
- cl_memcmp(&p_rcvd_rec->mlid, &p_mgrp->mcmember_rec.mlid,
sizeof(uint16_t))) {
+ cl_memcmp(&p_rcvd_rec->mlid,
+ &p_mgrp->mcmember_rec.mlid,
+ sizeof(uint16_t)))
+ {
goto Exit;
}
- /* if the requester physical port doesn't have the pkey that is
defined for the
- group - exit. */
- if (! osm_physp_has_pkey( p_rcv->p_log, p_mgrp->mcmember_rec.pkey,
p_req_physp ))
+ /* if the requester physical port doesn't have the pkey that is
defined for
+ the group - exit. */
+ if (! osm_physp_has_pkey( p_rcv->p_log,
+ p_mgrp->mcmember_rec.pkey,
+ p_req_physp ))
goto Exit;
- /* so did we get the PortGUID mask */
- if (IB_MCR_COMPMASK_PORT_GID & comp_mask)
- {
- /* try to find this port */
- if (osm_mgrp_is_port_present(p_mgrp, portguid, &p_mcm_port))
- {
- scope_state = p_mcm_port->scope_state;
- }
- else
- {
- /* port not in group */
- goto Exit;
- }
- }
- else
- {
- /* point to the group information */
- scope_state = p_mgrp->mcmember_rec.scope_state;
- }
/* now do the rest of the match */
if ((IB_MCR_COMPMASK_QKEY & comp_mask) &&
@@ -2004,17 +1997,15 @@ __osm_sa_mcm_by_comp_mask_cb(
if (query_hop != mgrp_hop) goto Exit;
}
+ if ((IB_MCR_COMPMASK_PROXY & comp_mask) &&
+ (p_rcvd_rec->proxy_join != p_mgrp->mcmember_rec.proxy_join)) goto
Exit;
+
if (IB_MCR_COMPMASK_SCOPE & comp_mask)
scope_state_mask = 0xF0;
if (IB_MCR_COMPMASK_JOIN_STATE & comp_mask)
scope_state_mask = scope_state_mask | 0x0F;
- if ((scope_state_mask & p_rcvd_rec->scope_state) !=
- (scope_state_mask & scope_state)) goto Exit;
-
- if ((IB_MCR_COMPMASK_PROXY & comp_mask) &&
- (p_rcvd_rec->proxy_join != p_mgrp->mcmember_rec.proxy_join)) goto
Exit;
/* need to validate mtu, rate, and pkt_lifetime fields. */
if (__validate_more_comp_fields( p_rcv->p_log,
@@ -2022,11 +2013,84 @@ __osm_sa_mcm_by_comp_mask_cb(
p_rcvd_rec,
comp_mask ) == FALSE) goto Exit;
+
+ /* Port specific fields */
+ /* so did we got the PortGUID mask */
+ if (IB_MCR_COMPMASK_PORT_GID & comp_mask)
+ {
+ /* try to find this port */
+ if (osm_mgrp_is_port_present(p_mgrp, portguid, &p_mcm_port))
+ {
+ scope_state = p_mcm_port->scope_state;
+ cl_memcpy(&port_gid, &(p_mcm_port->port_gid),
sizeof(ib_gid_t));
+ proxy_join=p_mcm_port->proxy_join;
+ }
+ else
+ {
+ /* port not in group */
+ goto Exit;
+ }
+ }
+ else
+ {
+ /* point to the group information */
+ scope_state = p_mgrp->mcmember_rec.scope_state;
+ }
+
+
+ /* Many MC record returned */
+ if ( (p_ctxt->trusted_req==TRUE) && !(IB_MCR_COMPMASK_PORT_GID &
comp_mask) )
+ {
+ osm_log(p_rcv->p_log, OSM_LOG_DEBUG,
+ "__osm_sa_mcm_by_comp_mask_cb: "
+ "trusted req is TRUE and no specific port
defined\n");
+
+ /* return all the ports the match in this MC group */
+ p_item = cl_qmap_head(&(p_mgrp->mcm_port_tbl));
+ while( p_item != cl_qmap_end(&(p_mgrp->mcm_port_tbl)) )
+ {
+ p_mcm_port=(osm_mcm_port_t *)p_item;
+
+ if ((scope_state_mask & p_rcvd_rec->scope_state) ==
+ (scope_state_mask & p_mcm_port->scope_state))
+ {
+ /* add to the list */
+ match_rec = p_mgrp->mcmember_rec;
+ match_rec.scope_state = p_mcm_port->scope_state;
+ cl_memcpy( &(match_rec.port_gid),
+ &(p_mcm_port->port_gid),
+ sizeof(ib_gid_t));
+ osm_log(p_rcv->p_log, OSM_LOG_DEBUG,
+ "__osm_sa_mcm_by_comp_mask_cb:
"
+ "record of port_gid: 0x%016"
PRIx64 "0x%016" PRIx64
+ " in multicast_lid: 0x%X is
returned\n",
+
cl_ntoh64(match_rec.port_gid.unicast.prefix),
+
cl_ntoh64(match_rec.port_gid.unicast.interface_id),
+ cl_ntoh16(p_mgrp->mlid)
+ );
+
+ match_rec.proxy_join =
(uint8_t)(p_mcm_port->proxy_join);
+
+ __osm_mcmr_rcv_new_mcmr(p_rcv, &match_rec,
p_ctxt->p_list);
+ }
+ p_item = cl_qmap_next(p_item);
+ }
+ }
+ /* One MC record returned */
+ else
+ {
+ if ((scope_state_mask & p_rcvd_rec->scope_state) !=
+ (scope_state_mask & scope_state)) goto Exit;
+
/* add to the list */
match_rec = p_mgrp->mcmember_rec;
match_rec.scope_state = scope_state;
+ cl_memcpy(&(match_rec.port_gid), &port_gid, sizeof(ib_gid_t));
+ match_rec.proxy_join = (uint8_t)proxy_join;
__osm_mcmr_rcv_new_mcmr(p_rcv, &match_rec, p_ctxt->p_list);
+ }
+
Exit:
OSM_LOG_EXIT( p_rcv->p_log );
}
@@ -2053,7 +2117,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t*
ib_api_status_t status;
ib_net64_t comp_mask;
osm_physp_t* p_req_physp;
- boolean_t trusted_req = TRUE;
+ boolean_t trusted_req;
CL_ASSERT( p_rcv );
@@ -2067,6 +2131,12 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t*
CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_MCMEMBER_RECORD );
+ /*
+ if sm_key is not zero and does not match we never get here
+ see main SA receiver
+ */
+ trusted_req = (p_rcvd_mad->sm_key != 0);
+
/* update the requester physical port. */
p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log,
p_rcv->p_subn,
@@ -2086,6 +2156,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t*
context.comp_mask = p_rcvd_mad->comp_mask;
context.p_rcv = p_rcv;
context.p_req_physp = p_req_physp;
+ context.trusted_req = trusted_req;
CL_PLOCK_ACQUIRE( p_rcv->p_lock );
@@ -2212,8 +2283,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t*
the mad is valid. Meaning - is either zero or equal to the local
sm_key.
*/
- if (p_rcvd_mad->sm_key == 0)
- trusted_req = FALSE;
+
for ( i = 0; i < pre_trim_num_rec; i++ )
{
More information about the general
mailing list